Upgrade macos

This commit is contained in:
Bassem Girgis
2025-03-19 08:52:56 -05:00
parent 53580cb51f
commit d29ef955f5
8041 changed files with 1936720 additions and 130842 deletions

View File

@@ -0,0 +1,251 @@
/* -*- Mode: C; c-basic-offset:4 ; -*- */
/*
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2014 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2007 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2010-2012 Oak Ridge National Labs. All rights reserved.
* Copyright (c) 2018-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2021 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*
*/
/** @file
*
* A bitmap implementation. The bits start off with 0, so this bitmap
* has bits numbered as bit 0, bit 1, bit 2 and so on. This bitmap
* has auto-expansion capabilities, that is once the size is set
* during init, it can be automatically expanded by setting the bit
* beyond the current size. But note, this is allowed just when the
* bit is set -- so the valid functions are set_bit and
* find_and_set_bit. Other functions like clear, if passed a bit
* outside the initialized range will result in an error.
*
* To allow these bitmaps to track fortran handles (which MPI defines
* to be Fortran INTEGER), we offer a pmix_bitmap_set_max_size, so that
* the upper layer can ask to never have more than
* OMPI_FORTRAN_HANDLE_MAX, which is min(INT_MAX, fortran INTEGER max).
*/
#ifndef PMIX_BITMAP_H
#define PMIX_BITMAP_H
#include "src/include/pmix_config.h"
#include <string.h>
#include "src/class/pmix_object.h"
BEGIN_C_DECLS
struct pmix_bitmap_t {
pmix_object_t super; /**< Subclass of pmix_object_t */
uint64_t *bitmap; /**< The actual bitmap array of characters */
int array_size; /**< The actual array size that maintains the bitmap */
int max_size; /**< The maximum size that this bitmap may grow (optional) */
};
typedef struct pmix_bitmap_t pmix_bitmap_t;
PMIX_EXPORT PMIX_CLASS_DECLARATION(pmix_bitmap_t);
/**
* Set the maximum size of the bitmap.
* May be reset any time, but HAS TO BE SET BEFORE pmix_bitmap_init!
*
* @param bitmap The input bitmap (IN)
* @param max_size The maximum size of the bitmap in terms of bits (IN)
* @return PMIX error code or success
*
*/
PMIX_EXPORT int pmix_bitmap_set_max_size(pmix_bitmap_t *bm, int max_size);
/**
* Initializes the bitmap and sets its size. This must be called
* before the bitmap can be actually used
*
* @param bitmap The input bitmap (IN)
* @param size The initial size of the bitmap in terms of bits (IN)
* @return PMIX error code or success
*
*/
PMIX_EXPORT int pmix_bitmap_init(pmix_bitmap_t *bm, int size);
/**
* Set a bit of the bitmap. If the bit asked for is beyond the current
* size of the bitmap, then the bitmap is extended to accommodate the
* bit
*
* @param bitmap The input bitmap (IN)
* @param bit The bit which is to be set (IN)
* @return PMIX error code or success
*
*/
PMIX_EXPORT int pmix_bitmap_set_bit(pmix_bitmap_t *bm, int bit);
/**
* Clear/unset a bit of the bitmap. If the bit is beyond the current
* size of the bitmap, an error is returned
*
* @param bitmap The input bitmap (IN)
* @param bit The bit which is to be cleared (IN)
* @return PMIX error code if the bit is out of range, else success
*
*/
PMIX_EXPORT int pmix_bitmap_clear_bit(pmix_bitmap_t *bm, int bit);
/**
* Find out if a bit is set in the bitmap
*
* @param bitmap The input bitmap (IN)
* @param bit The bit which is to be checked (IN)
* @return true if the bit is set
* false if the bit is not set OR the index
* is outside the bounds of the provided
* bitmap
*
*/
PMIX_EXPORT bool pmix_bitmap_is_set_bit(pmix_bitmap_t *bm, int bit);
/**
* Find the first clear bit in the bitmap and set it
*
* @param bitmap The input bitmap (IN)
* @param position Position of the first clear bit (OUT)
* @return err PMIX_SUCCESS on success
*/
PMIX_EXPORT int pmix_bitmap_find_and_set_first_unset_bit(pmix_bitmap_t *bm, int *position);
/**
* Clear all bits in the bitmap
*
* @param bitmap The input bitmap (IN)
* @return PMIX error code if bm is NULL
*
*/
PMIX_EXPORT int pmix_bitmap_clear_all_bits(pmix_bitmap_t *bm);
/**
* Set all bits in the bitmap
* @param bitmap The input bitmap (IN)
* @return PMIX error code if bm is NULL
*
*/
PMIX_EXPORT int pmix_bitmap_set_all_bits(pmix_bitmap_t *bm);
/**
* Gives the current size (number of bits) in the bitmap. This is the
* legal (accessible) number of bits
*
* @param bitmap The input bitmap (IN)
* @return PMIX error code if bm is NULL
*
*/
static inline int pmix_bitmap_size(pmix_bitmap_t *bm)
{
return (NULL == bm) ? 0 : (bm->array_size * ((int) (sizeof(*bm->bitmap) * 8)));
}
/**
* Copy a bitmap
*
* @param dest Pointer to the destination bitmap
* @param src Pointer to the source bitmap
* @ return PMIX error code if something goes wrong
*/
static inline void pmix_bitmap_copy(pmix_bitmap_t *dest, pmix_bitmap_t *src)
{
if (dest->array_size < src->array_size) {
if (NULL != dest->bitmap)
free(dest->bitmap);
dest->max_size = src->max_size;
dest->bitmap = (uint64_t *) malloc(src->array_size * sizeof(uint64_t));
}
memcpy(dest->bitmap, src->bitmap, src->array_size * sizeof(uint64_t));
dest->array_size = src->array_size;
}
/**
* Bitwise AND operator (inplace)
*
* @param dest Pointer to the bitmap that should be modified
* @param right Point to the other bitmap in the operation
* @return PMIX error code if the length of the two bitmaps is not equal or one is NULL.
*/
PMIX_EXPORT int pmix_bitmap_bitwise_and_inplace(pmix_bitmap_t *dest, pmix_bitmap_t *right);
/**
* Bitwise OR operator (inplace)
*
* @param dest Pointer to the bitmap that should be modified
* @param right Point to the other bitmap in the operation
* @return PMIX error code if the length of the two bitmaps is not equal or one is NULL.
*/
PMIX_EXPORT int pmix_bitmap_bitwise_or_inplace(pmix_bitmap_t *dest, pmix_bitmap_t *right);
/**
* Bitwise XOR operator (inplace)
*
* @param dest Pointer to the bitmap that should be modified
* @param right Point to the other bitmap in the operation
* @return PMIX error code if the length of the two bitmaps is not equal or one is NULL.
*/
PMIX_EXPORT int pmix_bitmap_bitwise_xor_inplace(pmix_bitmap_t *dest, pmix_bitmap_t *right);
/**
* If the bitmaps are different
*
* @param left Pointer to a bitmap
* @param right Pointer to another bitmap
* @return true if different, false if the same
*/
PMIX_EXPORT bool pmix_bitmap_are_different(pmix_bitmap_t *left, pmix_bitmap_t *right);
/**
* Get a string representation of the bitmap.
* Useful for debugging.
*
* @param bitmap Point to the bitmap to represent
* @return Pointer to the string (caller must free if not NULL)
*/
PMIX_EXPORT char *pmix_bitmap_get_string(pmix_bitmap_t *bitmap);
/**
* Return the number of 'unset' bits, up to the specified length
*
* @param bitmap Pointer to the bitmap
* @param len Number of bits to check
* @return Integer
*/
PMIX_EXPORT int pmix_bitmap_num_unset_bits(pmix_bitmap_t *bm, int len);
/**
* Return the number of 'set' bits, up to the specified length
*
* @param bitmap Pointer to the bitmap
* @param len Number of bits to check
* @return Integer
*/
PMIX_EXPORT int pmix_bitmap_num_set_bits(pmix_bitmap_t *bm, int len);
/**
* Check a bitmap to see if any bit is set
*/
PMIX_EXPORT bool pmix_bitmap_is_clear(pmix_bitmap_t *bm);
END_C_DECLS
#endif

View File

@@ -0,0 +1,427 @@
/*
* Copyright (c) 2004-2007 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2005 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2015-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2015-2016 Research Organization for Information Science
* and Technology (RIST). All rights reserved.
* Copyright (c) 2016 Mellanox Technologies, Inc.
* All rights reserved.
* Copyright (c) 2022 Triad National Security, LLC. All rights reserved.
*
* Copyright (c) 2021-2022 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*
*/
/** @file
*
* A hash table that may be indexed with either fixed length
* (e.g. uint32_t/uint64_t) or arbitrary size binary key
* values. However, only one key type may be used in a given table
* concurrently.
*/
#ifndef PMIX_HASH_TABLE_H
#define PMIX_HASH_TABLE_H
#include "src/include/pmix_config.h"
#include "src/include/pmix_prefetch.h"
#ifdef HAVE_STDINT_H
# include <stdint.h>
#endif
#include "src/class/pmix_list.h"
#include "pmix_common.h"
BEGIN_C_DECLS
PMIX_EXPORT PMIX_CLASS_DECLARATION(pmix_hash_table_t);
struct pmix_hash_table_t {
pmix_object_t super; /**< subclass of pmix_object_t */
const char *ht_label; /**< label for debugging */
struct pmix_hash_element_t *ht_table; /**< table of elements (opaque to users) */
size_t ht_capacity; /**< allocated size (capacity) of table */
size_t ht_size; /**< number of extant entries */
size_t ht_growth_trigger; /**< size hits this and table is grown */
int ht_density_numer, ht_density_denom; /**< max allowed density of table */
int ht_growth_numer, ht_growth_denom; /**< growth factor when grown */
const struct pmix_hash_type_methods_t *ht_type_methods;
};
typedef struct pmix_hash_table_t pmix_hash_table_t;
#define PMIX_HASH_TABLE_STATIC_INIT \
{ \
.super = PMIX_OBJ_STATIC_INIT(pmix_object_t), \
.ht_label = NULL, \
.ht_table = NULL, \
.ht_capacity = 0, \
.ht_size = 0, \
.ht_growth_trigger = 0, \
.ht_density_numer = 0, \
.ht_density_denom = 0, \
.ht_growth_numer = 0, \
.ht_growth_denom = 0, \
.ht_type_methods = NULL \
}
/**
* Initializes the table size, must be called before using
* the table.
*
* @param table The input hash table (IN).
* @param size The size of the table, which will be rounded up
* (if required) to the next highest power of two (IN).
* @return PMIX error code.
*
*/
PMIX_EXPORT int pmix_hash_table_init(pmix_hash_table_t *ht, size_t table_size);
/* this could be the new init if people wanted a more general API */
PMIX_EXPORT int pmix_hash_table_init2(pmix_hash_table_t *ht, size_t estimated_max_size,
int density_numer, int density_denom, int growth_numer,
int growth_denom);
/**
* Returns the number of elements currently stored in the table.
*
* @param table The input hash table (IN).
* @return The number of elements in the table.
*
*/
static inline size_t pmix_hash_table_get_size(pmix_hash_table_t *ht)
{
return ht->ht_size;
}
/**
* Remove all elements from the table.
*
* @param table The input hash table (IN).
* @return PMIX return code.
*
*/
PMIX_EXPORT int pmix_hash_table_remove_all(pmix_hash_table_t *ht);
/**
* Retrieve value via uint32_t key.
*
* @param table The input hash table (IN).
* @param key The input key (IN).
* @param ptr The value associated with the key
* @return integer return code:
* - PMIX_SUCCESS if key was found
* - PMIX_ERR_NOT_FOUND if key was not found
* - PMIX_ERROR other error
*
*/
PMIX_EXPORT int pmix_hash_table_get_value_uint32(pmix_hash_table_t *table, uint32_t key,
void **ptr);
/**
* Set value based on uint32_t key.
*
* @param table The input hash table (IN).
* @param key The input key (IN).
* @param value The value to be associated with the key (IN).
* @return PMIX return code.
*
*/
PMIX_EXPORT int pmix_hash_table_set_value_uint32(pmix_hash_table_t *table, uint32_t key,
void *value);
/**
* Remove value based on uint32_t key.
*
* @param table The input hash table (IN).
* @param key The input key (IN).
* @return PMIX return code.
*
*/
PMIX_EXPORT int pmix_hash_table_remove_value_uint32(pmix_hash_table_t *table, uint32_t key);
/**
* Retrieve value via uint64_t key.
*
* @param table The input hash table (IN).
* @param key The input key (IN).
* @param ptr The value associated with the key
* @return integer return code:
* - PMIX_SUCCESS if key was found
* - PMIX_ERR_NOT_FOUND if key was not found
* - PMIX_ERROR other error
*
*/
PMIX_EXPORT int pmix_hash_table_get_value_uint64(pmix_hash_table_t *table, uint64_t key,
void **ptr);
/**
* Set value based on uint64_t key.
*
* @param table The input hash table (IN).
* @param key The input key (IN).
* @param value The value to be associated with the key (IN).
* @return PMIX return code.
*
*/
PMIX_EXPORT int pmix_hash_table_set_value_uint64(pmix_hash_table_t *table, uint64_t key,
void *value);
/**
* Remove value based on uint64_t key.
*
* @param table The input hash table (IN).
* @param key The input key (IN).
* @return PMIX return code.
*
*/
PMIX_EXPORT int pmix_hash_table_remove_value_uint64(pmix_hash_table_t *table, uint64_t key);
/**
* Retrieve value via arbitrary length binary key.
*
* @param table The input hash table (IN).
* @param key The input key (IN).
* @param ptr The value associated with the key
* @return integer return code:
* - PMIX_SUCCESS if key was found
* - PMIX_ERR_NOT_FOUND if key was not found
* - PMIX_ERROR other error
*
*/
PMIX_EXPORT int pmix_hash_table_get_value_ptr(pmix_hash_table_t *table, const void *key,
size_t keylen, void **ptr);
/**
* Set value based on arbitrary length binary key.
*
* @param table The input hash table (IN).
* @param key The input key (IN).
* @param value The value to be associated with the key (IN).
* @return PMIX return code.
*
*/
PMIX_EXPORT int pmix_hash_table_set_value_ptr(pmix_hash_table_t *table, const void *key,
size_t keylen, void *value);
/**
* Remove value based on arbitrary length binary key.
*
* @param table The input hash table (IN).
* @param key The input key (IN).
* @return PMIX return code.
*
*/
PMIX_EXPORT int pmix_hash_table_remove_value_ptr(pmix_hash_table_t *table, const void *key,
size_t keylen);
/** The following functions are only for allowing iterating through
the hash table. The calls return along with a key, a pointer to
the hash node with the current key, so that subsequent calls do
not have to traverse all over again to the key (although it may
just be a simple thing - to go to the array element and then
traverse through the individual list). But lets take out this
inefficiency too. This is similar to having an STL iterator in
functionality */
/**
* Get the first 32 bit key from the hash table, which can be used later to
* get the next key
* @param table The hash table pointer (IN)
* @param key The first key (OUT)
* @param value The value corresponding to this key (OUT)
* @param node The pointer to the hash table internal node which stores
* the key-value pair (this is required for subsequent calls
* to get_next_key) (OUT)
* @return PMIX error code
*
*/
PMIX_EXPORT int pmix_hash_table_get_first_key_uint32(pmix_hash_table_t *table, uint32_t *key,
void **value, void **node);
/**
* Get the next 32 bit key from the hash table, knowing the current key
* @param table The hash table pointer (IN)
* @param key The key (OUT)
* @param value The value corresponding to this key (OUT)
* @param in_node The node pointer from previous call to either get_first
or get_next (IN)
* @param out_node The pointer to the hash table internal node which stores
* the key-value pair (this is required for subsequent calls
* to get_next_key) (OUT)
* @return PMIX error code
*
*/
PMIX_EXPORT int pmix_hash_table_get_next_key_uint32(pmix_hash_table_t *table, uint32_t *key,
void **value, void *in_node, void **out_node);
/**
* Get the first 64 key from the hash table, which can be used later to
* get the next key
* @param table The hash table pointer (IN)
* @param key The first key (OUT)
* @param value The value corresponding to this key (OUT)
* @param node The pointer to the hash table internal node which stores
* the key-value pair (this is required for subsequent calls
* to get_next_key) (OUT)
* @return PMIX error code
*
*/
PMIX_EXPORT int pmix_hash_table_get_first_key_uint64(pmix_hash_table_t *table, uint64_t *key,
void **value, void **node);
/**
* Get the next 64 bit key from the hash table, knowing the current key
* @param table The hash table pointer (IN)
* @param key The key (OUT)
* @param value The value corresponding to this key (OUT)
* @param in_node The node pointer from previous call to either get_first
or get_next (IN)
* @param out_node The pointer to the hash table internal node which stores
* the key-value pair (this is required for subsequent calls
* to get_next_key) (OUT)
* @return PMIX error code
*
*/
PMIX_EXPORT int pmix_hash_table_get_next_key_uint64(pmix_hash_table_t *table, uint64_t *key,
void **value, void *in_node, void **out_node);
/**
* Get the first ptr bit key from the hash table, which can be used later to
* get the next key
* @param table The hash table pointer (IN)
* @param key The first key (OUT)
* @param key_size The first key size (OUT)
* @param value The value corresponding to this key (OUT)
* @param node The pointer to the hash table internal node which stores
* the key-value pair (this is required for subsequent calls
* to get_next_key) (OUT)
* @return PMIX error code
*
*/
PMIX_EXPORT int pmix_hash_table_get_first_key_ptr(pmix_hash_table_t *table, void **key,
size_t *key_size, void **value, void **node);
/**
* Get the next ptr bit key from the hash table, knowing the current key
* @param table The hash table pointer (IN)
* @param key The key (OUT)
* @param key_size The key size (OUT)
* @param value The value corresponding to this key (OUT)
* @param in_node The node pointer from previous call to either get_first
or get_next (IN)
* @param out_node The pointer to the hash table internal node which stores
* the key-value pair (this is required for subsequent calls
* to get_next_key) (OUT)
* @return PMIX error code
*
*/
PMIX_EXPORT int pmix_hash_table_get_next_key_ptr(pmix_hash_table_t *table, void **key,
size_t *key_size, void **value, void *in_node,
void **out_node);
/**
* Returns the size of the opaque pmix_hash_element_t structure. Note that this
* only returns the size of the structure itself and does not capture the size
* of data that are stored within an element.
*/
PMIX_EXPORT size_t
pmix_hash_table_sizeof_hash_element(void);
/**
* @brief Returns next power-of-two of the given value.
*
* @param value The integer value to return power of 2
*
* @returns The next power of two
*
* WARNING: *NO* error checking is performed. This is meant to be a
* fast inline function.
* Using __builtin_clz (count-leading-zeros) uses 4 cycles instead of 77
* compared to the loop-version (on Intel Nehalem -- with icc-12.1.0 -O2).
*/
static inline int pmix_next_poweroftwo(int value)
{
int power2;
#if PMIX_C_HAVE_BUILTIN_CLZ
if (PMIX_UNLIKELY(0 == value)) {
return 1;
}
power2 = 1 << (8 * sizeof(int) - __builtin_clz(value));
#else
for (power2 = 1; value > 0; value >>= 1, power2 <<= 1) /* empty */
;
#endif
return power2;
}
/**
* Loop over a hash table.
*
* @param[in] key Key for each item
* @param[in] type Type of key (ui32|ui64|ptr)
* @param[in] value Storage for each item
* @param[in] ht Hash table to iterate over
*
* This macro provides a simple way to loop over the items in a pmix_hash_table_t. It
* is not safe to call pmix_hash_table_remove* from within the loop.
*
* Example Usage:
*
* uint64_t key;
* void * value;
* PMIX_HASH_TABLE_FOREACH(key, uint64, value, ht) {
* do_something(key, value);
* }
*/
#define PMIX_HASH_TABLE_FOREACH(key, type, value, ht) \
for (void *_nptr = NULL; \
PMIX_SUCCESS \
== pmix_hash_table_get_next_key_##type(ht, &key, (void **) &value, _nptr, &_nptr);)
#define PMIX_HASH_TABLE_FOREACH_PTR(key, value, ht, body) \
{ \
size_t key_size_; \
for (void *_nptr = NULL; \
PMIX_SUCCESS \
== pmix_hash_table_get_next_key_ptr(ht, &key, &key_size_, (void **) &value, _nptr, \
&_nptr);) \
body \
}
END_C_DECLS
#endif /* PMIX_HASH_TABLE_H */

View File

@@ -0,0 +1,378 @@
/* -*- Mode: C; c-basic-offset:4 ; indent-tabs-mode:nil -*- */
/*
* Copyright (c) 2012-2016 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2012 Los Alamos National Security, LLC. All rights reserved
* Copyright (c) 2015-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2019 Research Organization for Information Science
* and Technology (RIST). All rights reserved.
* Copyright (c) 2020 IBM Corporation. All rights reserved.
* Copyright (c) 2021-2022 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
/** @file
*
* This file provides a "hotel" class:
*
* - A hotel has a fixed number of rooms (i.e., storage slots)
* - An arbitrary data pointer can check into an empty room at any time
* - The occupant of a room can check out at any time
* - Optionally, the occupant of a room can be forcibly evicted at a
* given time (i.e., when an pmix timer event expires).
* - The hotel has finite occupancy; if you try to checkin a new
* occupant and the hotel is already full, it will gracefully fail
* to checkin.
*
* One use case for this class is for ACK-based network retransmission
* schemes (NACK-based retransmission schemes probably can use
* pmix_ring_buffer).
*
* For ACK-based retransmission schemes, a hotel might be used
* something like this:
*
* - when a message is sent, check it in to a hotel with a timer
* - if an ACK is received, check it out of the hotel (which also cancels
* the timer)
* - if an ACK isn't received in time, the timer will expire and the
* upper layer will get a callback with the message
* - if an ACK is received late (i.e., after its timer has expired),
* then checkout will gracefully fail
*
* Note that this class intentionally provides pretty minimal
* functionality. It is intended to be used in performance-critical
* code paths -- extra functionality would simply add latency.
*
* There is an pmix_hotel_init() function to create a hotel, but no
* corresponding finalize; the destructor will handle all finalization
* issues. Note that when a hotel is destroyed, it will delete all
* pending events from the event base (i.e., all pending eviction
* callbacks); no further eviction callbacks will be invoked.
*/
#ifndef PMIX_HOTEL_H
#define PMIX_HOTEL_H
#include "src/include/pmix_config.h"
#include "pmix_common.h"
#include "src/class/pmix_object.h"
#include "src/include/pmix_prefetch.h"
#include "src/include/pmix_types.h"
#include <event.h>
#include "src/util/pmix_error.h"
#include "src/util/pmix_output.h"
BEGIN_C_DECLS
struct pmix_hotel_t;
/* User-supplied function to be invoked when an occupant is evicted. */
typedef void (*pmix_hotel_eviction_callback_fn_t)(struct pmix_hotel_t *hotel, int room_num,
void *occupant);
/* Note that this is an internal data structure; it is not part of the
public pmix_hotel interface. Public consumers of pmix_hotel
shouldn't need to use this struct at all (we only have it here in
this .h file because some functions are inlined for speed, and need
to get to the internals of this struct).
The room struct should be as small as possible to be cache
friendly. Specifically: it would be great if multiple rooms could
fit in a single cache line because we'll always allocate a
contiguous set of rooms in an array. */
typedef struct {
void *occupant;
pmix_event_t eviction_timer_event;
} pmix_hotel_room_t;
/* Note that this is an internal data structure; it is not part of the
public pmix_hotel interface. Public consumers of pmix_hotel
shouldn't need to use this struct at all (we only have it here in
this .h file because some functions are inlined for speed, and need
to get to the internals of this struct).
Use a unique struct for holding the arguments for eviction
callbacks. We *could* make the to-be-evicted pmix_hotel_room_t
instance as the argument, but we don't, for 2 reasons:
1. We want as many pmix_hotel_room_t's to fit in a cache line as
possible (i.e., to be as cache-friendly as possible). The
common/fast code path only needs to access the data in the
pmix_hotel_room_t (and not the callback argument data).
2. Evictions will be uncommon, so we don't mind penalizing them a
bit by making the data be in a separate cache line.
*/
typedef struct {
struct pmix_hotel_t *hotel;
int room_num;
} pmix_hotel_room_eviction_callback_arg_t;
typedef struct pmix_hotel_t {
/* make this an object */
pmix_object_t super;
/* Max number of rooms in the hotel */
int num_rooms;
/* event base to be used for eviction timeout */
pmix_event_base_t *evbase;
struct timeval eviction_timeout;
pmix_hotel_eviction_callback_fn_t evict_callback_fn;
/* All rooms in this hotel */
pmix_hotel_room_t *rooms;
/* Separate array for all the eviction callback arguments (see
rationale above for why this is a separate array) */
pmix_hotel_room_eviction_callback_arg_t *eviction_args;
/* All currently unoccupied rooms in this hotel (not necessarily
in any particular order) */
int *unoccupied_rooms;
int last_unoccupied_room;
} pmix_hotel_t;
PMIX_EXPORT PMIX_CLASS_DECLARATION(pmix_hotel_t);
#define PMIX_HOTEL_STATIC_INIT \
{ \
.super = PMIX_OBJ_STATIC_INIT(pmix_object_t), \
.num_rooms = 0, \
.evbase = NULL, \
.eviction_timeout = {0, 0}, \
.evict_callback_fn = NULL, \
.rooms = NULL, \
.eviction_args = NULL, \
.unoccupied_rooms = NULL, \
.last_unoccupied_room = 0 \
}
/**
* Initialize the hotel.
*
* @param hotel Pointer to a hotel (IN)
* @param num_rooms The total number of rooms in the hotel (IN)
* @param evbase Pointer to event base used for eviction timeout
* @param eviction_timeout Max length of a stay at the hotel before
* the eviction callback is invoked (in seconds)
* @param evict_callback_fn Callback function invoked if an occupant
* does not check out before the eviction_timeout.
*
* NOTE: If the callback function is NULL, then no eviction timer
* will be set - occupants will remain checked into the hotel until
* explicitly checked out.
*
* Also note: the eviction_callback_fn should absolutely not call any
* of the hotel checkout functions. Specifically: the occupant has
* already been ("forcibly") checked out *before* the
* eviction_callback_fn is invoked.
*
* @return PMIX_SUCCESS if all initializations were successful. Otherwise,
* the error indicate what went wrong in the function.
*/
PMIX_EXPORT pmix_status_t pmix_hotel_init(pmix_hotel_t *hotel, int num_rooms,
pmix_event_base_t *evbase, uint32_t eviction_timeout,
pmix_hotel_eviction_callback_fn_t evict_callback_fn);
/**
* Check in an occupant to the hotel.
*
* @param hotel Pointer to hotel (IN)
* @param occupant Occupant to check in (opaque to the hotel) (IN)
* @param room The room number that identifies this occupant in the
* hotel (OUT).
*
* If there is room in the hotel, the occupant is checked in and the
* timer for that occupant is started. The occupant's room is
* returned in the "room" param.
*
* Note that once a room's checkout_expire timer expires, the occupant
* is forcibly checked out, and then the eviction callback is invoked.
*
* @return PMIX_SUCCESS if the occupant is successfully checked in,
* and the room parameter will contain a valid value.
* @return PMIX_ERR_TEMP_OUT_OF_RESOURCE is the hotel is full. Try
* again later.
*/
static inline pmix_status_t pmix_hotel_checkin(pmix_hotel_t *hotel, void *occupant, int *room_num)
{
pmix_hotel_room_t *room;
/* Do we have any rooms available? */
if (PMIX_UNLIKELY(hotel->last_unoccupied_room < 0)) {
*room_num = -1;
return PMIX_ERR_OUT_OF_RESOURCE;
}
/* Put this occupant into the first empty room that we have */
*room_num = hotel->unoccupied_rooms[hotel->last_unoccupied_room--];
room = &(hotel->rooms[*room_num]);
room->occupant = occupant;
/* Assign the event and make it pending */
if (NULL != hotel->evbase) {
pmix_event_add(&(room->eviction_timer_event), &(hotel->eviction_timeout));
}
return PMIX_SUCCESS;
}
/**
* Same as pmix_hotel_checkin(), but slightly optimized for when the
* caller *knows* that there is a room available.
*/
static inline void pmix_hotel_checkin_with_res(pmix_hotel_t *hotel, void *occupant, int *room_num)
{
pmix_hotel_room_t *room;
/* Put this occupant into the first empty room that we have */
*room_num = hotel->unoccupied_rooms[hotel->last_unoccupied_room--];
room = &(hotel->rooms[*room_num]);
assert(room->occupant == NULL);
room->occupant = occupant;
/* Assign the event and make it pending */
if (NULL != hotel->evbase) {
pmix_event_add(&(room->eviction_timer_event), &(hotel->eviction_timeout));
}
}
/**
* Check the specified occupant out of the hotel.
*
* @param hotel Pointer to hotel (IN)
* @param room Room number to checkout (IN)
*
* If there is an occupant in the room, their timer is canceled and
* they are checked out.
*
* Nothing is returned (as a minor optimization).
*/
static inline void pmix_hotel_checkout(pmix_hotel_t *hotel, int room_num)
{
pmix_hotel_room_t *room;
/* Bozo check */
assert(room_num < hotel->num_rooms);
if (0 > room_num) {
/* occupant wasn't checked in */
return;
}
/* If there's an occupant in the room, check them out */
room = &(hotel->rooms[room_num]);
if (PMIX_LIKELY(NULL != room->occupant)) {
/* Do not change this logic without also changing the same
logic in pmix_hotel_checkout_and_return_occupant() and
pmix_hotel.c:local_eviction_callback(). */
room->occupant = NULL;
if (NULL != hotel->evbase) {
pmix_event_del(&(room->eviction_timer_event));
}
hotel->last_unoccupied_room++;
assert(hotel->last_unoccupied_room < hotel->num_rooms);
hotel->unoccupied_rooms[hotel->last_unoccupied_room] = room_num;
}
/* Don't bother returning whether we actually checked someone out
or not (because this is in the critical performance path) --
assume the upper layer knows what it's doing. */
}
/**
* Check the specified occupant out of the hotel and return the occupant.
*
* @param hotel Pointer to hotel (IN)
* @param room Room number to checkout (IN)
* @param void * occupant (OUT)
* If there is an occupant in the room, their timer is canceled and
* they are checked out.
*
* Use this checkout and when caller needs the occupant
*/
static inline void pmix_hotel_checkout_and_return_occupant(pmix_hotel_t *hotel, int room_num,
void **occupant)
{
pmix_hotel_room_t *room;
/* Bozo check */
assert(room_num < hotel->num_rooms);
if (0 > room_num) {
/* occupant wasn't checked in */
*occupant = NULL;
return;
}
/* If there's an occupant in the room, check them out */
room = &(hotel->rooms[room_num]);
if (PMIX_LIKELY(NULL != room->occupant)) {
pmix_output(10, "checking out occupant %p from room num %d", room->occupant, room_num);
/* Do not change this logic without also changing the same
logic in pmix_hotel_checkout() and
pmix_hotel.c:local_eviction_callback(). */
*occupant = room->occupant;
room->occupant = NULL;
if (NULL != hotel->evbase) {
pmix_event_del(&(room->eviction_timer_event));
}
hotel->last_unoccupied_room++;
assert(hotel->last_unoccupied_room < hotel->num_rooms);
hotel->unoccupied_rooms[hotel->last_unoccupied_room] = room_num;
} else {
*occupant = NULL;
}
}
/**
* Returns true if the hotel is empty (no occupant)
* @param hotel Pointer to hotel (IN)
* @return bool true if empty false if there is a occupant(s)
*
*/
static inline bool pmix_hotel_is_empty(pmix_hotel_t *hotel)
{
if (hotel->last_unoccupied_room == hotel->num_rooms - 1)
return true;
else
return false;
}
/**
* Access the occupant of a room, but leave them checked into their room.
*
* @param hotel Pointer to hotel (IN)
* @param room Room number to checkout (IN)
* @param void * occupant (OUT)
*
* This accessor function is typically used to cycle across the occupants
* to check for someone already present that matches a description.
*/
static inline void pmix_hotel_knock(pmix_hotel_t *hotel, int room_num, void **occupant)
{
pmix_hotel_room_t *room;
/* Bozo check */
assert(room_num < hotel->num_rooms);
*occupant = NULL;
if (0 > room_num) {
/* occupant wasn't checked in */
return;
}
/* If there's an occupant in the room, have them come to the door */
room = &(hotel->rooms[room_num]);
if (PMIX_LIKELY(NULL != room->occupant)) {
pmix_output(10, "occupant %p in room num %d responded to knock", room->occupant, room_num);
*occupant = room->occupant;
}
}
END_C_DECLS
#endif /* PMIX_HOTEL_H */

View File

@@ -0,0 +1,918 @@
/* -*- Mode: C; c-basic-offset:4 ; -*- */
/*
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2006 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2007 Voltaire All rights reserved.
* Copyright (c) 2013 Los Alamos National Security, LLC. All rights
* reserved.
* Copyright (c) 2013-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2021-2022 Nanook Consulting All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
/**
* @file
*
* The pmix_list_t interface is used to provide a generic
* doubly-linked list container for PMIx. It was inspired by (but
* is slightly different than) the Standard Template Library (STL)
* std::list class. One notable difference from std::list is that
* when an pmix_list_t is destroyed, all of the pmix_list_item_t
* objects that it contains are orphaned -- they are \em not
* destroyed.
*
* The general idea is that pmix_list_item_t objects can be put on an
* pmix_list_t. Hence, you create a new type that derives from
* pmix_list_item_t; this new type can then be used with pmix_list_t
* containers.
*
* NOTE: pmix_list_item_t instances can only be on \em one list at a
* time. Specifically, if you add an pmix_list_item_t to one list,
* and then add it to another list (without first removing it from the
* first list), you will effectively be hosing the first list. You
* have been warned.
*
* If PMIX_ENABLE_DEBUG is true, a bunch of checks occur, including
* some spot checks for a debugging reference count in an attempt to
* ensure that an pmix_list_item_t is only one *one* list at a time.
* Given the highly concurrent nature of this class, these spot checks
* cannot guarantee that an item is only one list at a time.
* Specifically, since it is a desirable attribute of this class to
* not use locks for normal operations, it is possible that two
* threads may [erroneously] modify an pmix_list_item_t concurrently.
*
* The only way to guarantee that a debugging reference count is valid
* for the duration of an operation is to lock the item_t during the
* operation. But this fundamentally changes the desirable attribute
* of this class (i.e., no locks). So all we can do is spot-check the
* reference count in a bunch of places and check that it is still the
* value that we think it should be. But this doesn't mean that you
* can run into "unlucky" cases where two threads are concurrently
* modifying an item_t, but all the spot checks still return the
* "right" values. All we can do is hope that we have enough spot
* checks to statistically drive down the possibility of the unlucky
* cases happening.
*/
#ifndef PMIX_LIST_H
#define PMIX_LIST_H
#include "src/include/pmix_config.h"
#include <stdio.h>
#include <stdlib.h>
#if HAVE_STDBOOL_H
# include <stdbool.h>
#endif
#include "pmix_common.h"
#include "src/class/pmix_object.h"
BEGIN_C_DECLS
/**
* \internal
*
* The class for the list container.
*/
PMIX_EXPORT PMIX_CLASS_DECLARATION(pmix_list_t);
/**
* \internal
*
* Base class for items that are put in list (pmix_list_t) containers.
*/
PMIX_EXPORT PMIX_CLASS_DECLARATION(pmix_list_item_t);
/**
* \internal
*
* Struct of an pmix_list_item_t
*/
struct pmix_list_item_t {
pmix_object_t super;
/**< Generic parent class for all PMIx objects */
volatile struct pmix_list_item_t *pmix_list_next;
/**< Pointer to next list item */
volatile struct pmix_list_item_t *pmix_list_prev;
/**< Pointer to previous list item */
int32_t item_free;
#if PMIX_ENABLE_DEBUG
/** Atomic reference count for debugging */
int32_t pmix_list_item_refcount;
/** The list this item belong to */
volatile struct pmix_list_t *pmix_list_item_belong_to;
#endif
};
/**
* Base type for items that are put in a list (pmix_list_t) containers.
*/
typedef struct pmix_list_item_t pmix_list_item_t;
/* static initializer for pmix_list_t */
#define PMIX_LIST_ITEM_STATIC_INIT \
{ \
.super = PMIX_OBJ_STATIC_INIT(pmix_object_t), \
.pmix_list_next = NULL, \
.pmix_list_prev = NULL, \
.item_free = 0 \
}
/**
* Get the next item in a list.
*
* @param item A list item.
*
* @returns The next item in the list
*/
#define pmix_list_get_next(item) \
((item) ? ((pmix_list_item_t *) ((pmix_list_item_t *) (item))->pmix_list_next) : NULL)
/**
* Get the next item in a list.
*
* @param item A list item.
*
* @returns The next item in the list
*/
#define pmix_list_get_prev(item) \
((item) ? ((pmix_list_item_t *) ((pmix_list_item_t *) (item))->pmix_list_prev) : NULL)
/**
* \internal
*
* Struct of an pmix_list_t
*/
struct pmix_list_t {
pmix_object_t super;
/**< Generic parent class for all PMIx objects */
pmix_list_item_t pmix_list_sentinel;
/**< Head and tail item of the list */
volatile size_t pmix_list_length;
/**< Quick reference to the number of items in the list */
};
/**
* List container type.
*/
typedef struct pmix_list_t pmix_list_t;
/* static initializer for pmix_list_t */
#define PMIX_LIST_STATIC_INIT \
{ \
.super = PMIX_OBJ_STATIC_INIT(pmix_object_t), \
.pmix_list_sentinel = PMIX_LIST_ITEM_STATIC_INIT, \
.pmix_list_length = 0 \
}
/** Cleanly destruct a list
*
* The pmix_list_t destructor doesn't release the items on the
* list - so provide two convenience macros that do so and then
* destruct/release the list object itself
*
* @param[in] list List to destruct or release
*/
#define PMIX_LIST_DESTRUCT(list) \
do { \
pmix_list_item_t *it; \
while (NULL != (it = pmix_list_remove_first(list))) { \
PMIX_RELEASE(it); \
} \
PMIX_DESTRUCT(list); \
} while (0)
#define PMIX_LIST_RELEASE(list) \
do { \
pmix_list_item_t *it; \
while (NULL != (it = pmix_list_remove_first(list))) { \
PMIX_RELEASE(it); \
} \
PMIX_RELEASE(list); \
} while (0)
/**
* Loop over a list.
*
* @param[in] item Storage for each item
* @param[in] list List to iterate over
* @param[in] type Type of each list item
*
* This macro provides a simple way to loop over the items in an pmix_list_t. It
* is not safe to call pmix_list_remove_item from within the loop.
*
* Example Usage:
*
* class_foo_t *foo;
* pmix_list_foreach(foo, list, class_foo_t) {
* do something;
* }
*/
#define PMIX_LIST_FOREACH(item, list, type) \
for (item = (type *) (list)->pmix_list_sentinel.pmix_list_next; \
item != (type *) &(list)->pmix_list_sentinel; \
item = (type *) ((pmix_list_item_t *) (item))->pmix_list_next)
#define PMIX_LIST_FOREACH_DECL(item, list, type) \
for (type *item = (type *) (list)->pmix_list_sentinel.pmix_list_next; \
item != (type *) &(list)->pmix_list_sentinel; \
item = (type *) ((pmix_list_item_t *) (item))->pmix_list_next)
/**
* Loop over a list in reverse.
*
* @param[in] item Storage for each item
* @param[in] list List to iterate over
* @param[in] type Type of each list item
*
* This macro provides a simple way to loop over the items in an pmix_list_t. It
* is not safe to call pmix_list_remove_item from within the loop.
*
* Example Usage:
*
* class_foo_t *foo;
* pmix_list_foreach(foo, list, class_foo_t) {
* do something;
* }
*/
#define PMIX_LIST_FOREACH_REV(item, list, type) \
for (item = (type *) (list)->pmix_list_sentinel.pmix_list_prev; \
item != (type *) &(list)->pmix_list_sentinel; \
item = (type *) ((pmix_list_item_t *) (item))->pmix_list_prev)
/**
* Loop over a list in a *safe* way
*
* @param[in] item Storage for each item
* @param[in] next Storage for next item
* @param[in] list List to iterate over
* @param[in] type Type of each list item
*
* This macro provides a simple way to loop over the items in an pmix_list_t. It
* is safe to call pmix_list_remove_item(list, item) from within the loop.
*
* Example Usage:
*
* class_foo_t *foo, *next;
* pmix_list_foreach_safe(foo, next, list, class_foo_t) {
* do something;
* pmix_list_remove_item (list, (pmix_list_item_t *) foo);
* }
*/
#define PMIX_LIST_FOREACH_SAFE(item, next, list, type) \
for (item = (type *) (list)->pmix_list_sentinel.pmix_list_next, \
next = (type *) ((pmix_list_item_t *) (item))->pmix_list_next; \
item != (type *) &(list)->pmix_list_sentinel; \
item = next, next = (type *) ((pmix_list_item_t *) (item))->pmix_list_next)
/**
* Loop over a list in a *safe* way
*
* @param[in] item Storage for each item
* @param[in] next Storage for next item
* @param[in] list List to iterate over
* @param[in] type Type of each list item
*
* This macro provides a simple way to loop over the items in an pmix_list_t. If
* is safe to call pmix_list_remove_item(list, item) from within the loop.
*
* Example Usage:
*
* class_foo_t *foo, *next;
* pmix_list_foreach_safe(foo, next, list, class_foo_t) {
* do something;
* pmix_list_remove_item (list, (pmix_list_item_t *) foo);
* }
*/
#define PMIX_LIST_FOREACH_SAFE_REV(item, prev, list, type) \
for (item = (type *) (list)->pmix_list_sentinel.pmix_list_prev, \
prev = (type *) ((pmix_list_item_t *) (item))->pmix_list_prev; \
item != (type *) &(list)->pmix_list_sentinel; \
item = prev, prev = (type *) ((pmix_list_item_t *) (item))->pmix_list_prev)
/**
* Check for empty list
*
* @param list The list container
*
* @returns true if list's size is 0, false otherwise
*
* This is an O(1) operation.
*
* This is an inlined function in compilers that support inlining,
* so it's usually a cheap operation.
*/
static inline bool pmix_list_is_empty(pmix_list_t *list)
{
return (list->pmix_list_sentinel.pmix_list_next == &(list->pmix_list_sentinel) ? true : false);
}
/**
* Return the first item on the list (does not remove it).
*
* @param list The list container
*
* @returns A pointer to the first item on the list
*
* This is an O(1) operation to return the first item on the list. It
* should be compared against the returned value from
* pmix_list_get_end() to ensure that the list is not empty.
*
* This is an inlined function in compilers that support inlining, so
* it's usually a cheap operation.
*/
static inline pmix_list_item_t *pmix_list_get_first(pmix_list_t *list)
{
pmix_list_item_t *item = (pmix_list_item_t *) list->pmix_list_sentinel.pmix_list_next;
#if PMIX_ENABLE_DEBUG
/* Spot check: ensure that the first item is only on one list */
assert(1 == item->pmix_list_item_refcount);
assert(list == item->pmix_list_item_belong_to);
#endif
return item;
}
/**
* Return the last item on the list (does not remove it).
*
* @param list The list container
*
* @returns A pointer to the last item on the list
*
* This is an O(1) operation to return the last item on the list. It
* should be compared against the returned value from
* pmix_list_get_begin() to ensure that the list is not empty.
*
* This is an inlined function in compilers that support inlining, so
* it's usually a cheap operation.
*/
static inline pmix_list_item_t *pmix_list_get_last(pmix_list_t *list)
{
pmix_list_item_t *item = (pmix_list_item_t *) list->pmix_list_sentinel.pmix_list_prev;
#if PMIX_ENABLE_DEBUG
/* Spot check: ensure that the last item is only on one list */
assert(1 == item->pmix_list_item_refcount);
assert(list == item->pmix_list_item_belong_to);
#endif
return item;
}
/**
* Return the beginning of the list; an invalid list entry suitable
* for comparison only.
*
* @param list The list container
*
* @returns A pointer to the beginning of the list.
*
* This is an O(1) operation to return the beginning of the list.
* Similar to the STL, this is a special invalid list item -- it
* should \em not be used for storage. It is only suitable for
* comparison to other items in the list to see if they are valid or
* not; it's usually used when iterating through the items in a list.
*
* This is an inlined function in compilers that support inlining, so
* it's usually a cheap operation.
*/
static inline pmix_list_item_t *pmix_list_get_begin(pmix_list_t *list)
{
return &(list->pmix_list_sentinel);
}
/**
* Return the end of the list; an invalid list entry suitable for
* comparison only.
*
* @param list The list container
*
* @returns A pointer to the end of the list.
*
* This is an O(1) operation to return the end of the list.
* Similar to the STL, this is a special invalid list item -- it
* should \em not be used for storage. It is only suitable for
* comparison to other items in the list to see if they are valid or
* not; it's usually used when iterating through the items in a list.
*
* This is an inlined function in compilers that support inlining, so
* it's usually a cheap operation.
*/
static inline pmix_list_item_t *pmix_list_get_end(pmix_list_t *list)
{
return &(list->pmix_list_sentinel);
}
/**
* Return the number of items in a list
*
* @param list The list container
*
* @returns The size of the list (size_t)
*
* This is an O(1) lookup to return the size of the list.
*
* This is an inlined function in compilers that support inlining, so
* it's usually a cheap operation.
*
* \warning The size of the list is cached as part of the list. In
* the future, calling \c pmix_list_splice or \c pmix_list_join may
* result in this function recomputing the list size, which would be
* an O(N) operation. If \c pmix_list_splice or \c pmix_list_join is
* never called on the specified list, this function will always be
* O(1).
*/
static inline size_t pmix_list_get_size(pmix_list_t *list)
{
#if PMIX_ENABLE_DEBUG && 0
/* not sure if we really want this running in devel, as it does
* slow things down. Wanted for development of splice / join to
* make sure length was reset properly
*/
size_t check_len = 0;
pmix_list_item_t *item;
for (item = pmix_list_get_first(list); item != pmix_list_get_end(list);
item = pmix_list_get_next(item)) {
check_len++;
}
if (check_len != list->pmix_list_length) {
fprintf(
stderr,
" Error :: pmix_list_get_size - pmix_list_length does not match actual list length\n");
fflush(stderr);
abort();
}
#endif
return list->pmix_list_length;
}
/**
* Remove an item from a list.
*
* @param list The list container
* @param item The item to remove
*
* @returns A pointer to the item on the list previous to the one
* that was removed.
*
* This is an O(1) operation to remove an item from the list. The
* forward / reverse pointers in the list are updated and the item is
* removed. The list item that is returned is now "owned" by the
* caller -- they are responsible for PMIX_RELEASE()'ing it.
*
* If debugging is enabled (specifically, if --enable-debug was used
* to configure PMIx), this is an O(N) operation because it checks
* to see if the item is actually in the list first.
*
* This is an inlined function in compilers that support inlining, so
* it's usually a cheap operation.
*/
static inline pmix_list_item_t *pmix_list_remove_item(pmix_list_t *list, pmix_list_item_t *item)
{
#if PMIX_ENABLE_DEBUG
pmix_list_item_t *item_ptr;
bool found = false;
/* check to see that the item is in the list */
for (item_ptr = pmix_list_get_first(list); item_ptr != pmix_list_get_end(list);
item_ptr = (pmix_list_item_t *) (item_ptr->pmix_list_next)) {
if (item_ptr == (pmix_list_item_t *) item) {
found = true;
break;
}
}
if (!found) {
fprintf(stderr, " Warning :: pmix_list_remove_item - the item %p is not on the list %p \n",
(void *) item, (void *) list);
fflush(stderr);
return (pmix_list_item_t *) NULL;
}
assert(list == item->pmix_list_item_belong_to);
#endif
/* reset next pointer of previous element */
item->pmix_list_prev->pmix_list_next = item->pmix_list_next;
/* reset previous pointer of next element */
item->pmix_list_next->pmix_list_prev = item->pmix_list_prev;
list->pmix_list_length--;
#if PMIX_ENABLE_DEBUG
/* Spot check: ensure that this item is still only on one list */
item->pmix_list_item_refcount -= 1;
assert(0 == item->pmix_list_item_refcount);
item->pmix_list_item_belong_to = NULL;
#endif
return (pmix_list_item_t *) item->pmix_list_prev;
}
/**
* Append an item to the end of the list.
*
* @param list The list container
* @param item The item to append
*
* This is an O(1) operation to append an item to the end of a list.
* The pmix_list_item_t is not PMIX_RETAIN()'ed; it is assumed that
* "ownership" of the item is passed from the caller to the list.
*
* This is an inlined function in compilers that support inlining, so
* it's usually a cheap operation.
*/
#if PMIX_ENABLE_DEBUG
# define pmix_list_append(l, i) _pmix_list_append(l, i, __FILE__, __LINE__)
#else
# define pmix_list_append(l, i) _pmix_list_append(l, i)
#endif /* PMIX_ENABLE_DEBUG */
static inline void _pmix_list_append(pmix_list_t *list, pmix_list_item_t *item
#if PMIX_ENABLE_DEBUG
,
const char *FILE_NAME, int LINENO
#endif /* PMIX_ENABLE_DEBUG */
)
{
pmix_list_item_t *sentinel = &(list->pmix_list_sentinel);
#if PMIX_ENABLE_DEBUG
/* Spot check: ensure that this item is previously on no lists */
assert(0 == item->pmix_list_item_refcount);
assert(NULL == item->pmix_list_item_belong_to);
item->super.cls_init_file_name = FILE_NAME;
item->super.cls_init_lineno = LINENO;
#endif
/* set new element's previous pointer */
item->pmix_list_prev = sentinel->pmix_list_prev;
/* reset previous pointer on current last element */
sentinel->pmix_list_prev->pmix_list_next = item;
/* reset new element's next pointer */
item->pmix_list_next = sentinel;
/* reset the list's tail element previous pointer */
sentinel->pmix_list_prev = item;
/* increment list element counter */
list->pmix_list_length++;
#if PMIX_ENABLE_DEBUG
/* Spot check: ensure this item is only on the list that we just
appended it to */
item->pmix_list_item_refcount += 1;
assert(1 == item->pmix_list_item_refcount);
item->pmix_list_item_belong_to = list;
#endif
}
/**
* Prepend an item to the beginning of the list.
*
* @param list The list container
* @param item The item to prepend
*
* This is an O(1) operation to prepend an item to the beginning of a
* list. The pmix_list_item_t is not PMIX_RETAIN()'ed; it is assumed
* that "ownership" of the item is passed from the caller to the list.
*
* This is an inlined function in compilers that support inlining, so
* it's usually a cheap operation.
*/
static inline void pmix_list_prepend(pmix_list_t *list, pmix_list_item_t *item)
{
pmix_list_item_t *sentinel = &(list->pmix_list_sentinel);
#if PMIX_ENABLE_DEBUG
/* Spot check: ensure that this item is previously on no lists */
assert(0 == item->pmix_list_item_refcount);
assert(NULL == item->pmix_list_item_belong_to);
#endif
/* reset item's next pointer */
item->pmix_list_next = sentinel->pmix_list_next;
/* reset item's previous pointer */
item->pmix_list_prev = sentinel;
/* reset previous first element's previous pointer */
sentinel->pmix_list_next->pmix_list_prev = item;
/* reset head's next pointer */
sentinel->pmix_list_next = item;
/* increment list element counter */
list->pmix_list_length++;
#if PMIX_ENABLE_DEBUG
/* Spot check: ensure this item is only on the list that we just
prepended it to */
item->pmix_list_item_refcount += 1;
assert(1 == item->pmix_list_item_refcount);
item->pmix_list_item_belong_to = list;
#endif
}
/**
* Remove the first item from the list and return it.
*
* @param list The list container
*
* @returns The first item on the list. If the list is empty,
* NULL will be returned
*
* This is an O(1) operation to return the first item on the list. If
* the list is not empty, a pointer to the first item in the list will
* be returned. Ownership of the item is transferred from the list to
* the caller; no calls to PMIX_RETAIN() or PMIX_RELEASE() are invoked.
*
* This is an inlined function in compilers that support inlining, so
* it's usually a cheap operation.
*/
static inline pmix_list_item_t *pmix_list_remove_first(pmix_list_t *list)
{
/* Removes and returns first item on list.
Caller now owns the item and should release the item
when caller is done with it.
*/
volatile pmix_list_item_t *item;
if (0 == list->pmix_list_length) {
return (pmix_list_item_t *) NULL;
}
#if PMIX_ENABLE_DEBUG
/* Spot check: ensure that the first item is only on this list */
assert(1 == list->pmix_list_sentinel.pmix_list_next->pmix_list_item_refcount);
#endif
/* reset list length counter */
list->pmix_list_length--;
/* get pointer to first element on the list */
item = (pmix_list_item_t*)list->pmix_list_sentinel.pmix_list_next;
/* reset previous pointer of next item on the list */
item->pmix_list_next->pmix_list_prev = item->pmix_list_prev;
/* reset the head next pointer */
list->pmix_list_sentinel.pmix_list_next = item->pmix_list_next;
#if PMIX_ENABLE_DEBUG
assert(list == item->pmix_list_item_belong_to);
item->pmix_list_item_belong_to = NULL;
item->pmix_list_prev = (pmix_list_item_t *) NULL;
item->pmix_list_next = (pmix_list_item_t *) NULL;
/* Spot check: ensure that the item we're returning is now on no
lists */
item->pmix_list_item_refcount -= 1;
assert(0 == item->pmix_list_item_refcount);
#endif
return (pmix_list_item_t *) item;
}
/**
* Remove the last item from the list and return it.
*
* @param list The list container
*
* @returns The last item on the list. If the list is empty,
* NULL will be returned
*
* This is an O(1) operation to return the last item on the list. If
* the list is not empty, a pointer to the last item in the list will
* be returned. Ownership of the item is transferred from the list to
* the caller; no calls to PMIX_RETAIN() or PMIX_RELEASE() are invoked.
*
* This is an inlined function in compilers that support inlining, so
* it's usually a cheap operation.
*/
static inline pmix_list_item_t *pmix_list_remove_last(pmix_list_t *list)
{
/* Removes, releases and returns last item on list.
Caller now owns the item and should release the item
when caller is done with it.
*/
volatile pmix_list_item_t *item;
if (0 == list->pmix_list_length) {
return (pmix_list_item_t *) NULL;
}
#if PMIX_ENABLE_DEBUG
/* Spot check: ensure that the first item is only on this list */
assert(1 == list->pmix_list_sentinel.pmix_list_prev->pmix_list_item_refcount);
#endif
/* reset list length counter */
list->pmix_list_length--;
/* get item */
item = (pmix_list_item_t*)list->pmix_list_sentinel.pmix_list_prev;
/* reset previous pointer on next to last pointer */
item->pmix_list_prev->pmix_list_next = item->pmix_list_next;
/* reset tail's previous pointer */
list->pmix_list_sentinel.pmix_list_prev = item->pmix_list_prev;
#if PMIX_ENABLE_DEBUG
assert(list == item->pmix_list_item_belong_to);
item->pmix_list_next = item->pmix_list_prev = (pmix_list_item_t *) NULL;
/* Spot check: ensure that the item we're returning is now on no
lists */
item->pmix_list_item_refcount -= 1;
assert(0 == item->pmix_list_item_refcount);
item->pmix_list_item_belong_to = NULL;
#endif
return (pmix_list_item_t *) item;
}
/**
* Add an item to the list before a given element
*
* @param list The list container
* @param pos List element to insert \c item before
* @param item The item to insert
*
* Inserts \c item before \c pos. This is an O(1) operation.
*/
static inline void pmix_list_insert_pos(pmix_list_t *list, pmix_list_item_t *pos,
pmix_list_item_t *item)
{
#if PMIX_ENABLE_DEBUG
/* Spot check: ensure that the item we're insertting is currently
not on any list */
assert(0 == item->pmix_list_item_refcount);
assert(NULL == item->pmix_list_item_belong_to);
#endif
/* point item at the existing elements */
item->pmix_list_next = pos;
item->pmix_list_prev = pos->pmix_list_prev;
/* splice into the list */
pos->pmix_list_prev->pmix_list_next = item;
pos->pmix_list_prev = item;
/* reset list length counter */
list->pmix_list_length++;
#if PMIX_ENABLE_DEBUG
/* Spot check: double check that this item is only on the list
that we just added it to */
item->pmix_list_item_refcount += 1;
assert(1 == item->pmix_list_item_refcount);
item->pmix_list_item_belong_to = list;
#endif
}
/**
* Add an item to the list at a specific index location in the list.
*
* @param list The list container
* @param item The item to insert
* @param index Location to add the item
*
* @returns true if insertion succeeded; otherwise false
*
* This is potentially an O(N) operation to traverse down to the
* correct location in the list and add an item.
*
* Example: if idx = 2 and list = item1->item2->item3->item4, then
* after insert, list = item1->item2->item->item3->item4.
*
* If index is greater than the length of the list, no action is
* performed and false is returned.
*/
PMIX_EXPORT bool pmix_list_insert(pmix_list_t *list,
pmix_list_item_t *item,
long long idx);
/**
* Join a list into another list
*
* @param thislist List container for list being operated on
* @param pos List item in \c thislist marking the position before
* which items are inserted
* @param xlist List container for list being spliced from
*
* Join a list into another list. All of the elements of \c xlist
* are inserted before \c pos and removed from \c xlist.
*
* This operation is an O(1) operation. Both \c thislist and \c
* xlist must be valid list containsers. \c xlist will be empty
* but valid after the call. All pointers to \c pmix_list_item_t
* containers remain valid, including those that point to elements
* in \c xlist.
*/
PMIX_EXPORT void pmix_list_join(pmix_list_t *thislist,
pmix_list_item_t *pos,
pmix_list_t *xlist);
/**
* Splice a list into another list
*
* @param thislist List container for list being operated on
* @param pos List item in \c thislist marking the position before
* which items are inserted
* @param xlist List container for list being spliced from
* @param first List item in \c xlist marking the start of elements
* to be copied into \c thislist
* @param last List item in \c xlist marking the end of elements
* to be copied into \c thislist
*
* Splice a subset of a list into another list. The \c [first,
* last) elements of \c xlist are moved into \c thislist,
* inserting them before \c pos. \c pos must be a valid iterator
* in \c thislist and \c [first, last) must be a valid range in \c
* xlist. \c position must not be in the range \c [first, last).
* It is, however, valid for \c xlist and \c thislist to be the
* same list.
*
* This is an O(N) operation because the length of both lists must
* be recomputed.
*/
PMIX_EXPORT void pmix_list_splice(pmix_list_t *thislist,
pmix_list_item_t *pos,
pmix_list_t *xlist,
pmix_list_item_t *first,
pmix_list_item_t *last);
/**
* Comparison function for pmix_list_sort(), below.
*
* @param a Pointer to a pointer to an pmix_list_item_t.
* Explanation below.
* @param b Pointer to a pointer to an pmix_list_item_t.
* Explanation below.
* @retval 1 if \em a is greater than \em b
* @retval 0 if \em a is equal to \em b
* @retval 11 if \em a is less than \em b
*
* This function is invoked by qsort(3) from within
* pmix_list_sort(). It is important to understand what
* pmix_list_sort() does before invoking qsort, so go read that
* documentation first.
*
* The important thing to realize here is that a and b will be \em
* double pointers to the items that you need to compare. Here's
* a sample compare function to illustrate this point:
*/
typedef int (*pmix_list_item_compare_fn_t)(pmix_list_item_t **a,
pmix_list_item_t **b);
/**
* Sort a list with a provided compare function.
*
* @param list The list to sort
* @param compare Compare function
*
* Put crassly, this function's complexity is O(N) + O(log(N)).
* Its algorithm is:
*
* - remove every item from the list and put the corresponding
* (pmix_list_item_t*)'s in an array
* - call qsort(3) with that array and your compare function
* - re-add every element of the now-sorted array to the list
*
* The resulting list is now ordered. Note, however, that since
* an array of pointers is sorted, the comparison function must do
* a double de-reference to get to the actual pmix_list_item_t (or
* whatever the underlying type is). See the documentation of
* pmix_list_item_compare_fn_t for an example).
*/
PMIX_EXPORT int pmix_list_sort(pmix_list_t *list,
pmix_list_item_compare_fn_t compare);
END_C_DECLS
#endif /* PMIX_LIST_H */

View File

@@ -0,0 +1,786 @@
/* -*- Mode: C; c-basic-offset:4 ; -*- */
/*
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2007 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2006 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2007 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2013-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2016 Research Organization for Information Science
* and Technology (RIST). All rights reserved.
* Copyright (c) 2021-2022 Nanook Consulting All rights reserved.
* Copyright (c) 2021-2023 Triad National Security, LLC. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
/**
* @file:
*
* A simple C-language object-oriented system with single inheritance
* and ownership-based memory management using a retain/release model.
*
* A class consists of a struct and singly-instantiated class
* descriptor. The first element of the struct must be the parent
* class's struct. The class descriptor must be given a well-known
* name based upon the class struct name (if the struct is sally_t,
* the class descriptor should be sally_t_class) and must be
* statically initialized as discussed below.
*
* (a) To define a class
*
* In a interface (.h) file, define the class. The first element
* should always be the parent class, for example
* @code
* struct sally_t
* {
* parent_t parent;
* void *first_member;
* ...
* };
* typedef struct sally_t sally_t;
*
* PMIX_CLASS_DECLARATION(sally_t);
* @endcode
* All classes must have a parent which is also class.
*
* In an implementation (.c) file, instantiate a class descriptor for
* the class like this:
* @code
* PMIX_CLASS_INSTANCE(sally_t, parent_t, sally_construct, sally_destruct);
* @endcode
* This macro actually expands to
* @code
* pmix_class_t sally_t_class = {
* "sally_t",
* PMIX_CLASS(parent_t), // pointer to parent_t_class
* sally_construct,
* sally_destruct,
* 0, 0, NULL, NULL,
* sizeof ("sally_t")
* };
* @endcode
* This variable should be declared in the interface (.h) file using
* the PMIX_CLASS_DECLARATION macro as shown above.
*
* sally_construct, and sally_destruct are function pointers to the
* constructor and destructor for the class and are best defined as
* static functions in the implementation file. NULL pointers maybe
* supplied instead.
*
* Other class methods may be added to the struct.
*
* (b) Class instantiation: dynamic
*
* To create a instance of a class (an object) use PMIX_NEW:
* @code
* sally_t *sally = PMIX_NEW(sally_t);
* @endcode
* which allocates memory of sizeof(sally_t) and runs the class's
* constructors.
*
* Use PMIX_RETAIN, PMIX_RELEASE to do reference-count-based
* memory management:
* @code
* PMIX_RETAIN(sally);
* PMIX_RELEASE(sally);
* PMIX_RELEASE(sally);
* @endcode
* When the reference count reaches zero, the class's destructor, and
* those of its parents, are run and the memory is freed.
*
* N.B. There is no explicit free/delete method for dynamic objects in
* this model.
*
* (c) Class instantiation: static
*
* For an object with static (or stack) allocation, it is only
* necessary to initialize the memory, which is done using
* PMIX_CONSTRUCT:
* @code
* sally_t sally;
*
* PMIX_CONSTRUCT(&sally, sally_t);
* @endcode
* The retain/release model is not necessary here, but before the
* object goes out of scope, PMIX_DESTRUCT should be run to release
* initialized resources:
* @code
* PMIX_DESTRUCT(&sally);
* @endcode
*/
#ifndef PMIX_OBJECT_H
#define PMIX_OBJECT_H
#include "src/include/pmix_config.h"
#include "pmix_common.h"
#include <assert.h>
#ifdef HAVE_STDLIB_H
# include <stdlib.h>
#endif /* HAVE_STDLIB_H */
#include <pthread.h>
#include <stdio.h>
#include <errno.h>
BEGIN_C_DECLS
#if PMIX_ENABLE_DEBUG
/* Any kind of unique ID should do the job */
# define PMIX_OBJ_MAGIC_ID ((0xdeafbeedULL << 32) + 0xdeafbeedULL)
#endif
/*
* Macros for variadic object instantiation: w/wout custom memory allocator.
*
* NOTE(skg) There is probably a nicer way to implement this functionality. In
* particular, with further macro magic we can probably unify a lot of the
* common code here, but that is for another day.
*/
/**
* Takes in at least three arguments, eats all of them except the third.
* This allows us to do things like:
* PMIX_NEW_HAS_ARITY_HELPER(sally_t, TMA, NO_TMA, ERROR) --> NO_TMA
* PMIX_NEW_HAS_ARITY_HELPER(sally_t, a_tma, TMA, NO_TMA, ERROR) --> TMA
*/
#define PMIX_NEW_HAS_ARITY_HELPER(_1, _2, N, ...) N
#define PMIX_NEW_HAS_ARITY_IMPL(...) \
PMIX_NEW_HAS_ARITY_HELPER(__VA_ARGS__)
/*
* PMIX_CONSTRUCT() takes a maximum of three arguments:
* Two arguments means caller does not want a custom memory allocator.
* Three arguments means caller wants a custom (TMA) memory allocator.
*
* Please see PMIX_NEW_HAS_ARITY_HELPER's description above for more details
* about how this macro functions.
*/
#define PMIX_CONSTRUCT_HAS_ARITY_HELPER(_1, _2, _3, N, ...) N
#define PMIX_CONSTRUCT_HAS_ARITY_IMPL(...) \
PMIX_CONSTRUCT_HAS_ARITY_HELPER(__VA_ARGS__)
/*
* Macro suffix naming convention must be _TMA or _NO_TMA.
*
* These are the displacement mode lists used in the PMIX_NEW_HAS_ARITY_HELPER
* example above.
*/
#define PMIX_NEW_HAS_ARGS_SOURCE() TMA, NO_TMA, ERROR
#define PMIX_CONSTRUCT_HAS_ARGS_SOURCE() TMA, NO_TMA, ERROR, ERROR
#define PMIX_OBJ_HAS_ARGS(...) \
PMIX_NEW_HAS_ARITY_IMPL(__VA_ARGS__, PMIX_NEW_HAS_ARGS_SOURCE())
#define PMIX_CONSTRUCT_HAS_ARGS(...) \
PMIX_CONSTRUCT_HAS_ARITY_IMPL(__VA_ARGS__, PMIX_CONSTRUCT_HAS_ARGS_SOURCE())
/*
* These are used to generate the proper macro name and forward the relevant
* arguments depending on the number of arguments used.
*/
#define PMIX_NEW_DISAMBIGUATE2(has_args, ...) \
PMIX_NEW_ ## has_args (__VA_ARGS__)
#define PMIX_NEW_DISAMBIGUATE(has_args, ...) \
PMIX_NEW_DISAMBIGUATE2(has_args, __VA_ARGS__)
#define PMIX_CONSTRUCT_DISAMBIGUATE2(has_args, ...) \
PMIX_CONSTRUCT_ ## has_args (__VA_ARGS__)
#define PMIX_CONSTRUCT_DISAMBIGUATE(has_args, ...) \
PMIX_CONSTRUCT_DISAMBIGUATE2(has_args, __VA_ARGS__)
/* typedefs ***********************************************************/
typedef struct pmix_object_t pmix_object_t;
typedef struct pmix_class_t pmix_class_t;
typedef void (*pmix_construct_t)(pmix_object_t *);
typedef void (*pmix_destruct_t)(pmix_object_t *);
/* types **************************************************************/
/** Memory allocator for objects */
typedef struct pmix_tma {
/** Pointer to the TMA's malloc() function. */
void *(*tma_malloc)(struct pmix_tma *, size_t);
/** Pointer to the TMA's calloc() function. */
void *(*tma_calloc)(struct pmix_tma *, size_t, size_t);
/** Pointer to the TMA's realloc() function. */
void *(*tma_realloc)(struct pmix_tma *, void *, size_t);
/*
* NOTE: The seemingly unnecessary name mangling here is in response to
* certain compilers not liking the use of a function pointer named strdup.
*/
/** Pointer to the TMA's strdup() function. */
char *(*tma_strdup)(struct pmix_tma *, const char *s);
/**
* A memmove()-like function that copies the provided contents to an
* appropriate location in the memory area maintained by the allocator.
* Like memmove(), it returns a pointer to the content's destination.
*/
void *(*tma_memmove)(struct pmix_tma *tma, const void *src, size_t n);
/** Pointer to the TMA's free() function. */
void (*tma_free)(struct pmix_tma *, void *);
/** Points to a user-defined TMA context. */
void *data_context;
/**
* Points to generic data used by a TMA. An example includes a pointer to a
* value that maintains the next available address.
*/
void **data_ptr;
} pmix_tma_t;
static inline void *pmix_tma_malloc(pmix_tma_t *tma, size_t size)
{
if (NULL != tma) {
return tma->tma_malloc(tma, size);
} else {
return malloc(size);
}
}
static inline void *pmix_tma_calloc(pmix_tma_t *tma, size_t nmemb, size_t size)
{
if (NULL != tma) {
return tma->tma_calloc(tma, nmemb, size);
} else {
return calloc(nmemb, size);
}
}
static inline void *pmix_tma_realloc(pmix_tma_t *tma, void *ptr, size_t size)
{
if (NULL != tma) {
return tma->tma_realloc(tma, ptr, size);
} else {
return realloc(ptr, size);
}
}
static inline char *pmix_tma_strdup(pmix_tma_t *tma, const char *src)
{
if (NULL != tma) {
return tma->tma_strdup(tma, src);
} else {
return strdup(src);
}
}
static inline void pmix_tma_free(pmix_tma_t *tma, void *ptr)
{
if (NULL != tma) {
tma->tma_free(tma, ptr);
} else {
free(ptr);
}
}
/**
* Class descriptor.
*
* There should be a single instance of this descriptor for each class
* definition.
*/
struct pmix_class_t {
const char *cls_name; /**< symbolic name for class */
pmix_class_t *cls_parent; /**< parent class descriptor */
pmix_construct_t cls_construct; /**< class constructor */
pmix_destruct_t cls_destruct; /**< class destructor */
int cls_initialized; /**< is class initialized */
int cls_depth; /**< depth of class hierarchy tree */
pmix_construct_t *cls_construct_array;
/**< array of parent class constructors */
pmix_destruct_t *cls_destruct_array;
/**< array of parent class destructors */
size_t cls_sizeof; /**< size of an object instance */
};
PMIX_EXPORT extern int pmix_class_init_epoch;
/**
* For static initializations of OBJects.
*
* @param NAME Name of the class to initialize
*/
#if PMIX_ENABLE_DEBUG
# define PMIX_OBJ_STATIC_INIT(BASE_CLASS) \
{ \
.obj_magic_id = PMIX_OBJ_MAGIC_ID, \
.obj_class = PMIX_CLASS(BASE_CLASS), \
.obj_lock = PTHREAD_MUTEX_INITIALIZER, \
.obj_reference_count = 1, \
.obj_tma = { \
.tma_malloc = NULL, \
.tma_calloc = NULL, \
.tma_realloc = NULL, \
.tma_strdup = NULL, \
.tma_memmove = NULL, \
.tma_free = NULL, \
.data_context = NULL, \
.data_ptr = NULL \
}, \
.cls_init_file_name = __FILE__, \
.cls_init_lineno = __LINE__ \
}
#else
# define PMIX_OBJ_STATIC_INIT(BASE_CLASS) \
{ \
.obj_class = PMIX_CLASS(BASE_CLASS), \
.obj_lock = PTHREAD_MUTEX_INITIALIZER, \
.obj_reference_count = 1, \
.obj_tma = { \
.tma_malloc = NULL, \
.tma_calloc = NULL, \
.tma_realloc = NULL, \
.tma_strdup = NULL, \
.tma_memmove = NULL, \
.tma_free = NULL, \
.data_context = NULL, \
.data_ptr = NULL \
} \
}
#endif
/**
* Base object.
*
* This is special and does not follow the pattern for other classes.
*/
struct pmix_object_t {
#if PMIX_ENABLE_DEBUG
/** Magic ID -- want this to be the very first item in the
struct's memory */
uint64_t obj_magic_id;
#endif
pthread_mutex_t obj_lock;
pmix_class_t *obj_class; /**< class descriptor */
int32_t obj_reference_count; /**< reference count */
pmix_tma_t obj_tma; /**< allocator for this object */
#if PMIX_ENABLE_DEBUG
const char *cls_init_file_name; /**< In debug mode store the file where the object get constructed */
int cls_init_lineno; /**< In debug mode store the line number where the object get constructed */
#endif /* PMIX_ENABLE_DEBUG */
};
/* macros ************************************************************/
/**
* Return a pointer to the class descriptor associated with a
* class type.
*
* @param NAME Name of class
* @return Pointer to class descriptor
*/
#define PMIX_CLASS(NAME) (&(NAME##_class))
/**
* Static initializer for a class descriptor
*
* @param NAME Name of class
* @param PARENT Name of parent class
* @param CONSTRUCTOR Pointer to constructor
* @param DESTRUCTOR Pointer to destructor
*
* Put this in NAME.c
*/
#define PMIX_CLASS_INSTANCE(NAME, PARENT, CONSTRUCTOR, DESTRUCTOR) \
pmix_class_t NAME##_class = {#NAME, \
PMIX_CLASS(PARENT), \
(pmix_construct_t) CONSTRUCTOR, \
(pmix_destruct_t) DESTRUCTOR, \
0, \
0, \
NULL, \
NULL, \
sizeof(NAME)}
/**
* Declaration for class descriptor
*
* @param NAME Name of class
*
* Put this in NAME.h
*/
#define PMIX_CLASS_DECLARATION(NAME) extern pmix_class_t NAME##_class
/**
* Create an object: dynamically allocate storage and run the class
* constructor.
*
* @param type Type (class) of the object
* @return Pointer to the object
*/
static inline pmix_object_t *pmix_obj_new_tma(pmix_class_t *cls, pmix_tma_t *tma);
#if PMIX_ENABLE_DEBUG
static inline pmix_object_t *pmix_obj_new_debug_tma(pmix_class_t *type, pmix_tma_t *tma,
const char *file, int line)
{
pmix_object_t *object = pmix_obj_new_tma(type, tma);
if (NULL != object) {
object->obj_magic_id = PMIX_OBJ_MAGIC_ID;
object->cls_init_file_name = file;
object->cls_init_lineno = line;
}
return object;
}
#define PMIX_NEW_NO_TMA(type) \
((type *)pmix_obj_new_debug_tma(PMIX_CLASS(type), NULL, __FILE__, __LINE__))
#define PMIX_NEW_TMA(type, tma) \
((type *)pmix_obj_new_debug_tma(PMIX_CLASS(type), (tma), __FILE__, __LINE__))
#else
#define PMIX_NEW_NO_TMA(type) ((type *)pmix_obj_new_tma(PMIX_CLASS(type), NULL))
#define PMIX_NEW_TMA(type, tma) ((type *)pmix_obj_new_tma(PMIX_CLASS(type), (tma)))
#endif /* PMIX_ENABLE_DEBUG */
/**
* PMIX_NEW() takes a maximum of two arguments:
* One argument means caller does not want a custom memory allocator, namely the
* common case.
* Two arguments means caller wants a custom (TMA) memory allocator.
*/
#define PMIX_NEW(...) \
PMIX_NEW_DISAMBIGUATE(PMIX_OBJ_HAS_ARGS(__VA_ARGS__), __VA_ARGS__)
/**
* Retain an object (by incrementing its reference count)
*
* @param object Pointer to the object
*/
#if PMIX_ENABLE_DEBUG
# define PMIX_RETAIN(object) \
do { \
assert(NULL != ((pmix_object_t *) (object))->obj_class); \
assert(PMIX_OBJ_MAGIC_ID == ((pmix_object_t *) (object))->obj_magic_id); \
pmix_obj_update((pmix_object_t *) (object), 1); \
assert(((pmix_object_t *) (object))->obj_reference_count >= 0); \
} while (0)
#else
# define PMIX_RETAIN(object) pmix_obj_update((pmix_object_t *) (object), 1)
#endif
/**
* Helper macro for the debug mode to store the locations where the status of
* an object change.
*/
#if PMIX_ENABLE_DEBUG
# define PMIX_REMEMBER_FILE_AND_LINENO(OBJECT, FILE, LINENO) \
do { \
((pmix_object_t *) (OBJECT))->cls_init_file_name = FILE; \
((pmix_object_t *) (OBJECT))->cls_init_lineno = LINENO; \
} while (0)
# define PMIX_SET_MAGIC_ID(OBJECT, VALUE) \
do { \
((pmix_object_t *) (OBJECT))->obj_magic_id = (VALUE); \
} while (0)
#else
# define PMIX_REMEMBER_FILE_AND_LINENO(OBJECT, FILE, LINENO)
# define PMIX_SET_MAGIC_ID(OBJECT, VALUE)
#endif /* PMIX_ENABLE_DEBUG */
/**
* Release an object (by decrementing its reference count). If the
* reference count reaches zero, destruct (finalize) the object and
* free its storage.
*
* Note: If the object is freed, then the value of the pointer is set
* to NULL.
*
* @param object Pointer to the object
*/
#if PMIX_ENABLE_DEBUG
# define PMIX_RELEASE(object) \
do { \
pmix_object_t *_obj = (pmix_object_t *) object; \
assert(NULL != _obj->obj_class); \
assert(PMIX_OBJ_MAGIC_ID == _obj->obj_magic_id); \
if (0 == pmix_obj_update(_obj, -1)) { \
PMIX_SET_MAGIC_ID((object), 0); \
pmix_obj_run_destructors(_obj); \
PMIX_REMEMBER_FILE_AND_LINENO(object, __FILE__, __LINE__); \
if (NULL != _obj->obj_tma.tma_free) { \
pmix_tma_free(&_obj->obj_tma, object); \
} \
else { \
free(object); \
} \
object = NULL; \
} \
} while (0)
#else
# define PMIX_RELEASE(object) \
do { \
pmix_object_t *_obj = (pmix_object_t *) object; \
if (0 == pmix_obj_update(_obj, -1)) { \
pmix_obj_run_destructors(_obj); \
if (NULL != _obj->obj_tma.tma_free) { \
pmix_tma_free(&_obj->obj_tma, object); \
} \
else { \
free(object); \
} \
object = NULL; \
} \
} while (0)
#endif
/**
* Construct (initialize) objects that are not dynamically allocated.
*
* @param object Pointer to the object
* @param type The object type
*/
static inline void pmix_obj_construct_tma(pmix_object_t *obj, pmix_tma_t *tma)
{
if (NULL == tma) {
obj->obj_tma.tma_malloc = NULL;
obj->obj_tma.tma_calloc = NULL;
obj->obj_tma.tma_realloc = NULL;
obj->obj_tma.tma_strdup = NULL;
obj->obj_tma.tma_memmove = NULL;
obj->obj_tma.tma_free = NULL;
obj->obj_tma.data_context = NULL;
obj->obj_tma.data_ptr = NULL;
} else {
obj->obj_tma = *tma;
}
}
#define PMIX_CONSTRUCT_INTERNAL_TMA(object, type, t) \
do { \
PMIX_SET_MAGIC_ID((object), PMIX_OBJ_MAGIC_ID); \
if (pmix_class_init_epoch != (type)->cls_initialized) { \
pmix_class_initialize((type)); \
} \
((pmix_object_t *) (object))->obj_class = (type); \
((pmix_object_t *) (object))->obj_reference_count = 1; \
pmix_obj_construct_tma(((pmix_object_t *) (object)), (t)); \
pmix_obj_run_constructors((pmix_object_t *) (object)); \
PMIX_REMEMBER_FILE_AND_LINENO(object, __FILE__, __LINE__); \
} while (0)
#define PMIX_CONSTRUCT_TMA(object, type, t) \
do { \
PMIX_CONSTRUCT_INTERNAL_TMA((object), PMIX_CLASS(type), (t)); \
} while (0)
#define PMIX_CONSTRUCT_NO_TMA(object, type) \
do { \
PMIX_CONSTRUCT_TMA(object, type, NULL); \
} while (0)
#define PMIX_CONSTRUCT(...) \
PMIX_CONSTRUCT_DISAMBIGUATE(PMIX_CONSTRUCT_HAS_ARGS(__VA_ARGS__), __VA_ARGS__)
/**
* Destruct (finalize) an object that is not dynamically allocated.
*
* @param object Pointer to the object
*/
#if PMIX_ENABLE_DEBUG
# define PMIX_DESTRUCT(object) \
do { \
assert(PMIX_OBJ_MAGIC_ID == ((pmix_object_t *) (object))->obj_magic_id); \
PMIX_SET_MAGIC_ID((object), 0); \
pmix_obj_run_destructors((pmix_object_t *) (object)); \
PMIX_REMEMBER_FILE_AND_LINENO(object, __FILE__, __LINE__); \
} while (0)
#else
# define PMIX_DESTRUCT(object) \
do { \
pmix_obj_run_destructors((pmix_object_t *) (object)); \
PMIX_REMEMBER_FILE_AND_LINENO(object, __FILE__, __LINE__); \
} while (0)
#endif
PMIX_CLASS_DECLARATION(pmix_object_t);
/* declarations *******************************************************/
/**
* Lazy initialization of class descriptor.
*
* Specifically cache arrays of function pointers for the constructor
* and destructor hierarchies for this class.
*
* @param class Pointer to class descriptor
*/
PMIX_EXPORT void pmix_class_initialize(pmix_class_t *cls);
/**
* Shut down the class system and release all memory
*
* This function should be invoked as the ABSOLUTE LAST function to
* use the class subsystem. It frees all associated memory with ALL
* classes, rendering all of them inoperable. It is here so that
* tools like valgrind and purify don't report still-reachable memory
* upon process termination.
*/
PMIX_EXPORT int pmix_class_finalize(void);
/**
* Run the hierarchy of class constructors for this object, in a
* parent-first order.
*
* Do not use this function directly: use PMIX_CONSTRUCT() instead.
*
* WARNING: This implementation relies on a hardwired maximum depth of
* the inheritance tree!!!
*
* Hardwired for fairly shallow inheritance trees
* @param size Pointer to the object.
*/
static inline void pmix_obj_run_constructors(pmix_object_t *object)
{
pmix_construct_t *cls_construct;
assert(NULL != object->obj_class);
cls_construct = object->obj_class->cls_construct_array;
while (NULL != *cls_construct) {
(*cls_construct)(object);
cls_construct++;
}
}
/**
* Run the hierarchy of class destructors for this object, in a
* parent-last order.
*
* Do not use this function directly: use PMIX_DESTRUCT() instead.
*
* @param size Pointer to the object.
*/
static inline void pmix_obj_run_destructors(pmix_object_t *object)
{
pmix_destruct_t *cls_destruct;
assert(NULL != object->obj_class);
cls_destruct = object->obj_class->cls_destruct_array;
while (NULL != *cls_destruct) {
(*cls_destruct)(object);
cls_destruct++;
}
}
/**
* Create new object: dynamically allocate storage and run the class
* constructor.
*
* Do not use this function directly: use PMIX_NEW() instead.
*
* @param size Size of the object
* @param cls Pointer to the class descriptor of this object
* @return Pointer to the object
*/
static inline pmix_object_t *pmix_obj_new_tma(pmix_class_t *cls, pmix_tma_t *tma)
{
pmix_object_t *object;
assert(cls->cls_sizeof >= sizeof(pmix_object_t));
object = (pmix_object_t *) pmix_tma_malloc(tma, cls->cls_sizeof);
if (pmix_class_init_epoch != cls->cls_initialized) {
pmix_class_initialize(cls);
}
if (NULL != object) {
#if PMIX_ENABLE_DEBUG
pthread_mutexattr_t attr;
pthread_mutexattr_init(&attr);
/* set type to ERRORCHECK so that we catch recursive locks */
# if PMIX_HAVE_PTHREAD_MUTEX_ERRORCHECK_NP
pthread_mutexattr_settype(&attr, PTHREAD_MUTEX_ERRORCHECK_NP);
# elif PMIX_HAVE_PTHREAD_MUTEX_ERRORCHECK
pthread_mutexattr_settype(&attr, PTHREAD_MUTEX_ERRORCHECK);
# endif /* PMIX_HAVE_PTHREAD_MUTEX_ERRORCHECK_NP */
pthread_mutex_init(&object->obj_lock, &attr);
pthread_mutexattr_destroy(&attr);
#else
/* Without debugging, choose the fastest available mutexes */
pthread_mutex_init(&object->obj_lock, NULL);
#endif /* PMIX_ENABLE_DEBUG */
object->obj_class = cls;
object->obj_reference_count = 1;
if (NULL == tma) {
object->obj_tma.tma_malloc = NULL;
object->obj_tma.tma_calloc = NULL;
object->obj_tma.tma_realloc = NULL;
object->obj_tma.tma_strdup = NULL;
object->obj_tma.tma_free = NULL;
object->obj_tma.data_context = NULL;
object->obj_tma.data_ptr = NULL;
} else {
object->obj_tma = *tma;
}
pmix_obj_run_constructors(object);
}
return object;
}
/**
* Atomically update the object's reference count by some increment.
*
* This function should not be used directly: it is called via the
* macros PMIX_RETAIN and PMIX_RELEASE
*
* @param object Pointer to the object
* @param inc Increment by which to update reference count
* @return New value of the reference count
*/
static inline int pmix_obj_update(pmix_object_t *object, int inc) __pmix_attribute_always_inline__;
static inline int pmix_obj_update(pmix_object_t *object, int inc)
{
int ret = pthread_mutex_lock(&object->obj_lock);
if (ret == EDEADLK) {
errno = ret;
perror("pthread_mutex_lock()");
abort();
}
ret = (object->obj_reference_count += inc);
pthread_mutex_unlock(&object->obj_lock);
return ret;
}
/**
* Get a pointer to a given object's memory allocator. Returns a pointer to the
* TMA, if available. Returns NULL Otherwise.
*/
static inline pmix_tma_t *
pmix_obj_get_tma(
pmix_object_t *obj
) {
// Look for a given function pointer. If it isn't NULL, then assume that
// this object has a custom memory allocator.
if (obj->obj_tma.tma_malloc) {
return &obj->obj_tma;
}
return NULL;
}
END_C_DECLS
#endif

View File

@@ -0,0 +1,215 @@
/* -*- Mode: C; c-basic-offset:4 ; -*- */
/*
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2017 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2017 Intel, Inc. All rights reserved.
* Copyright (c) 2021-2022 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
/** @file
*
* Utility functions to manage fortran <-> c opaque object
* translation. Note that since MPI defines fortran handles as
* [signed] int's, we use int everywhere in here where you would
* normally expect size_t. There's some code that makes sure indices
* don't go above FORTRAN_HANDLE_MAX (which is min(INT_MAX, fortran
* INTEGER max)), just to be sure.
*/
#ifndef PMIX_POINTER_ARRAY_H
#define PMIX_POINTER_ARRAY_H
#include "src/include/pmix_config.h"
#include "src/class/pmix_object.h"
#include "src/include/pmix_prefetch.h"
BEGIN_C_DECLS
/**
* dynamic pointer array
*/
struct pmix_pointer_array_t {
/** base class */
pmix_object_t super;
/** Index of lowest free element. NOTE: This is only an
optimization to know where to search for the first free slot.
It does \em not necessarily imply indices all above this index
are not taken! */
int lowest_free;
/** number of free elements in the list */
int number_free;
/** size of list, i.e. number of elements in addr */
int size;
/** maximum size of the array */
int max_size;
/** block size for each allocation */
int block_size;
/** pointer to an array of bits to speed up the research for an empty position. */
uint64_t *free_bits;
/** pointer to array of pointers */
void **addr;
};
#define PMIX_POINTER_ARRAY_STATIC_INIT \
{ \
.super = PMIX_OBJ_STATIC_INIT(pmix_object_t), \
.lowest_free = 0, \
.number_free = 0, \
.size = 0, \
.max_size = 0, \
.block_size = 0, \
.free_bits = NULL, \
.addr = NULL \
}
/**
* Convenience typedef
*/
typedef struct pmix_pointer_array_t pmix_pointer_array_t;
/**
* Class declaration
*/
PMIX_EXPORT PMIX_CLASS_DECLARATION(pmix_pointer_array_t);
/**
* Initialize the pointer array with an initial size of initial_allocation.
* Set the maximum size of the array, as well as the size of the allocation
* block for all subsequent growing operations. Remarque: The pointer array
* has to be created bfore calling this function.
*
* @param array Pointer to pointer of an array (IN/OUT)
* @param initial_allocation The number of elements in the initial array (IN)
* @param max_size The maximum size of the array (IN)
* @param block_size The size for all subsequent grows of the array (IN).
*
* @return PMIX_SUCCESS if all initializations were successful. Otherwise,
* the error indicate what went wrong in the function.
*/
PMIX_EXPORT int pmix_pointer_array_init(pmix_pointer_array_t *array, int initial_allocation,
int max_size, int block_size);
/**
* Add a pointer to the array (Grow the array, if need be)
*
* @param array Pointer to array (IN)
* @param ptr Pointer value (IN)
*
* @return Index of inserted array element. Return value of
* (-1) indicates an error.
*/
PMIX_EXPORT int pmix_pointer_array_add(pmix_pointer_array_t *array, void *ptr);
/**
* Set the value of an element in array
*
* @param array Pointer to array (IN)
* @param index Index of element to be reset (IN)
* @param value New value to be set at element index (IN)
*
* @return Error code. (-1) indicates an error.
*/
PMIX_EXPORT int pmix_pointer_array_set_item(pmix_pointer_array_t *array, int index, void *value);
/**
* Get the value of an element in array
*
* @param array Pointer to array (IN)
* @param element_index Index of element to be returned (IN)
*
* @return Error code. NULL indicates an error.
*/
static inline void *pmix_pointer_array_get_item(pmix_pointer_array_t *table, int element_index)
{
void *p;
if (PMIX_UNLIKELY(0 > element_index || table->size <= element_index)) {
return NULL;
}
p = table->addr[element_index];
return p;
}
/**
* Get the size of the pointer array
*
* @param array Pointer to array (IN)
*
* @returns size Size of the array
*
* Simple inline function to return the size of the array in order to
* hide the member field from external users.
*/
static inline int pmix_pointer_array_get_size(pmix_pointer_array_t *array)
{
return array->size;
}
/**
* Set the size of the pointer array
*
* @param array Pointer to array (IN)
*
* @param size Desired size of the array
*
* Simple function to set the size of the array in order to
* hide the member field from external users.
*/
PMIX_EXPORT int pmix_pointer_array_set_size(pmix_pointer_array_t *array, int size);
/**
* Test whether a certain element is already in use. If not yet
* in use, reserve it.
*
* @param array Pointer to array (IN)
* @param index Index of element to be tested (IN)
* @param value New value to be set at element index (IN)
*
* @return true/false True if element could be reserved
* False if element could not be reserved (e.g., in use).
*
* In contrary to array_set, this function does not allow to overwrite
* a value, unless the previous value is NULL ( equiv. to free ).
*/
PMIX_EXPORT bool pmix_pointer_array_test_and_set_item(pmix_pointer_array_t *table, int index,
void *value);
/**
* Empty the array.
*
* @param array Pointer to array (IN)
*
*/
static inline void pmix_pointer_array_remove_all(pmix_pointer_array_t *array)
{
int i;
if (array->number_free == array->size)
return; /* nothing to do here this time (the array is already empty) */
array->lowest_free = 0;
array->number_free = array->size;
for (i = 0; i < array->size; i++) {
array->addr[i] = NULL;
}
for (i = 0; i < (int) ((array->size + 8 * sizeof(uint64_t) - 1) / (8 * sizeof(uint64_t)));
i++) {
array->free_bits[i] = 0;
}
}
END_C_DECLS
#endif /* PMIX_POINTER_ARRAY_H */

View File

@@ -0,0 +1,102 @@
/* -*- Mode: C; c-basic-offset:4 ; -*- */
/*
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2008 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2010 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2016-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2021-2022 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
/** @file
*
*/
#ifndef PMIX_RING_BUFFER_H
#define PMIX_RING_BUFFER_H
#include "src/include/pmix_config.h"
#include "src/class/pmix_object.h"
#include "src/util/pmix_output.h"
BEGIN_C_DECLS
/**
* dynamic pointer ring
*/
struct pmix_ring_buffer_t {
/** base class */
pmix_object_t super;
/* head/tail indices */
int head;
int tail;
/** size of list, i.e. number of elements in addr */
int size;
/** pointer to ring */
char **addr;
};
/**
* Convenience typedef
*/
typedef struct pmix_ring_buffer_t pmix_ring_buffer_t;
/**
* Class declaration
*/
PMIX_CLASS_DECLARATION(pmix_ring_buffer_t);
/**
* Initialize the ring buffer, defining its size.
*
* @param ring Pointer to a ring buffer (IN/OUT)
* @param size The number of elements in the ring (IN)
*
* @return PMIX_SUCCESS if all initializations were successful. Otherwise,
* the error indicate what went wrong in the function.
*/
PMIX_EXPORT int pmix_ring_buffer_init(pmix_ring_buffer_t *ring, int size);
/**
* Push an item onto the ring buffer, displacing the oldest
* item on the ring if the ring is full
*
* @param ring Pointer to ring (IN)
* @param ptr Pointer value (IN)
*
* @return Pointer to displaced item, NULL if ring
* is not yet full
*/
PMIX_EXPORT void *pmix_ring_buffer_push(pmix_ring_buffer_t *ring, void *ptr);
/**
* Pop an item off of the ring. The oldest entry on the ring will be
* returned. If nothing on the ring, NULL is returned.
*
* @param ring Pointer to ring (IN)
*
* @return Error code. NULL indicates an error.
*/
PMIX_EXPORT void *pmix_ring_buffer_pop(pmix_ring_buffer_t *ring);
/*
* Access an element of the ring, without removing it, indexed
* starting at the tail - a value of -1 will return the element
* at the head of the ring
*/
PMIX_EXPORT void *pmix_ring_buffer_poke(pmix_ring_buffer_t *ring, int i);
END_C_DECLS
#endif /* PMIX_RING_BUFFER_H */

View File

@@ -0,0 +1,278 @@
/*
* Copyright (c) 2004-2007 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2006 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2016-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2021-2022 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
#ifndef PMIX_VALUE_ARRAY_H
#define PMIX_VALUE_ARRAY_H
#include "src/include/pmix_config.h"
#include <string.h>
#ifdef HAVE_STRINGS_H
# include <strings.h>
#endif /* HAVE_STRINGS_H */
#include "src/class/pmix_object.h"
#if PMIX_ENABLE_DEBUG
# include "src/util/pmix_output.h"
#endif
#include "pmix_common.h"
BEGIN_C_DECLS
/*
* @file Array of elements maintained by value.
*/
struct pmix_value_array_t {
pmix_object_t super;
unsigned char *array_items;
size_t array_item_sizeof;
size_t array_size;
size_t array_alloc_size;
};
typedef struct pmix_value_array_t pmix_value_array_t;
PMIX_EXPORT PMIX_CLASS_DECLARATION(pmix_value_array_t);
/**
* Initialize the array to hold items by value. This routine must
* be called prior to using the array.
*
* @param array The array to initialize (IN).
* @param item_size The sizeof each array element (IN).
* @return PMIX error code
*
* Note that there is no corresponding "finalize" function -- use
* OBJ_DESTRUCT (for stack arrays) or OBJ_RELEASE (for heap arrays) to
* delete it.
*/
static inline int pmix_value_array_init(pmix_value_array_t *array, size_t item_sizeof)
{
array->array_item_sizeof = item_sizeof;
array->array_alloc_size = 1;
array->array_size = 0;
array->array_items = (unsigned char *) realloc(array->array_items,
item_sizeof * array->array_alloc_size);
return (NULL != array->array_items) ? PMIX_SUCCESS : PMIX_ERR_OUT_OF_RESOURCE;
}
/**
* Reserve space in the array for new elements, but do not change the size.
*
* @param array The input array (IN).
* @param size The anticipated size of the array (IN).
* @return PMIX error code.
*/
static inline int pmix_value_array_reserve(pmix_value_array_t *array, size_t size)
{
if (size > array->array_alloc_size) {
array->array_items = (unsigned char *) realloc(array->array_items,
array->array_item_sizeof * size);
if (NULL == array->array_items) {
array->array_size = 0;
array->array_alloc_size = 0;
return PMIX_ERR_OUT_OF_RESOURCE;
}
array->array_alloc_size = size;
}
return PMIX_SUCCESS;
}
/**
* Retrieves the number of elements in the array.
*
* @param array The input array (IN).
* @return The number of elements currently in use.
*/
static inline size_t pmix_value_array_get_size(pmix_value_array_t *array)
{
return array->array_size;
}
/**
* Set the number of elements in the array.
*
* @param array The input array (IN).
* @param size The new array size.
*
* @return PMIX error code.
*
* Note that resizing the array to a smaller size may not change
* the underlying memory allocated by the array. However, setting
* the size larger than the current allocation will grow it. In either
* case, if the routine is successful, pmix_value_array_get_size() will
* return the new size.
*/
PMIX_EXPORT int pmix_value_array_set_size(pmix_value_array_t *array, size_t size);
/**
* Macro to retrieve an item from the array by value.
*
* @param array The input array (IN).
* @param item_type The C datatype of the array item (IN).
* @param item_index The array index (IN).
*
* @returns item The requested item.
*
* Note that this does not change the size of the array - this macro is
* strictly for performance - the user assumes the responsibility of
* ensuring the array index is valid (0 <= item index < array size).
*/
#define PMIX_VALUE_ARRAY_GET_ITEM(array, item_type, item_index) \
((item_type *) ((array)->array_items))[item_index]
/**
* Retrieve an item from the array by reference.
*
* @param array The input array (IN).
* @param item_index The array index (IN).
*
* @return ptr Pointer to the requested item.
*
* Note that if the specified item_index is larger than the current
* array size, the array is grown to satisfy the request.
*/
static inline void *pmix_value_array_get_item(pmix_value_array_t *array, size_t item_index)
{
if (item_index >= array->array_size
&& pmix_value_array_set_size(array, item_index + 1) != PMIX_SUCCESS)
return NULL;
return array->array_items + (item_index * array->array_item_sizeof);
}
/**
* Macro to set an array element by value.
*
* @param array The input array (IN).
* @param item_type The C datatype of the array item (IN).
* @param item_index The array index (IN).
* @param item_value The new value for the specified index (IN).
*
* Note that this does not change the size of the array - this macro is
* strictly for performance - the user assumes the responsibility of
* ensuring the array index is valid (0 <= item index < array size).
*
* It is safe to free the item after returning from this call; it is
* copied into the array by value.
*/
#define PMIX_VALUE_ARRAY_SET_ITEM(array, item_type, item_index, item_value) \
(((item_type *) ((array)->array_items))[item_index] = item_value)
/**
* Set an array element by value.
*
* @param array The input array (IN).
* @param item_index The array index (IN).
* @param item_value A pointer to the item, which is copied into
* the array.
*
* @return PMIX error code.
*
* It is safe to free the item after returning from this call; it is
* copied into the array by value.
*/
static inline int pmix_value_array_set_item(pmix_value_array_t *array, size_t item_index,
const void *item)
{
int rc;
if (item_index >= array->array_size
&& (rc = pmix_value_array_set_size(array, item_index + 1)) != PMIX_SUCCESS)
return rc;
memcpy(array->array_items + (item_index * array->array_item_sizeof), item,
array->array_item_sizeof);
return PMIX_SUCCESS;
}
/**
* Appends an item to the end of the array.
*
* @param array The input array (IN).
* @param item A pointer to the item to append, which is copied
* into the array.
*
* @return PMIX error code
*
* This will grow the array if it is not large enough to contain the
* item. It is safe to free the item after returning from this call;
* it is copied by value into the array.
*/
static inline int pmix_value_array_append_item(pmix_value_array_t *array, const void *item)
{
return pmix_value_array_set_item(array, array->array_size, item);
}
/**
* Remove a specific item from the array.
*
* @param array The input array (IN).
* @param item_index The index to remove, which must be less than
* the current array size (IN).
*
* @return PMIX error code.
*
* All elements following this index are shifted down.
*/
static inline int pmix_value_array_remove_item(pmix_value_array_t *array, size_t item_index)
{
#if PMIX_ENABLE_DEBUG
if (item_index >= array->array_size) {
pmix_output(0, "pmix_value_array_remove_item: invalid index %lu\n",
(unsigned long) item_index);
return PMIX_ERR_BAD_PARAM;
}
#endif
memmove(array->array_items + (array->array_item_sizeof * item_index),
array->array_items + (array->array_item_sizeof * (item_index + 1)),
array->array_item_sizeof * (array->array_size - item_index - 1));
array->array_size--;
return PMIX_SUCCESS;
}
/**
* Get the base pointer of the underlying array.
*
* @param array The input array (IN).
* @param array_type The C datatype of the array (IN).
*
* @returns ptr Pointer to the actual array.
*
* This function is helpful when you need to iterate through an
* entire array; simply get the base value of the array and use native
* C to iterate through it manually. This can have better performance
* than looping over PMIX_VALUE_ARRAY_GET_ITEM() and
* PMIX_VALUE_ARRAY_SET_ITEM() because it will [potentially] reduce the
* number of pointer dereferences.
*/
#define PMIX_VALUE_ARRAY_GET_BASE(array, item_type) ((item_type *) ((array)->array_items))
END_C_DECLS
#endif

View File

@@ -0,0 +1,68 @@
/*
* Copyright (c) 2015-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2021-2023 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
#ifndef PMIX_CLIENT_OPS_H
#define PMIX_CLIENT_OPS_H
#include "src/include/pmix_config.h"
#include "src/class/pmix_list.h"
#include "src/class/pmix_pointer_array.h"
#include "src/common/pmix_iof.h"
#include "src/include/pmix_globals.h"
#include "src/threads/pmix_threads.h"
BEGIN_C_DECLS
typedef struct {
pmix_peer_t *myserver; // messaging support to/from my server
bool singleton; // no server
pmix_list_t pending_requests; // list of pmix_cb_t pending data requests
pmix_pointer_array_t peers; // array of pmix_peer_t cached for data ops
pmix_list_t groups; // list of groups this client is part of
// verbosity for client get operations
int get_output;
int get_verbose;
// verbosity for client connect operations
int connect_output;
int connect_verbose;
// verbosity for client fence operations
int fence_output;
int fence_verbose;
// verbosity for client pub operations
int pub_output;
int pub_verbose;
// verbosity for client spawn operations
int spawn_output;
int spawn_verbose;
// verbosity for client event operations
int event_output;
int event_verbose;
// verbosity for client iof operations
int iof_output;
int iof_verbose;
// verbosity for basic client functions
int base_output;
int base_verbose;
/* IOF output sinks */
pmix_iof_sink_t iof_stdout;
pmix_iof_sink_t iof_stderr;
} pmix_client_globals_t;
PMIX_EXPORT extern pmix_client_globals_t pmix_client_globals;
PMIX_EXPORT void pmix_parse_localquery(int sd, short args, void *cbdata);
PMIX_EXPORT pmix_status_t pmix_client_convert_group_procs(const pmix_proc_t *inprocs, size_t insize,
pmix_proc_t **outprocs, size_t *outsize);
END_C_DECLS
#endif /* PMIX_CLIENT_OPS_H */

View File

@@ -0,0 +1,76 @@
/*
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2011 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2008 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2012-2013 Los Alamos National Security, LLC.
* All rights reserved.
* Copyright (c) 2015-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2017 IBM Corporation. All rights reserved.
* Copyright (c) 2017 Mellanox Technologies. All rights reserved.
* Copyright (c) 2018 Research Organization for Information Science
* and Technology (RIST). All rights reserved.
* Copyright (c) 2021-2022 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
/**
* @file
*
* I/O Forwarding Service
*/
#ifndef PMIX_ATTRIBUTES_H
#define PMIX_ATTRIBUTES_H
#include "src/include/pmix_config.h"
#ifdef HAVE_SYS_TYPES_H
# include <sys/types.h>
#endif
#ifdef HAVE_SYS_UIO_H
# include <sys/uio.h>
#endif
#ifdef HAVE_NET_UIO_H
# include <net/uio.h>
#endif
#ifdef HAVE_UNISTD_H
# include <unistd.h>
#endif
#include "src/class/pmix_list.h"
#include "src/include/pmix_globals.h"
BEGIN_C_DECLS
PMIX_EXPORT void pmix_init_registered_attrs(void);
PMIX_EXPORT void pmix_release_registered_attrs(void);
PMIX_EXPORT pmix_status_t pmix_register_tool_attrs(void);
PMIX_EXPORT pmix_status_t pmix_register_client_attrs(void);
PMIX_EXPORT pmix_status_t pmix_register_server_attrs(void);
PMIX_EXPORT char **pmix_attributes_print_functions(char *level);
PMIX_EXPORT char **pmix_attributes_print_attr(char *level, char *function);
PMIX_EXPORT void pmix_attributes_print_attrs(char ***ans, char *function, pmix_regattr_t *attrs,
size_t nattrs);
PMIX_EXPORT void pmix_attributes_print_headers(char ***ans, char *level);
PMIX_EXPORT void pmix_attrs_query_support(int sd, short args, void *cbdata);
PMIX_EXPORT const char *pmix_attributes_lookup(const char *name);
PMIX_EXPORT const char *pmix_attributes_reverse_lookup(const char *name);
PMIX_EXPORT const pmix_regattr_input_t *pmix_attributes_lookup_term(char *attr);
END_C_DECLS
#endif /* PMIX_IOF_H */

View File

@@ -0,0 +1,287 @@
/*
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2011 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2008 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2012-2013 Los Alamos National Security, LLC.
* All rights reserved.
* Copyright (c) 2015-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2017 IBM Corporation. All rights reserved.
* Copyright (c) 2017 Mellanox Technologies. All rights reserved.
* Copyright (c) 2018 Research Organization for Information Science
* and Technology (RIST). All rights reserved.
* Copyright (c) 2021-2024 Nanook Consulting All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
/**
* @file
*
* I/O Forwarding Service
*/
#ifndef PMIX_IOF_H
#define PMIX_IOF_H
#include "src/include/pmix_config.h"
#ifdef HAVE_SYS_TYPES_H
# include <sys/types.h>
#endif
#ifdef HAVE_SYS_UIO_H
# include <sys/uio.h>
#endif
#ifdef HAVE_NET_UIO_H
# include <net/uio.h>
#endif
#ifdef HAVE_UNISTD_H
# include <unistd.h>
#endif
#include <signal.h>
#include "src/class/pmix_list.h"
#include "src/include/pmix_globals.h"
#include "src/util/pmix_fd.h"
BEGIN_C_DECLS
/*
* Maximum size of single msg
*/
#define PMIX_IOF_BASE_MSG_MAX 8192
#define PMIX_IOF_BASE_TAG_MAX 1024
#define PMIX_IOF_MAX_INPUT_BUFFERS 50
#define PMIX_IOF_MAX_RETRIES 4
typedef struct {
pmix_list_item_t super;
bool pending;
bool always_writable;
int numtries;
pmix_event_t *ev;
struct timeval tv;
int fd;
pmix_list_t outputs;
} pmix_iof_write_event_t;
PMIX_EXPORT PMIX_CLASS_DECLARATION(pmix_iof_write_event_t);
#define PMIX_IOF_WRITE_EVENT_STATIC_INIT \
{ \
.super = PMIX_LIST_ITEM_STATIC_INIT, \
.pending = false, \
.always_writable = false, \
.numtries = 0, \
.ev = NULL, \
.tv = {0, 0}, \
.fd = 0, \
.outputs = PMIX_LIST_STATIC_INIT \
}
typedef struct {
pmix_list_item_t super;
pmix_proc_t name;
pmix_iof_channel_t tag;
pmix_iof_write_event_t wev;
bool xoff;
bool exclusive;
bool closed;
} pmix_iof_sink_t;
PMIX_EXPORT PMIX_CLASS_DECLARATION(pmix_iof_sink_t);
#define PMIX_IOF_SINK_STATIC_INIT \
{ \
.super = PMIX_LIST_ITEM_STATIC_INIT, \
.name = {{0}, 0}, \
.tag = PMIX_FWD_NO_CHANNELS, \
.wev = PMIX_IOF_WRITE_EVENT_STATIC_INIT, \
.xoff = false, \
.exclusive = false, \
.closed = false \
}
typedef struct {
pmix_list_item_t super;
char *data;
int numbytes;
} pmix_iof_write_output_t;
PMIX_EXPORT PMIX_CLASS_DECLARATION(pmix_iof_write_output_t);
typedef struct {
pmix_object_t super;
pmix_event_t ev;
struct timeval tv;
int fd;
bool active;
void *childproc;
bool always_readable;
pmix_proc_t name;
pmix_iof_channel_t channel;
pmix_proc_t *targets;
size_t ntargets;
pmix_info_t *directives;
size_t ndirs;
} pmix_iof_read_event_t;
PMIX_EXPORT PMIX_CLASS_DECLARATION(pmix_iof_read_event_t);
typedef struct {
pmix_list_item_t super;
pmix_proc_t name;
pmix_iof_write_event_t *channel;
pmix_iof_flags_t flags;
pmix_iof_channel_t stream;
bool copystdout;
bool copystderr;
pmix_byte_object_t bo;
} pmix_iof_residual_t;
PMIX_EXPORT PMIX_CLASS_DECLARATION(pmix_iof_residual_t);
/* Write event macro's */
static inline bool pmix_iof_fd_always_ready(int fd)
{
return pmix_fd_is_regular(fd) || (pmix_fd_is_chardev(fd) && !isatty(fd))
|| pmix_fd_is_blkdev(fd);
}
#define PMIX_IOF_SINK_BLOCKSIZE (1024)
#define PMIX_IOF_SINK_ACTIVATE(w) \
do { \
struct timeval *tv = NULL; \
(w)->pending = true; \
PMIX_POST_OBJECT((w)); \
if ((w)->always_writable) { \
/* Regular is always write ready. Use timer to activate */ \
tv = &(w)->tv; \
} \
if (pmix_event_add((w)->ev, tv)) { \
PMIX_ERROR_LOG(PMIX_ERR_BAD_PARAM); \
} \
} while (0);
/* define an output "sink", adding it to the provided
* endpoint list for this proc */
#define PMIX_IOF_SINK_DEFINE(snk, nm, fid, tg, wrthndlr) \
do { \
pmix_output_verbose(1, pmix_client_globals.iof_output, \
"defining endpt: file %s line %d fd %d", __FILE__, __LINE__, (fid)); \
PMIX_CONSTRUCT((snk), pmix_iof_sink_t); \
pmix_strncpy((snk)->name.nspace, (nm)->nspace, PMIX_MAX_NSLEN); \
(snk)->name.rank = (nm)->rank; \
(snk)->tag = (tg); \
if (0 <= (fid)) { \
(snk)->wev.fd = (fid); \
(snk)->wev.always_writable = pmix_iof_fd_always_ready(fid); \
if ((snk)->wev.always_writable) { \
pmix_event_evtimer_set(pmix_globals.evbase, (snk)->wev.ev, wrthndlr, (snk)); \
} else { \
pmix_event_set(pmix_globals.evbase, (snk)->wev.ev, (snk)->wev.fd, PMIX_EV_WRITE, \
wrthndlr, (snk)); \
} \
} \
PMIX_POST_OBJECT(snk); \
} while (0);
/* Read event macro's */
#define PMIX_IOF_READ_ADDEV(rev) \
do { \
struct timeval *tv = NULL; \
if ((rev)->always_readable) { \
tv = &(rev)->tv; \
} \
if (pmix_event_add(&(rev)->ev, tv)) { \
PMIX_ERROR_LOG(PMIX_ERR_BAD_PARAM); \
} \
} while (0);
#define PMIX_IOF_READ_ACTIVATE(rev) \
do { \
(rev)->active = true; \
PMIX_POST_OBJECT(rev); \
PMIX_IOF_READ_ADDEV(rev); \
} while (0);
#define PMIX_IOF_READ_EVENT(rv, p, np, d, nd, fid, cbfunc, actv) \
do { \
size_t _ii; \
pmix_iof_read_event_t *rev; \
pmix_output_verbose(1, pmix_client_globals.iof_output, "defining read event at: %s %d", \
__FILE__, __LINE__); \
rev = PMIX_NEW(pmix_iof_read_event_t); \
if (NULL != (p)) { \
(rev)->ntargets = (np); \
PMIX_PROC_CREATE((rev)->targets, (rev)->ntargets); \
memcpy((rev)->targets, (p), (np) * sizeof(pmix_proc_t)); \
} \
if (NULL != (d) && 0 < (nd)) { \
PMIX_INFO_CREATE((rev)->directives, (nd)); \
(rev)->ndirs = (nd); \
for (_ii = 0; _ii < (size_t) nd; _ii++) { \
PMIX_INFO_XFER(&((rev)->directives[_ii]), &((d)[_ii])); \
} \
} \
rev->fd = (fid); \
rev->always_readable = pmix_iof_fd_always_ready(fid); \
*(rv) = rev; \
if (rev->always_readable) { \
pmix_event_evtimer_set(pmix_globals.evbase, &rev->ev, (cbfunc), rev); \
} else { \
pmix_event_set(pmix_globals.evbase, &rev->ev, (fid), PMIX_EV_READ, (cbfunc), rev); \
} \
if ((actv)) { \
PMIX_IOF_READ_ACTIVATE(rev) \
} \
} while (0);
#define PMIX_IOF_READ_EVENT_LOCAL(rv, fid, cbfunc, actv) \
do { \
pmix_iof_read_event_t *rev; \
pmix_output_verbose(1, pmix_client_globals.iof_output, "defining read event at: %s %d", \
__FILE__, __LINE__); \
rev = PMIX_NEW(pmix_iof_read_event_t); \
rev->fd = (fid); \
rev->always_readable = pmix_iof_fd_always_ready(fid); \
*(rv) = rev; \
if (rev->always_readable) { \
pmix_event_evtimer_set(pmix_globals.evbase, &rev->ev, (cbfunc), rev); \
} else { \
pmix_event_set(pmix_globals.evbase, &rev->ev, (fid), PMIX_EV_READ, (cbfunc), rev); \
} \
if ((actv)) { \
PMIX_IOF_READ_ACTIVATE(rev) \
} \
} while (0);
PMIX_EXPORT pmix_status_t pmix_iof_flush(void);
PMIX_EXPORT pmix_status_t pmix_iof_write_output(const pmix_proc_t *name, pmix_iof_channel_t stream,
const pmix_byte_object_t *bo);
PMIX_EXPORT void pmix_iof_static_dump_output(pmix_iof_sink_t *sink);
PMIX_EXPORT void pmix_iof_write_handler(int fd, short event, void *cbdata);
PMIX_EXPORT bool pmix_iof_stdin_check(int fd);
PMIX_EXPORT void pmix_iof_read_local_handler(int unusedfd, short event, void *cbdata);
PMIX_EXPORT void pmix_iof_stdin_cb(int fd, short event, void *cbdata);
PMIX_EXPORT pmix_status_t pmix_iof_process_iof(pmix_iof_channel_t channels,
const pmix_proc_t *source,
const pmix_byte_object_t *bo,
const pmix_info_t *info, size_t ninfo,
pmix_iof_req_t *req);
PMIX_EXPORT void pmix_iof_check_flags(pmix_info_t *info, pmix_iof_flags_t *flags);
PMIX_EXPORT void pmix_iof_flush_residuals(void);
PMIX_EXPORT pmix_byte_object_t* pmix_iof_prep_output(const pmix_proc_t *name,
pmix_iof_flags_t *myflags,
pmix_iof_channel_t stream,
const pmix_byte_object_t *bo);
END_C_DECLS
#endif /* PMIX_IOF_H */

View File

@@ -0,0 +1,179 @@
/* -*- Mode: C; c-basic-offset:4 ; indent-tabs-mode:nil -*- */
/*
* Copyright (c) 2004-2008 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2005 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2011-2015 Los Alamos National Security, LLC. All rights
* reserved.
* Copyright (c) 2016-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2021-2024 Nanook Consulting All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
/**
* @file
*
* The PMIx Fork/Exec Subsystem
*
*/
#ifndef PMIX_PFEXEC_H
#define PMIX_PFEXEC_H
#include "pmix_config.h"
#include "src/class/pmix_list.h"
#include "src/common/pmix_iof.h"
#include "src/server/pmix_server_ops.h"
BEGIN_C_DECLS
typedef struct {
int usepty;
bool connect_stdin;
/* private - callers should not modify these fields */
int p_stdin[2];
int p_stdout[2];
int p_stderr[2];
} pmix_pfexec_base_io_conf_t;
typedef struct {
pmix_list_item_t super;
pmix_event_t ev;
pmix_proc_t proc;
pid_t pid;
bool completed;
int exitcode;
int keepalive[2];
pmix_pfexec_base_io_conf_t opts;
pmix_iof_sink_t stdinsink;
pmix_iof_read_event_t *stdoutev;
pmix_iof_read_event_t *stderrev;
} pmix_pfexec_child_t;
PMIX_EXPORT PMIX_CLASS_DECLARATION(pmix_pfexec_child_t);
typedef struct {
pmix_event_t *handler;
bool active;
pmix_list_t children;
int timeout_before_sigkill;
size_t nextid;
bool selected;
} pmix_pfexec_globals_t;
PMIX_EXPORT extern pmix_pfexec_globals_t pmix_pfexec_globals;
typedef struct {
pmix_object_t super;
pmix_event_t ev;
pmix_proc_t *proc;
int signal;
pmix_lock_t *lock;
} pmix_pfexec_signal_caddy_t;
PMIX_EXPORT PMIX_CLASS_DECLARATION(pmix_pfexec_signal_caddy_t);
PMIX_EXPORT int pmix_pfexec_base_open(void);
PMIX_EXPORT int pmix_pfexec_register(void);
PMIX_EXPORT int pmix_pfexec_base_close(void);
PMIX_EXPORT pmix_status_t pmix_pfexec_base_spawn_job(pmix_setup_caddy_t *fcd);
PMIX_EXPORT void pmix_pfexec_base_spawn_proc(int sd, short args, void *cbdata);
PMIX_EXPORT void pmix_pfexec_base_kill_proc(int sd, short args, void *cbdata);
PMIX_EXPORT void pmix_pfexec_base_signal_proc(int sd, short args, void *cbdata);
PMIX_EXPORT void pmix_pfexec_check_complete(int sd, short args, void *cbdata);
#define PMIX_PFEXEC_SPAWN(fcd) \
do { \
pmix_event_assign(&(fcd->ev), pmix_globals.evbase, -1, EV_WRITE, \
pmix_pfexec_base_spawn_proc, fcd); \
PMIX_POST_OBJECT((fcd)); \
pmix_event_active(&((fcd)->ev), EV_WRITE, 1); \
} while (0)
#define PMIX_PFEXEC_KILL(r, lk) \
do { \
pmix_pfexec_signal_caddy_t *scd; \
(scd) = PMIX_NEW(pmix_pfexec_signal_caddy_t); \
(scd)->proc = (r); \
(scd)->lock = (lk); \
pmix_event_assign(&((scd)->ev), pmix_globals.evbase, -1, EV_WRITE, \
pmix_pfexec_base_kill_proc, (scd)); \
PMIX_POST_OBJECT((scd)); \
pmix_event_active(&((scd)->ev), EV_WRITE, 1); \
} while (0)
#define PMIX_PFEXEC_SIGNAL(scd, r, nm, fn, lk) \
do { \
pmix_pfexec_signal_caddy_t *scd; \
(scd) = PMIX_NEW(pmix_pfexec_signal_caddy_t); \
(scd)->proc = (r); \
(scd)->signal = (nm); \
(scd)->lock = (lk); \
pmix_event_assign(&((scd)->ev), pmix_globals.evbase, -1, EV_WRITE, \
pmix_pfexec_base_signal_proc, (scd)); \
PMIX_POST_OBJECT((scd)); \
pmix_event_active(&((scd)->ev), EV_WRITE, 1); \
} while (0)
typedef struct {
pmix_object_t super;
pmix_event_t ev;
pmix_pfexec_child_t *child;
} pmix_pfexec_cmpl_caddy_t;
PMIX_EXPORT PMIX_CLASS_DECLARATION(pmix_pfexec_cmpl_caddy_t);
#define PMIX_PFEXEC_CHK_COMPLETE(c) \
do { \
pmix_pfexec_cmpl_caddy_t *pc = PMIX_NEW(pmix_pfexec_cmpl_caddy_t); \
pc->child = (c); \
pmix_event_assign(&((pc)->ev), pmix_globals.evbase, -1, EV_WRITE, \
pmix_pfexec_check_complete, (pc)); \
PMIX_POST_OBJECT((pc)); \
pmix_event_active(&((pc)->ev), EV_WRITE, 1); \
} while (0)
/*
* Struct written up the pipe from the child to the parent.
*/
typedef struct {
/* True if the child has died; false if this is just a warning to
be printed. */
bool fatal;
/* Relevant only if fatal==true */
int exit_status;
/* Length of the strings that are written up the pipe after this
struct */
int file_str_len;
int topic_str_len;
int msg_str_len;
} pmix_pfexec_pipe_err_msg_t;
PMIX_EXPORT pmix_status_t pmix_pfexec_base_setup_child(pmix_pfexec_child_t *child);
/*
* Max length of strings from the pmix_pfexec_pipe_err_msg_t
*/
#define PMIX_PFEXEC_MAX_FILE_LEN 511
#define PMIX_PFEXEC_MAX_TOPIC_LEN PMIX_PFEXEC_MAX_FILE_LEN
END_C_DECLS
#endif /* MCA_PFEXEC_H */

View File

@@ -0,0 +1,299 @@
/* -*- Mode: C; c-basic-offset:4 ; indent-tabs-mode:nil -*- */
/*
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2006 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2015-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2020 IBM Corporation. All rights reserved.
* Copyright (c) 2021-2022 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
#ifndef PMIX_EVENT_H
#define PMIX_EVENT_H
#include "src/include/pmix_config.h"
#include "src/include/pmix_types.h"
#include <event.h>
#include "pmix_common.h"
#include "src/class/pmix_list.h"
#include "src/mca/bfrops/bfrops_types.h"
#include "src/util/pmix_output.h"
BEGIN_C_DECLS
#define PMIX_EVENT_ORDER_NONE 0x00
#define PMIX_EVENT_ORDER_FIRST 0x01
#define PMIX_EVENT_ORDER_LAST 0x02
#define PMIX_EVENT_ORDER_BEFORE 0x04
#define PMIX_EVENT_ORDER_AFTER 0x08
#define PMIX_EVENT_ORDER_PREPEND 0x10
#define PMIX_EVENT_ORDER_APPEND 0x20
#define PMIX_EVENT_ORDER_FIRST_OVERALL 0x40
#define PMIX_EVENT_ORDER_LAST_OVERALL 0x80
/* define an internal attribute for marking that the
* server processed an event before passing it up
* to its host in case it comes back down - avoids
* infinite loop */
#define PMIX_SERVER_INTERNAL_NOTIFY "pmix.srvr.internal.notify"
/* define a struct for tracking registration ranges */
typedef struct {
pmix_data_range_t range;
pmix_proc_t *procs;
size_t nprocs;
} pmix_range_trkr_t;
#define PMIX_RANGE_TRKR_STATIC_INIT \
{ \
.range = PMIX_RANGE_UNDEF, \
.procs = NULL, \
.nprocs = 0 \
}
/* define a common struct for tracking event handlers */
typedef struct {
pmix_list_item_t super;
char *name;
size_t index;
uint8_t precedence;
bool oneshot;
char *locator;
pmix_proc_t source; // who generated this event
/* When registering for events, callers can specify
* the range of sources from which they are willing
* to receive notifications - e.g., for callers to
* define different handlers for events coming from
* the RM vs those coming from their peers. We use
* the rng field to track these values upon registration.
*/
pmix_range_trkr_t rng;
/* For registration, we use the affected field to track
* the range of procs that, if affected by the event,
* should cause the handler to be called (subject, of
* course, to any rng constraints).
*/
pmix_proc_t *affected;
size_t naffected;
pmix_notification_fn_t evhdlr;
void *cbobject;
pmix_status_t *codes;
size_t ncodes;
} pmix_event_hdlr_t;
PMIX_CLASS_DECLARATION(pmix_event_hdlr_t);
#define PMIX_EVENT_HDLR_STATIC_INIT \
{ \
.super = PMIX_LIST_ITEM_STATIC_INIT, \
.name = NULL, \
.index = SIZE_MAX, \
.precedence = UINT8_MAX, \
.locator = NULL, \
.source = PMIX_PROC_STATIC_INIT, \
.rng = PMIX_RANGE_TRKR_STATIC_INIT, \
.affected - NULL, \
.naffected = 0, \
.evhdlr = NULL, \
.cbobject = NULL, \
.codes = NULL, \
.ncodes = 0 \
}
/* define an object for tracking status codes we are actively
* registered to receive */
typedef struct {
pmix_list_item_t super;
pmix_status_t code;
size_t nregs;
} pmix_active_code_t;
PMIX_CLASS_DECLARATION(pmix_active_code_t);
/* define an object for housing the different lists of events
* we have registered so we can easily scan them in precedent
* order when we get an event */
typedef struct {
pmix_object_t super;
size_t nhdlrs;
pmix_event_hdlr_t *first;
pmix_event_hdlr_t *last;
pmix_list_t actives;
pmix_list_t single_events;
pmix_list_t multi_events;
pmix_list_t default_events;
} pmix_events_t;
PMIX_CLASS_DECLARATION(pmix_events_t);
#define PMIX_EVENTS_STATIC_INIT \
{ \
.super = PMIX_OBJ_STATIC_INIT(pmix_object_t), \
.nhdlrs = 0, \
.first = NULL, \
.last = NULL, \
.actives = PMIX_LIST_STATIC_INIT, \
.single_events = PMIX_LIST_STATIC_INIT, \
.multi_events = PMIX_LIST_STATIC_INIT, \
.default_events = PMIX_LIST_STATIC_INIT \
}
/* define an object for chaining event notifications thru
* the local state machine. Each registered event handler
* that asked to be notified for a given code is given a
* chance to "see" the reported event, starting with
* single-code handlers, then multi-code handlers, and
* finally default handlers. This object provides a
* means for us to relay the event across that chain
*/
typedef struct pmix_event_chain_t {
pmix_list_item_t super;
pmix_status_t status;
pmix_event_t ev;
bool timer_active;
bool nondefault;
bool endchain;
bool cached;
pmix_proc_t source;
pmix_data_range_t range;
/* When generating events, callers can specify
* the range of targets to receive notifications.
*/
pmix_proc_t *targets;
size_t ntargets;
/* the processes that we affected by the event */
pmix_proc_t *affected;
size_t naffected;
/* any info provided by the event generator */
pmix_info_t *info;
size_t ninfo;
size_t nallocated;
pmix_status_t interim_status;
pmix_info_t *results;
size_t nresults;
pmix_info_t *interim;
size_t ninterim;
pmix_event_hdlr_t *evhdlr;
pmix_op_cbfunc_t opcbfunc;
void *cbdata;
pmix_op_cbfunc_t final_cbfunc;
void *final_cbdata;
} pmix_event_chain_t;
PMIX_CLASS_DECLARATION(pmix_event_chain_t);
/* prepare a chain for processing by cycling across provided
* info structs and translating those supported by the event
* system into the chain object*/
PMIX_EXPORT pmix_status_t pmix_prep_event_chain(pmix_event_chain_t *chain, const pmix_info_t *info,
size_t ninfo, bool xfer);
/* invoke the error handler that is registered against the given
* status, passing it the provided info on the procs that were
* affected, plus any additional info provided by the server */
PMIX_EXPORT void pmix_invoke_local_event_hdlr(pmix_event_chain_t *chain);
PMIX_EXPORT bool pmix_notify_check_range(pmix_range_trkr_t *rng, const pmix_proc_t *proc);
PMIX_EXPORT bool pmix_notify_check_affected(pmix_proc_t *interested, size_t ninterested,
pmix_proc_t *affected, size_t naffected);
PMIX_EXPORT pmix_status_t pmix_deregister_event_hdlr(size_t event_hdlr_ref,
pmix_buffer_t *msg);
/* invoke the server event notification handler */
PMIX_EXPORT pmix_status_t pmix_server_notify_client_of_event(pmix_status_t status,
const pmix_proc_t *source,
pmix_data_range_t range,
const pmix_info_t info[], size_t ninfo,
pmix_op_cbfunc_t cbfunc, void *cbdata);
PMIX_EXPORT pmix_status_t pmix_notify_server_of_event(pmix_status_t status, const pmix_proc_t *source,
pmix_data_range_t range, const pmix_info_t info[],
size_t ninfo, pmix_op_cbfunc_t cbfunc, void *cbdata,
bool dolocal);
PMIX_EXPORT void pmix_event_timeout_cb(int fd, short flags, void *arg);
#define PMIX_REPORT_EVENT(e, p, r, f) \
do { \
pmix_event_chain_t *ch, *cp; \
size_t _n; \
\
ch = NULL; \
/* see if we already have this event cached */ \
PMIX_LIST_FOREACH (cp, &pmix_globals.cached_events, pmix_event_chain_t) { \
if (cp->status == (e)) { \
ch = cp; \
break; \
} \
} \
if (NULL == ch) { \
/* nope - need to add it */ \
ch = PMIX_NEW(pmix_event_chain_t); \
ch->status = (e); \
ch->range = (r); \
PMIX_LOAD_PROCID(&ch->source, (p)->nptr->nspace, (p)->info->pname.rank); \
PMIX_PROC_CREATE(ch->affected, 1); \
ch->naffected = 1; \
PMIX_LOAD_PROCID(ch->affected, (p)->nptr->nspace, (p)->info->pname.rank); \
/* if this is lost-connection-to-server, then we let it go to */ \
/* the default event handler - otherwise, we don't */ \
if (PMIX_ERR_LOST_CONNECTION != (e) && PMIX_ERR_UNREACH != (e)) { \
ch->ninfo = 1; \
ch->nallocated = 3; \
PMIX_INFO_CREATE(ch->info, ch->nallocated); \
/* mark for non-default handlers only */ \
PMIX_INFO_LOAD(&ch->info[0], PMIX_EVENT_NON_DEFAULT, NULL, PMIX_BOOL); \
} else { \
ch->nallocated = 2; \
PMIX_INFO_CREATE(ch->info, ch->nallocated); \
} \
ch->final_cbfunc = (f); \
ch->final_cbdata = ch; \
/* cache it */ \
pmix_list_append(&pmix_globals.cached_events, &ch->super); \
ch->timer_active = true; \
pmix_event_assign(&ch->ev, pmix_globals.evbase, -1, 0, pmix_event_timeout_cb, ch); \
PMIX_POST_OBJECT(ch); \
pmix_event_add(&ch->ev, &pmix_globals.event_window); \
} else { \
/* add this peer to the array of sources */ \
pmix_proc_t proc_tmp; \
pmix_info_t *info_tmp; \
size_t ninfo_tmp; \
pmix_strncpy(proc_tmp.nspace, (p)->nptr->nspace, PMIX_MAX_NSLEN); \
proc_tmp.rank = (p)->info->pname.rank; \
ninfo_tmp = ch->nallocated + 1; \
PMIX_INFO_CREATE(info_tmp, ninfo_tmp); \
/* must keep the hdlr name and return object at the end, so prepend */ \
PMIX_INFO_LOAD(&info_tmp[0], PMIX_PROCID, &proc_tmp, PMIX_PROC); \
for (_n = 0; _n < ch->ninfo; _n++) { \
PMIX_INFO_XFER(&info_tmp[_n + 1], &ch->info[_n]); \
} \
PMIX_INFO_FREE(ch->info, ch->nallocated); \
ch->nallocated = ninfo_tmp; \
ch->info = info_tmp; \
ch->ninfo = ninfo_tmp - 2; \
/* reset the timer */ \
if (ch->timer_active) { \
pmix_event_del(&ch->ev); \
} \
PMIX_POST_OBJECT(ch); \
ch->timer_active = true; \
pmix_event_add(&ch->ev, &pmix_globals.event_window); \
} \
} while (0)
END_C_DECLS
#endif /* PMIX_EVENT_H */

View File

@@ -0,0 +1,150 @@
/* -*- Mode: C; c-basic-offset:4 ; indent-tabs-mode:nil -*- */
/*
* Copyright (c) 2007-2008 Cisco Systems, Inc. All rights reserved.
*
* Copyright (c) 2015-2018 Research Organization for Information Science
* and Technology (RIST). All rights reserved.
* Copyright (c) 2018-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2021-2022 Nanook Consulting. All rights reserved.
* Copyright (c) 2022 Triad National Security, LLC. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
/**
* @file
*
* This interface is for use by PMIx to obtain topology-related info
*
*/
#ifndef PMIX_HWLOC_H
#define PMIX_HWLOC_H
#include "src/include/pmix_config.h"
#include <hwloc.h>
#include "pmix_common.h"
#include "src/class/pmix_list.h"
#include "src/include/pmix_globals.h"
#include "src/mca/base/pmix_mca_base_framework.h"
#include "src/mca/base/pmix_mca_base_var.h"
#include "src/mca/mca.h"
#include "src/server/pmix_server_ops.h"
BEGIN_C_DECLS
#if HWLOC_API_VERSION < 0x20000
# ifndef HAVE_HWLOC_TOPOLOGY_DUP
# define HAVE_HWLOC_TOPOLOGY_DUP 0
# endif
# define HWLOC_OBJ_L3CACHE HWLOC_OBJ_CACHE
# define HWLOC_OBJ_L2CACHE HWLOC_OBJ_CACHE
# define HWLOC_OBJ_L1CACHE HWLOC_OBJ_CACHE
# if HWLOC_API_VERSION < 0x10b00
# define HWLOC_OBJ_NUMANODE HWLOC_OBJ_NODE
# define HWLOC_OBJ_PACKAGE HWLOC_OBJ_SOCKET
# endif
# define HAVE_DECL_HWLOC_OBJ_OSDEV_COPROC 0
#else
# define HAVE_DECL_HWLOC_OBJ_OSDEV_COPROC 1
#endif
/**
* Register params
*/
PMIX_EXPORT pmix_status_t pmix_hwloc_register(void);
/**
* Finalize. Tear down any allocated storage
*/
PMIX_EXPORT void pmix_hwloc_finalize(void);
/* Setup the topology for delivery to clients */
PMIX_EXPORT pmix_status_t pmix_hwloc_setup_topology(pmix_info_t *info, size_t ninfo);
/* Load the topology */
PMIX_EXPORT pmix_status_t pmix_hwloc_load_topology(pmix_topology_t *topo);
/* Generate the string representation of a cpuset */
PMIX_EXPORT pmix_status_t pmix_hwloc_generate_cpuset_string(const pmix_cpuset_t *cpuset,
char **cpuset_string);
/* get cpuset from its string representation */
PMIX_EXPORT pmix_status_t pmix_hwloc_parse_cpuset_string(const char *cpuset_string, pmix_cpuset_t *cpuset);
/* Get locality string */
PMIX_EXPORT pmix_status_t pmix_hwloc_generate_locality_string(const pmix_cpuset_t *cpuset, char **loc);
/* Get relative locality */
PMIX_EXPORT pmix_status_t pmix_hwloc_get_relative_locality(const char *locality1,
const char *locality2,
pmix_locality_t *loc);
/* Get current bound location */
PMIX_EXPORT pmix_status_t pmix_hwloc_get_cpuset(pmix_cpuset_t *cpuset, pmix_bind_envelope_t ref);
/* Get distance array */
PMIX_EXPORT pmix_status_t pmix_hwloc_compute_distances(pmix_topology_t *topo, pmix_cpuset_t *cpuset,
pmix_info_t info[], size_t ninfo,
pmix_device_distance_t **dist, size_t *ndist);
PMIX_EXPORT pmix_status_t pmix_hwloc_check_vendor(pmix_topology_t *topo,
unsigned short vendorID,
uint16_t class);
/* cpuset pack/unpack/copy/print functions */
PMIX_EXPORT pmix_status_t pmix_hwloc_pack_cpuset(pmix_buffer_t *buf, pmix_cpuset_t *src,
pmix_pointer_array_t *regtypes);
PMIX_EXPORT pmix_status_t pmix_hwloc_unpack_cpuset(pmix_buffer_t *buf, pmix_cpuset_t *dest,
pmix_pointer_array_t *regtypes);
PMIX_EXPORT pmix_status_t pmix_hwloc_copy_cpuset(pmix_cpuset_t *dest, pmix_cpuset_t *src);
PMIX_EXPORT char *pmix_hwloc_print_cpuset(pmix_cpuset_t *src);
PMIX_EXPORT void pmix_hwloc_destruct_cpuset(pmix_cpuset_t *cpuset);
PMIX_EXPORT void pmix_hwloc_release_cpuset(pmix_cpuset_t *ptr, size_t sz);
PMIX_EXPORT pmix_status_t pmix_hwloc_get_cpuset_size(pmix_cpuset_t *ptr, size_t *sz);
/* topology pack/unpack/copy/print functions */
PMIX_EXPORT pmix_status_t pmix_hwloc_pack_topology(pmix_buffer_t *buf, pmix_topology_t *src,
pmix_pointer_array_t *regtypes);
PMIX_EXPORT pmix_status_t pmix_hwloc_unpack_topology(pmix_buffer_t *buf, pmix_topology_t *dest,
pmix_pointer_array_t *regtypes);
PMIX_EXPORT pmix_status_t pmix_hwloc_copy_topology(pmix_topology_t *dest, pmix_topology_t *src);
PMIX_EXPORT char *pmix_hwloc_print_topology(pmix_topology_t *src);
PMIX_EXPORT void pmix_hwloc_destruct_topology(pmix_topology_t *ptr);
PMIX_EXPORT void pmix_hwloc_release_topology(pmix_topology_t *ptr, size_t sz);
PMIX_EXPORT pmix_status_t pmix_hwloc_get_topology_size(pmix_topology_t *ptr, size_t *sz);
/**** PRESERVE ABI ****/
PMIX_EXPORT void pmix_ploc_base_destruct_cpuset(pmix_cpuset_t *cpuset);
PMIX_EXPORT void pmix_ploc_base_release_cpuset(pmix_cpuset_t *ptr, size_t sz);
PMIX_EXPORT void pmix_ploc_base_destruct_topology(pmix_topology_t *ptr);
PMIX_EXPORT void pmix_ploc_base_release_topology(pmix_topology_t *ptr, size_t sz);
END_C_DECLS
#endif

View File

@@ -0,0 +1,142 @@
/* -*- Mode: C; c-basic-offset:4 ; indent-tabs-mode:nil -*- */
/*
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2006 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2007 Sun Microsystems, Inc. All rights reserved.
* Copyright (c) 2011 Sandia National Laboratories. All rights reserved.
* Copyright (c) 2011-2017 Los Alamos National Security, LLC. All rights
* reserved.
* Copyright (c) 2017 Research Organization for Information Science
* and Technology (RIST). All rights reserved.
* Copyright (c) 2018-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2021-2022 Nanook Consulting All rights reserved.
* Copyright (c) Amazon.com, Inc. or its affiliates. All Rights
* reserved.
* Copyright (c) 2023 Triad National Security, LLC. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
/** @file
*
* Atomic operations.
*
* This API is patterned after the FreeBSD kernel atomic interface
* (which is influenced by Intel's ia64 architecture). The
* FreeBSD interface is documented at
*
* http://www.freebsd.org/cgi/man.cgi?query=atomic&sektion=9
*
* Only the necessary subset of functions are implemented here.
*
* The following #defines will be true / false based on
* assembly support:
*
* - \c PMIX_HAVE_ATOMIC_MEM_BARRIER atomic memory barriers
* - \c PMIX_HAVE_ATOMIC_SPINLOCKS atomic spinlocks
* - \c PMIX_HAVE_ATOMIC_MATH_32 if 32 bit add/sub/compare-exchange can be done "atomically"
* - \c PMIX_HAVE_ATOMIC_MATH_64 if 64 bit add/sub/compare-exchange can be done "atomically"
*
* Note that for the Atomic math, atomic add/sub may be implemented as
* C code using pmix_atomic_compare_exchange. The appearance of atomic
* operation will be upheld in these cases.
*/
#ifndef PMIX_SYS_ATOMIC_H
#define PMIX_SYS_ATOMIC_H 1
#include "src/include/pmix_config.h"
#include "src/include/pmix_stdatomic.h"
#if PMIX_USE_C11_ATOMICS
#include <stdatomic.h>
static inline void pmix_atomic_wmb(void)
{
atomic_thread_fence(memory_order_release);
}
static inline void pmix_atomic_rmb(void)
{
# if defined(PMIX_ATOMIC_X86_64)
/* work around a bug in older gcc versions (observed in gcc 6.x)
* where acquire seems to get treated as a no-op instead of being
* equivalent to __asm__ __volatile__("": : :"memory") on x86_64 */
__asm__ __volatile__("" : : : "memory");
# else
atomic_thread_fence(memory_order_acquire);
# endif
}
#define PMIX_ATOMIC_DEFINE_OP(type, bits, operator, name) \
static inline type \
pmix_atomic_fetch_##name##_##bits(pmix_atomic_##type *addr, type value) \
{ \
return atomic_fetch_##name##_explicit( \
addr, value, memory_order_relaxed); \
} \
\
static inline type \
pmix_atomic_##name##_fetch_##bits(pmix_atomic_##type *addr, type value) \
{ \
return atomic_fetch_##name##_explicit( \
addr, value, memory_order_relaxed) operator value; \
}
/* end of PMIX_USE_C11_ATOMICS */
#elif PMIX_USE_GCC_BUILTIN_ATOMICS
static inline void pmix_atomic_wmb(void)
{
__atomic_thread_fence(__ATOMIC_RELEASE);
}
static inline void pmix_atomic_rmb(void)
{
#if defined(PMIX_ATOMIC_X86_64)
/* work around a bug in older gcc versions where ACQUIRE seems to get
* treated as a no-op instead of being equivalent to
* __asm__ __volatile__("": : :"memory") */
__asm__ __volatile__("" : : : "memory");
#else
__atomic_thread_fence(__ATOMIC_ACQUIRE);
#endif
}
#define PMIX_ATOMIC_DEFINE_OP(type, bits, operator, name) \
static inline type \
pmix_atomic_fetch_##name##_##bits(pmix_atomic_##type *addr, type value) \
{ \
return __atomic_fetch_##name(addr, value, __ATOMIC_RELAXED); \
} \
\
static inline type \
pmix_atomic_##name##_fetch_##bits(pmix_atomic_##type *addr, type value) \
{ \
return __atomic_##name##_fetch(addr, value, __ATOMIC_RELAXED); \
}
/* end of PMIX_USE_GCC_BUILTIN_ATOMICS */
#else
#error OpenPMIx requires either C11 atomics support or GCC built-in atomics.
#endif
PMIX_ATOMIC_DEFINE_OP(int32_t, 32, +, add)
PMIX_ATOMIC_DEFINE_OP(int32_t, 32, &, and)
PMIX_ATOMIC_DEFINE_OP(int32_t, 32, |, or)
PMIX_ATOMIC_DEFINE_OP(int32_t, 32, ^, xor)
PMIX_ATOMIC_DEFINE_OP(int32_t, 32, -, sub)
#endif /* PMIX_SYS_ATOMIC_H */

View File

@@ -0,0 +1,886 @@
/* src/include/pmix_config.h. Generated from pmix_config.h.in by configure. */
/* src/include/pmix_config.h.in. Generated from configure.ac by autoheader. */
/* -*- c -*-
*
* Copyright (c) 2004-2005 The Trustees of Indiana University.
* All rights reserved.
* Copyright (c) 2004-2005 The Trustees of the University of Tennessee.
* All rights reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2013-2015 Intel, Inc. All rights reserved
* Copyright (c) 2016 IBM Corporation. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*
* This file is automatically generated by configure. Edits will be lost
* the next time you run configure!
*/
#ifndef PMIX_CONFIG_H
#define PMIX_CONFIG_H
#include "src/include/pmix_config_top.h"
/* Define if building universal (internal helper macro) */
/* #undef AC_APPLE_UNIVERSAL_BUILD */
/* The normal alignment of `bool', in bytes. */
#define ALIGNOF_BOOL 1
/* The normal alignment of `double', in bytes. */
#define ALIGNOF_DOUBLE 8
/* The normal alignment of `int', in bytes. */
#define ALIGNOF_INT 4
/* The normal alignment of `long', in bytes. */
#define ALIGNOF_LONG 8
/* The normal alignment of `long long', in bytes. */
#define ALIGNOF_LONG_LONG 8
/* The normal alignment of `size_t', in bytes. */
#define ALIGNOF_SIZE_T 8
/* Define to 1 if you have the <arpa/inet.h> header file. */
#define HAVE_ARPA_INET_H 1
/* Define to 1 if you have the `asprintf' function. */
#define HAVE_ASPRINTF 1
/* Define to 1 if you have the `atexit' function. */
#define HAVE_ATEXIT 1
/* Define to 1 if you have the <crt_externs.h> header file. */
#define HAVE_CRT_EXTERNS_H 1
/* Define to 1 if you have the declaration of `AF_INET6', and to 0 if you
don't. */
#define HAVE_DECL_AF_INET6 1
/* Define to 1 if you have the declaration of `AF_UNSPEC', and to 0 if you
don't. */
#define HAVE_DECL_AF_UNSPEC 1
/* Define to 1 if you have the declaration of `HZ', and to 0 if you don't. */
/* #undef HAVE_DECL_HZ */
/* Define to 1 if you have the declaration of `PF_INET6', and to 0 if you
don't. */
#define HAVE_DECL_PF_INET6 1
/* Define to 1 if you have the declaration of `PF_UNSPEC', and to 0 if you
don't. */
#define HAVE_DECL_PF_UNSPEC 1
/* Define to 1 if you have the declaration of `__func__', and to 0 if you
don't. */
#define HAVE_DECL___FUNC__ 1
/* Define to 1 if you have the <dirent.h> header file. */
#define HAVE_DIRENT_H 1
/* Define to 1 if you have the <dlfcn.h> header file. */
#define HAVE_DLFCN_H 1
/* Define to 1 if you have the `execve' function. */
#define HAVE_EXECVE 1
/* Define to 1 if you have the <fcntl.h> header file. */
#define HAVE_FCNTL_H 1
/* Define to 1 if you have the `fork' function. */
#define HAVE_FORK 1
/* Define to 1 if you have the `getpeereid' function. */
#define HAVE_GETPEEREID 1
/* Define to 1 if you have the `getpeerucred' function. */
/* #undef HAVE_GETPEERUCRED */
/* Define to 1 if you have the <grp.h> header file. */
#define HAVE_GRP_H 1
/* Define to 1 if you have the <hostLib.h> header file. */
/* #undef HAVE_HOSTLIB_H */
/* Define to 1 if you have the <ifaddrs.h> header file. */
#define HAVE_IFADDRS_H 1
/* Define to 1 if the system has the type `int16_t'. */
#define HAVE_INT16_T 1
/* Define to 1 if the system has the type `int32_t'. */
#define HAVE_INT32_T 1
/* Define to 1 if the system has the type `int64_t'. */
#define HAVE_INT64_T 1
/* Define to 1 if the system has the type `int8_t'. */
#define HAVE_INT8_T 1
/* Define to 1 if the system has the type `intptr_t'. */
#define HAVE_INTPTR_T 1
/* Define to 1 if you have the <inttypes.h> header file. */
#define HAVE_INTTYPES_H 1
/* Define to 1 if you have the <ioLib.h> header file. */
/* #undef HAVE_IOLIB_H */
/* Define to 1 if you have the <libgen.h> header file. */
#define HAVE_LIBGEN_H 1
/* Define to 1 if you have the <libutil.h> header file. */
/* #undef HAVE_LIBUTIL_H */
/* Define to 1 if you have the <limits.h> header file. */
#define HAVE_LIMITS_H 1
/* Define to 1 if the system has the type `long long'. */
#define HAVE_LONG_LONG 1
/* Define to 1 if you have the <minix/config.h> header file. */
/* #undef HAVE_MINIX_CONFIG_H */
/* Define to 1 if you have the <mntent.h> header file. */
/* #undef HAVE_MNTENT_H */
/* Define to 1 if you have the <netdb.h> header file. */
#define HAVE_NETDB_H 1
/* Define to 1 if you have the <netinet/in.h> header file. */
#define HAVE_NETINET_IN_H 1
/* Define to 1 if you have the <netinet/tcp.h> header file. */
#define HAVE_NETINET_TCP_H 1
/* Define to 1 if you have the <net/if.h> header file. */
#define HAVE_NET_IF_H 1
/* Define to 1 if you have the <net/uio.h> header file. */
/* #undef HAVE_NET_UIO_H */
/* Define to 1 if you have the `openpty' function. */
#define HAVE_OPENPTY 1
/* Define to 1 if you have the `posix_fallocate' function. */
/* #undef HAVE_POSIX_FALLOCATE */
/* Define to 1 if you have the `pthread_setaffinity_np' function. */
/* #undef HAVE_PTHREAD_SETAFFINITY_NP */
/* Define to 1 if the system has the type `ptrdiff_t'. */
#define HAVE_PTRDIFF_T 1
/* Define to 1 if you have the `ptsname' function. */
#define HAVE_PTSNAME 1
/* Define to 1 if you have the <pty.h> header file. */
/* #undef HAVE_PTY_H */
/* Define to 1 if you have the `setenv' function. */
#define HAVE_SETENV 1
/* Define to 1 if you have the `setpgid' function. */
#define HAVE_SETPGID 1
/* Define to 1 if `si_band' is a member of `siginfo_t'. */
#define HAVE_SIGINFO_T_SI_BAND 1
/* Define to 1 if `si_fd' is a member of `siginfo_t'. */
/* #undef HAVE_SIGINFO_T_SI_FD */
/* Define to 1 if you have the <signal.h> header file. */
#define HAVE_SIGNAL_H 1
/* Define to 1 if you have the `snprintf' function. */
#define HAVE_SNPRINTF 1
/* Define to 1 if you have the `socketpair' function. */
#define HAVE_SOCKETPAIR 1
/* Define to 1 if the system has the type `socklen_t'. */
#define HAVE_SOCKLEN_T 1
/* Define to 1 if you have the <sockLib.h> header file. */
/* #undef HAVE_SOCKLIB_H */
/* Define to 1 if you have the `statfs' function. */
#define HAVE_STATFS 1
/* Define to 1 if you have the `statvfs' function. */
#define HAVE_STATVFS 1
/* Define to 1 if you have the <stdarg.h> header file. */
#define HAVE_STDARG_H 1
/* Define to 1 if you have the <stdatomic.h> header file. */
#define HAVE_STDATOMIC_H 1
/* Define to 1 if you have the <stdbool.h> header file. */
#define HAVE_STDBOOL_H 1
/* Define to 1 if you have the <stddef.h> header file. */
#define HAVE_STDDEF_H 1
/* Define to 1 if you have the <stdint.h> header file. */
#define HAVE_STDINT_H 1
/* Define to 1 if you have the <stdio.h> header file. */
#define HAVE_STDIO_H 1
/* Define to 1 if you have the <stdlib.h> header file. */
#define HAVE_STDLIB_H 1
/* Define to 1 if you have the <strings.h> header file. */
#define HAVE_STRINGS_H 1
/* Define to 1 if you have the <string.h> header file. */
#define HAVE_STRING_H 1
/* Define to 1 if you have the `strncpy_s' function. */
/* #undef HAVE_STRNCPY_S */
/* Define to 1 if you have the `strnlen' function. */
#define HAVE_STRNLEN 1
/* Define to 1 if you have the <stropts.h> header file. */
/* #undef HAVE_STROPTS_H */
/* Define to 1 if you have the `strsignal' function. */
#define HAVE_STRSIGNAL 1
/* Define to 1 if `d_type' is a member of `struct dirent'. */
#define HAVE_STRUCT_DIRENT_D_TYPE 1
/* Define to 1 if `ifr_hwaddr' is a member of `struct ifreq'. */
/* #undef HAVE_STRUCT_IFREQ_IFR_HWADDR */
/* Define to 1 if `ifr_mtu' is a member of `struct ifreq'. */
/* #undef HAVE_STRUCT_IFREQ_IFR_MTU */
/* Define to 1 if the system has the type `struct sockaddr_in'. */
#define HAVE_STRUCT_SOCKADDR_IN 1
/* Define to 1 if the system has the type `struct sockaddr_in6'. */
#define HAVE_STRUCT_SOCKADDR_IN6 1
/* Define to 1 if `sa_len' is a member of `struct sockaddr'. */
#define HAVE_STRUCT_SOCKADDR_SA_LEN 1
/* Define to 1 if the system has the type `struct sockaddr_storage'. */
#define HAVE_STRUCT_SOCKADDR_STORAGE 1
/* Define to 1 if the system has the type `struct sockaddr_un'. */
#define HAVE_STRUCT_SOCKADDR_UN 1
/* Define to 1 if `uid' is a member of `struct sockpeercred'. */
/* #undef HAVE_STRUCT_SOCKPEERCRED_UID */
/* Define to 1 if `f_fstypename' is a member of `struct statfs'. */
#define HAVE_STRUCT_STATFS_F_FSTYPENAME 1
/* Define to 1 if `f_type' is a member of `struct statfs'. */
/* #undef HAVE_STRUCT_STATFS_F_TYPE */
/* Define to 1 if `f_basetype' is a member of `struct statvfs'. */
/* #undef HAVE_STRUCT_STATVFS_F_BASETYPE */
/* Define to 1 if `f_fstypename' is a member of `struct statvfs'. */
/* #undef HAVE_STRUCT_STATVFS_F_FSTYPENAME */
/* Define to 1 if `cr_uid' is a member of `struct ucred'. */
/* #undef HAVE_STRUCT_UCRED_CR_UID */
/* Define to 1 if `uid' is a member of `struct ucred'. */
/* #undef HAVE_STRUCT_UCRED_UID */
/* Define to 1 if you have the <syslog.h> header file. */
#define HAVE_SYSLOG_H 1
/* Define to 1 if you have the <sys/auxv.h> header file. */
/* #undef HAVE_SYS_AUXV_H */
/* Define to 1 if you have the <sys/cdefs.h> header file. */
#define HAVE_SYS_CDEFS_H 1
/* Define to 1 if you have the <sys/fcntl.h> header file. */
#define HAVE_SYS_FCNTL_H 1
/* Define to 1 if you have the <sys/ioctl.h> header file. */
#define HAVE_SYS_IOCTL_H 1
/* Define to 1 if you have the <sys/mount.h> header file. */
#define HAVE_SYS_MOUNT_H 1
/* Define to 1 if you have the <sys/param.h> header file. */
#define HAVE_SYS_PARAM_H 1
/* Define to 1 if you have the <sys/select.h> header file. */
#define HAVE_SYS_SELECT_H 1
/* Define to 1 if you have the <sys/socket.h> header file. */
#define HAVE_SYS_SOCKET_H 1
/* Define to 1 if you have the <sys/sockio.h> header file. */
#define HAVE_SYS_SOCKIO_H 1
/* Define to 1 if you have the <sys/statfs.h> header file. */
/* #undef HAVE_SYS_STATFS_H */
/* Define to 1 if you have the <sys/statvfs.h> header file. */
#define HAVE_SYS_STATVFS_H 1
/* Define to 1 if you have the <sys/stat.h> header file. */
#define HAVE_SYS_STAT_H 1
/* Define to 1 if you have the <sys/sysctl.h> header file. */
#define HAVE_SYS_SYSCTL_H 1
/* Define to 1 if you have the <sys/time.h> header file. */
#define HAVE_SYS_TIME_H 1
/* Define to 1 if you have the <sys/types.h> header file. */
#define HAVE_SYS_TYPES_H 1
/* Define to 1 if you have the <sys/uio.h> header file. */
#define HAVE_SYS_UIO_H 1
/* Define to 1 if you have the <sys/un.h> header file. */
#define HAVE_SYS_UN_H 1
/* Define to 1 if you have the <sys/utsname.h> header file. */
#define HAVE_SYS_UTSNAME_H 1
/* Define to 1 if you have the <sys/wait.h> header file. */
#define HAVE_SYS_WAIT_H 1
/* Define to 1 if you have the `tcgetpgrp' function. */
#define HAVE_TCGETPGRP 1
/* Define to 1 if you have the <termios.h> header file. */
#define HAVE_TERMIOS_H 1
/* Define to 1 if you have the <termio.h> header file. */
/* #undef HAVE_TERMIO_H */
/* Define to 1 if you have the <time.h> header file. */
#define HAVE_TIME_H 1
/* Define to 1 if you have the <ucred.h> header file. */
/* #undef HAVE_UCRED_H */
/* Define to 1 if the system has the type `uint128_t'. */
/* #undef HAVE_UINT128_T */
/* Define to 1 if the system has the type `uint16_t'. */
#define HAVE_UINT16_T 1
/* Define to 1 if the system has the type `uint32_t'. */
#define HAVE_UINT32_T 1
/* Define to 1 if the system has the type `uint64_t'. */
#define HAVE_UINT64_T 1
/* Define to 1 if the system has the type `uint8_t'. */
#define HAVE_UINT8_T 1
/* Define to 1 if the system has the type `uintptr_t'. */
#define HAVE_UINTPTR_T 1
/* Define to 1 if you have the <unistd.h> header file. */
#define HAVE_UNISTD_H 1
/* whether unix byteswap routines -- htonl, htons, nothl, ntohs -- are
available */
#define HAVE_UNIX_BYTESWAP 1
/* Define to 1 if you have the `usleep' function. */
#define HAVE_USLEEP 1
/* Define to 1 if you have the <util.h> header file. */
#define HAVE_UTIL_H 1
/* Define to 1 if you have the <utmp.h> header file. */
#define HAVE_UTMP_H 1
/* Define to 1 if you have the `vasprintf' function. */
#define HAVE_VASPRINTF 1
/* Define to 1 if you have the `vsnprintf' function. */
#define HAVE_VSNPRINTF 1
/* Define to 1 if you have the `waitpid' function. */
#define HAVE_WAITPID 1
/* Define to 1 if you have the <wchar.h> header file. */
#define HAVE_WCHAR_H 1
/* Define to 1 if the system has the type `__int128'. */
#define HAVE___INT128 1
/* Define to the sub-directory where libtool stores uninstalled libraries. */
#define LT_OBJDIR ".libs/"
/* Whether or not we have apple */
#define OAC_HAVE_APPLE 1
/* Whether or not we have solaris */
#define OAC_HAVE_SOLARIS 0
/* Define to the address where bug reports for this package should be sent. */
#define PACKAGE_BUGREPORT "https://github.com/openpmix/openpmix/issues"
/* Define to the full name of this package. */
#define PACKAGE_NAME "pmix"
/* Define to the full name and version of this package. */
#define PACKAGE_STRING "pmix 5.0.5"
/* Define to the one symbol short name of this package. */
#define PACKAGE_TARNAME "pmix"
/* Define to the home page for this package. */
#define PACKAGE_URL ""
/* Define to the version of this package. */
#define PACKAGE_VERSION "5.0.5"
/* The compiler $lower which OMPI was built with */
#define PMIX_BUILD_PLATFORM_COMPILER_FAMILYID 0
/* The compiler $lower which OMPI was built with */
#define PMIX_BUILD_PLATFORM_COMPILER_VERSION 0
/* PMIx underlying C compiler */
#define PMIX_CC "gcc"
/* Capture the configure cmd line */
#define PMIX_CONFIGURE_CLI " \'--disable-option-checking\' \'--prefix=/Users/girgis/Documents/code/cpp-thirdparty-src/mpi/openmpi/install/5.0.7\' \'--without-tests-examples\' \'--enable-pmix-binaries\' \'--disable-pmix-backward-compatibility\' \'--disable-visibility\' \'--disable-devel-check\' \'--with-libevent\' \'--disable-libevent-lib-checks\' \'--with-libevent-extra-libs=/Users/girgis/Documents/code/cpp-thirdparty-src/mpi/openmpi/build/5.0.7/3rd-party/libevent-2.1.12-stable-ompi/libevent_core.la /Users/girgis/Documents/code/cpp-thirdparty-src/mpi/openmpi/build/5.0.7/3rd-party/libevent-2.1.12-stable-ompi/libevent_pthreads.la\' \'--disable-hwloc-lib-checks\' \'--with-hwloc-extra-libs=/Users/girgis/Documents/code/cpp-thirdparty-src/mpi/openmpi/build/5.0.7/3rd-party/hwloc-2.7.1/hwloc/libhwloc.la\' \'--with-wrapper-libs=-levent_core -levent_pthreads \' \'--disable-vt\' \'--disable-mpi-cxx\' \'--disable-static\' \'--disable-wrapper-rpath\' \'--disable-wrapper-runpath\' \'--disable-dlopen\' \'--enable-mca-static=allocator,bml,btl-sm,btl-self,coll,common-sm,errmgr,gpr,io,iof,maffinity-first_use,mpool-sm,ns,odls,oob,osc,pls,pml,ras,rcache,rds,rmaps,rmgr,rml,sds,topo\' \'CFLAGS=-O3\' \'CPPFLAGS=-I/Users/girgis/Documents/code/cpp-thirdparty-src/mpi/openmpi/build/5.0.7/3rd-party/libevent-2.1.12-stable-ompi -I/Users/girgis/Documents/code/cpp-thirdparty-src/mpi/openmpi/build/5.0.7/3rd-party/libevent-2.1.12-stable-ompi/include -I/Users/girgis/Documents/code/cpp-thirdparty-src/mpi/openmpi/build/5.0.7/3rd-party/hwloc-2.7.1/include -I/Users/girgis/Documents/code/cpp-thirdparty-src/mpi/openmpi/build/openmpi-5.0.7/3rd-party/hwloc-2.7.1/include\' \'--cache-file=/dev/null\' \'--srcdir=/Users/girgis/Documents/code/cpp-thirdparty-src/mpi/openmpi/build/openmpi-5.0.7/3rd-party/openpmix\'"
/* Date when PMIx was built */
#define PMIX_CONFIGURE_DATE "Wed Mar 19 13:29:30 UTC 2025"
/* Hostname where PMIx was built */
#define PMIX_CONFIGURE_HOST "hera.local"
/* User who built PMIx */
#define PMIX_CONFIGURE_USER "girgis"
/* Whether C compiler supports GCC style inline assembly */
#define PMIX_C_GCC_INLINE_ASSEMBLY 1
/* Whether C compiler supports atomic convenience variables in stdatomic.h */
#define PMIX_C_HAVE_ATOMIC_CONV_VAR 1
/* Whether C compiler supports __builtin_clz */
#define PMIX_C_HAVE_BUILTIN_CLZ 0
/* Whether C compiler supports __builtin_expect */
#define PMIX_C_HAVE_BUILTIN_EXPECT 1
/* Whether C compiler supports __builtin_prefetch */
#define PMIX_C_HAVE_BUILTIN_PREFETCH 0
/* Whether C compiler supports __Atomic keyword */
#define PMIX_C_HAVE__ATOMIC 1
/* Whether C compiler supports __Generic keyword */
#define PMIX_C_HAVE__GENERIC 1
/* Whether C compiler supports _Static_assert keyword */
#define PMIX_C_HAVE__STATIC_ASSERT 1
/* Whether C compiler supports __Thread_local */
#define PMIX_C_HAVE__THREAD_LOCAL 1
/* Whether C compiler supports __thread */
#define PMIX_C_HAVE___THREAD 1
/* Whether we want developer-level debugging code or not */
#define PMIX_ENABLE_DEBUG 0
/* Whether we want to enable dlopen support */
#define PMIX_ENABLE_DLOPEN_SUPPORT 0
/* Enable IPv6 support, but only if the underlying system supports it */
#define PMIX_ENABLE_IPV6 0
/* Whether we should enable thread support within the PMIX code base */
#define PMIX_ENABLE_MULTI_THREADS 1
/* Whether user wants PTY support or not */
#define PMIX_ENABLE_PTY_SUPPORT 1
/* Whether we want developer-level timing support or not */
#define PMIX_ENABLE_TIMING 0
/* If built from a git repo */
/* #undef PMIX_GIT_REPO_BUILD */
/* Whether your compiler has __attribute__ or not */
#define PMIX_HAVE_ATTRIBUTE 1
/* Whether your compiler has __attribute__ aligned or not */
#define PMIX_HAVE_ATTRIBUTE_ALIGNED 1
/* Whether your compiler has __attribute__ always_inline or not */
#define PMIX_HAVE_ATTRIBUTE_ALWAYS_INLINE 1
/* Whether your compiler has __attribute__ cold or not */
#define PMIX_HAVE_ATTRIBUTE_COLD 1
/* Whether your compiler has __attribute__ const or not */
#define PMIX_HAVE_ATTRIBUTE_CONST 1
/* Whether your compiler has __attribute__ deprecated or not */
#define PMIX_HAVE_ATTRIBUTE_DEPRECATED 1
/* Whether your compiler has __attribute__ deprecated with optional argument
*/
#define PMIX_HAVE_ATTRIBUTE_DEPRECATED_ARGUMENT 1
/* Whether your compiler has __attribute__ destructor or not */
#define PMIX_HAVE_ATTRIBUTE_DESTRUCTOR 1
/* Whether your compiler has __attribute__ extension or not */
#define PMIX_HAVE_ATTRIBUTE_EXTENSION 1
/* Whether your compiler has __attribute__ format or not */
#define PMIX_HAVE_ATTRIBUTE_FORMAT 1
/* Whether your compiler has __attribute__ format and it works on function
pointers */
#define PMIX_HAVE_ATTRIBUTE_FORMAT_FUNCPTR 1
/* Whether your compiler has __attribute__ hot or not */
#define PMIX_HAVE_ATTRIBUTE_HOT 1
/* Whether your compiler has __attribute__ malloc or not */
#define PMIX_HAVE_ATTRIBUTE_MALLOC 1
/* Whether your compiler has __attribute__ may_alias or not */
#define PMIX_HAVE_ATTRIBUTE_MAY_ALIAS 1
/* Whether your compiler has __attribute__ nonnull or not */
#define PMIX_HAVE_ATTRIBUTE_NONNULL 1
/* Whether your compiler has __attribute__ noreturn or not */
#define PMIX_HAVE_ATTRIBUTE_NORETURN 1
/* Whether your compiler has __attribute__ noreturn and it works on function
pointers */
#define PMIX_HAVE_ATTRIBUTE_NORETURN_FUNCPTR 1
/* Whether your compiler has __attribute__ no_instrument_function or not */
#define PMIX_HAVE_ATTRIBUTE_NO_INSTRUMENT_FUNCTION 1
/* Whether your compiler has __attribute__ optnone or not */
#define PMIX_HAVE_ATTRIBUTE_OPTNONE 1
/* Whether your compiler has __attribute__ packed or not */
#define PMIX_HAVE_ATTRIBUTE_PACKED 1
/* Whether your compiler has __attribute__ pure or not */
#define PMIX_HAVE_ATTRIBUTE_PURE 1
/* Whether your compiler has __attribute__ sentinel or not */
#define PMIX_HAVE_ATTRIBUTE_SENTINEL 1
/* Whether your compiler has __attribute__ unused or not */
#define PMIX_HAVE_ATTRIBUTE_UNUSED 1
/* Whether your compiler has __attribute__ visibility or not */
#define PMIX_HAVE_ATTRIBUTE_VISIBILITY 1
/* Whether your compiler has __attribute__ warn unused result or not */
#define PMIX_HAVE_ATTRIBUTE_WARN_UNUSED_RESULT 1
/* Whether your compiler has __attribute__ weak alias or not */
#define PMIX_HAVE_ATTRIBUTE_WEAK_ALIAS
/* Whether C11 atomic compare swap is both supported and lock-free on 128-bit
values */
/* #undef PMIX_HAVE_C11_CSWAP_INT128 */
/* whether ceil is found and available */
#define PMIX_HAVE_CEIL 1
/* Whether we have Clang __c11 atomic functions */
#define PMIX_HAVE_CLANG_BUILTIN_ATOMIC_C11_FUNC 1
/* whether clock_gettime is found and available */
#define PMIX_HAVE_CLOCK_GETTIME 1
/* whether dirname is found and available */
#define PMIX_HAVE_DIRNAME 1
/* Whether the __atomic builtin atomic compare swap is both supported and
lock-free on 128-bit values */
#define PMIX_HAVE_GCC_BUILTIN_CSWAP_INT128 1
/* whether gethostbyname is found and available */
#define PMIX_HAVE_GETHOSTBYNAME 1
/* Whether we are building against libev */
#define PMIX_HAVE_LIBEV 0
/* Whether we are building against libevent */
#define PMIX_HAVE_LIBEVENT 1
/* whether openpty is found and available */
#define PMIX_HAVE_OPENPTY 1
/* Whether the PMIX PDL framework is functional or not */
#define PMIX_HAVE_PDL_SUPPORT 0
/* If PTHREADS implementation supports PTHREAD_MUTEX_ERRORCHECK */
#define PMIX_HAVE_PTHREAD_MUTEX_ERRORCHECK 1
/* If PTHREADS implementation supports PTHREAD_MUTEX_ERRORCHECK_NP */
#define PMIX_HAVE_PTHREAD_MUTEX_ERRORCHECK_NP 0
/* Whether we have SA_RESTART in <signal.h> or not */
#define PMIX_HAVE_SA_RESTART 1
/* whether socket is found and available */
#define PMIX_HAVE_SOCKET 1
/* Whether the __sync builtin atomic compare and swap supports 128-bit values
*/
/* #undef PMIX_HAVE_SYNC_BUILTIN_CSWAP_INT128 */
/* Whether we have __va_copy or not */
#define PMIX_HAVE_UNDERSCORE_VA_COPY 1
/* Whether we have va_copy or not */
#define PMIX_HAVE_VA_COPY 1
/* Whether C compiler supports symbol visibility or not */
#define PMIX_HAVE_VISIBILITY 0
/* ident string for PMIX */
#define PMIX_IDENT_STRING ""
/* The library major version is always available, contrary to VERSION */
#define PMIX_MAJOR_VERSION 5
/* Whether or not we are using memory sanitizers */
#define PMIX_MEMORY_SANITIZERS 0
/* The library minor version is always available, contrary to VERSION */
#define PMIX_MINOR_VERSION 0
/* Whether the C compiler supports "bool" without any other help (such as
<stdbool.h>) */
#define PMIX_NEED_C_BOOL 1
/* Whether libraries can be configured with destructor functions */
#define PMIX_NO_LIB_DESTRUCTOR 0
/* package/branding string for PMIx */
#define PMIX_PACKAGE_STRING "PMIx girgis@hera.local Distribution"
/* Whether we have lt_dladvise or not */
#define PMIX_PDL_PLIBLTDL_HAVE_LT_DLADVISE 0
/* Whether or not we are using picky compiler settings */
#define PMIX_PICKY_COMPILERS 0
/* Where to report bugs */
#define PMIX_PROXY_BUGREPORT_STRING "https://github.com/openpmix/openpmix"
/* type to use for ptrdiff_t */
#define PMIX_PTRDIFF_TYPE ptrdiff_t
/* The library release version is always available, contrary to VERSION */
#define PMIX_RELEASE_VERSION 5
/* The OpenPMIx Git Revision */
#define PMIX_REPO_REV "v5.0.5"
/* Default value for mca_base_component_show_load_errors MCA variable */
#define PMIX_SHOW_LOAD_ERRORS_DEFAULT "all"
/* The PMIx Standard Provisional ABI compliance level(s) */
#define PMIX_STD_ABI_PROVISIONAL_VERSION "0.0"
/* The PMIx Standard Stable ABI compliance level(s) */
#define PMIX_STD_ABI_STABLE_VERSION "0.0"
/* The PMIx Standard compliance level */
#define PMIX_STD_VERSION "4.2"
/* Whether to use C11 atomics for atomics implementation */
#define PMIX_USE_C11_ATOMICS 0
/* Whether to use GCC-style built-in atomics for atomics implementation */
#define PMIX_USE_GCC_BUILTIN_ATOMICS 1
/* Whether to use <stdbool.h> or not */
#define PMIX_USE_STDBOOL_H 1
/* The library version is always available, contrary to VERSION */
#define PMIX_VERSION "5.0.5"
/* Enable per-user config files */
#define PMIX_WANT_HOME_CONFIG_FILES 1
/* if want pretty-print stack trace feature */
#define PMIX_WANT_PRETTY_PRINT_STACKTRACE 1
/* The size of `int', as computed by sizeof. */
#define SIZEOF_INT 4
/* The size of `long', as computed by sizeof. */
#define SIZEOF_LONG 8
/* The size of `pid_t', as computed by sizeof. */
#define SIZEOF_PID_T 4
/* The size of `short', as computed by sizeof. */
#define SIZEOF_SHORT 2
/* The size of `size_t', as computed by sizeof. */
#define SIZEOF_SIZE_T 8
/* The size of `void *', as computed by sizeof. */
#define SIZEOF_VOID_P 8
/* The size of `_Bool', as computed by sizeof. */
#define SIZEOF__BOOL 1
/* Define to 1 if all of the C90 standard headers exist (not just the ones
required in a freestanding environment). This macro is provided for
backward compatibility; new code need not use it. */
#define STDC_HEADERS 1
/* Enable extensions on AIX 3, Interix. */
#ifndef _ALL_SOURCE
# define _ALL_SOURCE 1
#endif
/* Enable general extensions on macOS. */
#ifndef _DARWIN_C_SOURCE
# define _DARWIN_C_SOURCE 1
#endif
/* Enable general extensions on Solaris. */
#ifndef __EXTENSIONS__
# define __EXTENSIONS__ 1
#endif
/* Enable GNU extensions on systems that have them. */
#ifndef _GNU_SOURCE
# define _GNU_SOURCE 1
#endif
/* Enable X/Open compliant socket functions that do not require linking
with -lxnet on HP-UX 11.11. */
#ifndef _HPUX_ALT_XOPEN_SOCKET_API
# define _HPUX_ALT_XOPEN_SOCKET_API 1
#endif
/* Identify the host operating system as Minix.
This macro does not affect the system headers' behavior.
A future release of Autoconf may stop defining this macro. */
#ifndef _MINIX
/* # undef _MINIX */
#endif
/* Enable general extensions on NetBSD.
Enable NetBSD compatibility extensions on Minix. */
#ifndef _NETBSD_SOURCE
# define _NETBSD_SOURCE 1
#endif
/* Enable OpenBSD compatibility extensions on NetBSD.
Oddly enough, this does nothing on OpenBSD. */
#ifndef _OPENBSD_SOURCE
# define _OPENBSD_SOURCE 1
#endif
/* Define to 1 if needed for POSIX-compatible behavior. */
#ifndef _POSIX_SOURCE
/* # undef _POSIX_SOURCE */
#endif
/* Define to 2 if needed for POSIX-compatible behavior. */
#ifndef _POSIX_1_SOURCE
/* # undef _POSIX_1_SOURCE */
#endif
/* Enable POSIX-compatible threading on Solaris. */
#ifndef _POSIX_PTHREAD_SEMANTICS
# define _POSIX_PTHREAD_SEMANTICS 1
#endif
/* Enable extensions specified by ISO/IEC TS 18661-5:2014. */
#ifndef __STDC_WANT_IEC_60559_ATTRIBS_EXT__
# define __STDC_WANT_IEC_60559_ATTRIBS_EXT__ 1
#endif
/* Enable extensions specified by ISO/IEC TS 18661-1:2014. */
#ifndef __STDC_WANT_IEC_60559_BFP_EXT__
# define __STDC_WANT_IEC_60559_BFP_EXT__ 1
#endif
/* Enable extensions specified by ISO/IEC TS 18661-2:2015. */
#ifndef __STDC_WANT_IEC_60559_DFP_EXT__
# define __STDC_WANT_IEC_60559_DFP_EXT__ 1
#endif
/* Enable extensions specified by ISO/IEC TS 18661-4:2015. */
#ifndef __STDC_WANT_IEC_60559_FUNCS_EXT__
# define __STDC_WANT_IEC_60559_FUNCS_EXT__ 1
#endif
/* Enable extensions specified by ISO/IEC TS 18661-3:2015. */
#ifndef __STDC_WANT_IEC_60559_TYPES_EXT__
# define __STDC_WANT_IEC_60559_TYPES_EXT__ 1
#endif
/* Enable extensions specified by ISO/IEC TR 24731-2:2010. */
#ifndef __STDC_WANT_LIB_EXT2__
# define __STDC_WANT_LIB_EXT2__ 1
#endif
/* Enable extensions specified by ISO/IEC 24747:2009. */
#ifndef __STDC_WANT_MATH_SPEC_FUNCS__
# define __STDC_WANT_MATH_SPEC_FUNCS__ 1
#endif
/* Enable extensions on HP NonStop. */
#ifndef _TANDEM_SOURCE
# define _TANDEM_SOURCE 1
#endif
/* Enable X/Open extensions. Define to 500 only if necessary
to make mbstate_t available. */
#ifndef _XOPEN_SOURCE
/* # undef _XOPEN_SOURCE */
#endif
/* Define WORDS_BIGENDIAN to 1 if your processor stores words with the most
significant byte first (like Motorola and SPARC, unlike Intel). */
#if defined AC_APPLE_UNIVERSAL_BUILD
# if defined __BIG_ENDIAN__
# define WORDS_BIGENDIAN 1
# endif
#else
# ifndef WORDS_BIGENDIAN
/* # undef WORDS_BIGENDIAN */
# endif
#endif
/* Define to 1 if `lex' declares `yytext' as a `char *' by default, not a
`char[]'. */
#define YYTEXT_POINTER 1
/* Enable GNU extensions on systems that have them. */
#ifndef _GNU_SOURCE
# define _GNU_SOURCE 1
#endif
/* Define to `__inline__' or `__inline' if that's what the C compiler
calls it, or to nothing if 'inline' is not supported under any name. */
#ifndef __cplusplus
#define inline __inline__
#endif
#include "src/include/pmix_config_bottom.h"
#endif /* PMIX_CONFIG_H */

View File

@@ -0,0 +1,570 @@
/*
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2005 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2010 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2009 Sun Microsystems, Inc. All rights reserved.
* Copyright (c) 2009-2011 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2013 Mellanox Technologies, Inc.
* All rights reserved.
* Copyright (c) 2013-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2016 IBM Corporation. All rights reserved.
* Copyright (c) 2021-2024 Nanook Consulting All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*
*/
#ifndef PMIX_CONFIG_BOTTOM_H
#define PMIX_CONFIG_BOTTOM_H
/*
* If we build a static library, Visual C define the _LIB symbol. In the
* case of a shared library _USERDLL get defined.
*
*/
#ifndef PMIX_BUILDING
# define PMIX_BUILDING 1
#endif
/*
* Flex is trying to include the unistd.h file. As there is no configure
* option or this, the flex generated files will try to include the file
* even on platforms without unistd.h. Therefore, if we
* know this file is not available, we can prevent flex from including it.
*/
#ifndef HAVE_UNISTD_H
# define YY_NO_UNISTD_H
#endif
/***********************************************************************
*
* code that should be in ompi_config_bottom.h regardless of build
* status
*
**********************************************************************/
/* Do we have posix or solaris thread lib */
#define PMIX_HAVE_THREADS (PMIX_HAVE_POSIX_THREADS || OAC_HAVE_SOLARIS_THREADS)
/*
* BEGIN_C_DECLS should be used at the beginning of your declarations,
* so that C++ compilers don't mangle their names. Use END_C_DECLS at
* the end of C declarations.
*/
#undef BEGIN_C_DECLS
#undef END_C_DECLS
#if defined(c_plusplus) || defined(__cplusplus)
# define BEGIN_C_DECLS extern "C" {
# define END_C_DECLS }
#else
# define BEGIN_C_DECLS /* empty */
# define END_C_DECLS /* empty */
#endif
/* Defined to 1 on Linux */
#undef PMIX_LINUX_SYS
/* Defined to 1 if the CPU_SET macro works */
#undef PMIX_HAVE_CPU_SET
/* Defined to 1 if you have the `windows.h' header. */
#undef PMIX_HAVE_WINDOWS_H
#undef pmix_pid_t
#undef pmix_thread_t
/*
* Note: this is public. We can not assume anything from the compiler used
* by the application and thus the PMIX_HAVE_* macros below are not
* fetched from the autoconf result here. We only automatically use a few
* well-known easy cases.
*/
/* Some handy constants to make the logic below a little more readable */
#if defined(__cplusplus) && (__GNUC__ > 3 || (__GNUC__ == 3 && __GNUC_MINOR >= 4))
# define GXX_ABOVE_3_4 1
#else
# define GXX_ABOVE_3_4 0
#endif
#if !defined(__cplusplus) && (__GNUC__ > 2 || (__GNUC__ == 2 && __GNUC_MINOR__ >= 95))
# define GCC_ABOVE_2_95 1
#else
# define GCC_ABOVE_2_95 0
#endif
#if !defined(__cplusplus) && (__GNUC__ > 2 || (__GNUC__ == 2 && __GNUC_MINOR__ >= 96))
# define GCC_ABOVE_2_96 1
#else
# define GCC_ABOVE_2_96 0
#endif
#if !defined(__cplusplus) && (__GNUC__ > 3 || (__GNUC__ == 3 && __GNUC_MINOR__ >= 3))
# define GCC_ABOVE_3_3 1
#else
# define GCC_ABOVE_3_3 0
#endif
/**
* The attribute definition should be included before any potential
* usage.
*/
#if PMIX_HAVE_ATTRIBUTE_ALIGNED
# define __pmix_attribute_aligned__(a) __attribute__((__aligned__(a)))
# define __pmix_attribute_aligned_max__ __attribute__((__aligned__))
#else
# define __pmix_attribute_aligned__(a)
# define __pmix_attribute_aligned_max__
#endif
/* Note that if we're compiling C++, then just use the "inline"
keyword, since it's part of C++ */
#if defined(c_plusplus) || defined(__cplusplus)
# define __pmix_inline inline
#elif defined(_MSC_VER) || defined(__HP_cc)
# define __pmix_inline __inline
#else
# define __pmix_inline __inline__
#endif
#if PMIX_HAVE_ATTRIBUTE_ALWAYS_INLINE
# define __pmix_attribute_always_inline__ __attribute__((__always_inline__))
#else
# define __pmix_attribute_always_inline__
#endif
#if PMIX_HAVE_ATTRIBUTE_COLD
# define __pmix_attribute_cold__ __attribute__((__cold__))
#else
# define __pmix_attribute_cold__
#endif
#ifdef PMIX_HAVE_ATTRIBUTE_CONST
# define __PMIX_HAVE_ATTRIBUTE_CONST PMIX_HAVE_ATTRIBUTE_CONST
#elif defined(__GNUC__)
# define __PMIX_HAVE_ATTRIBUTE_CONST (GXX_ABOVE_3_4 || GCC_ABOVE_2_95)
#else
# define __PMIX_HAVE_ATTRIBUTE_CONST 0
#endif
#if __PMIX_HAVE_ATTRIBUTE_CONST
# define __pmix_attribute_const __attribute__((__const__))
#else
# define __pmix_attribute_const
#endif
#if PMIX_HAVE_ATTRIBUTE_CONST
# define __pmix_attribute_const__ __attribute__((__const__))
#else
# define __pmix_attribute_const__
#endif
#ifdef PMIX_HAVE_ATTRIBUTE_DEPRECATED
# define __PMIX_HAVE_ATTRIBUTE_DEPRECATED PMIX_HAVE_ATTRIBUTE_DEPRECATED
#elif defined(__GNUC__)
# define __PMIX_HAVE_ATTRIBUTE_DEPRECATED (GXX_ABOVE_3_4 || GCC_ABOVE_3_3)
#else
# define __PMIX_HAVE_ATTRIBUTE_DEPRECATED 0
#endif
#if __PMIX_HAVE_ATTRIBUTE_DEPRECATED
# define __pmix_attribute_deprecated __attribute__((__deprecated__))
#else
# define __pmix_attribute_deprecated
#endif
#if PMIX_HAVE_ATTRIBUTE_DEPRECATED
# define __pmix_attribute_deprecated__ __attribute__((__deprecated__))
#else
# define __pmix_attribute_deprecated__
#endif
#if PMIX_HAVE_ATTRIBUTE_FORMAT
#if OAC_HAVE_SOLARIS
# define __pmix_attribute_format__(a, b, c)
#else
# define __pmix_attribute_format__(a, b, c) __attribute__((__format__(a, b, c)))
#endif
#else
# define __pmix_attribute_format__(a, b, c)
#endif
/* Use this __atribute__ on function-ptr declarations, only */
#if PMIX_HAVE_ATTRIBUTE_FORMAT_FUNCPTR
# define __pmix_attribute_format_funcptr__(a, b, c) __attribute__((__format__(a, b, c)))
#else
# define __pmix_attribute_format_funcptr__(a, b, c)
#endif
#if PMIX_HAVE_ATTRIBUTE_HOT
# define __pmix_attribute_hot__ __attribute__((__hot__))
#else
# define __pmix_attribute_hot__
#endif
#ifdef PMIX_HAVE_ATTRIBUTE_MALLOC
# define __PMIX_HAVE_ATTRIBUTE_MALLOC PMIX_HAVE_ATTRIBUTE_MALLOC
#elif defined(__GNUC__)
# define __PMIX_HAVE_ATTRIBUTE_MALLOC (GXX_ABOVE_3_4 || GCC_ABOVE_2_96)
#else
# define __PMIX_HAVE_ATTRIBUTE_MALLOC 0
#endif
#if __PMIX_HAVE_ATTRIBUTE_MALLOC
# define __pmix_attribute_malloc __attribute__((__malloc__))
#else
# define __pmix_attribute_malloc
#endif
#if PMIX_HAVE_ATTRIBUTE_MALLOC
# define __pmix_attribute_malloc__ __attribute__((__malloc__))
#else
# define __pmix_attribute_malloc__
#endif
#ifdef PMIX_HAVE_ATTRIBUTE_MAY_ALIAS
# define __PMIX_HAVE_ATTRIBUTE_MAY_ALIAS PMIX_HAVE_ATTRIBUTE_MAY_ALIAS
#elif defined(__GNUC__)
# define __PMIX_HAVE_ATTRIBUTE_MAY_ALIAS (GXX_ABOVE_3_4 || GCC_ABOVE_3_3)
#else
# define __PMIX_HAVE_ATTRIBUTE_MAY_ALIAS 0
#endif
#if __PMIX_HAVE_ATTRIBUTE_MAY_ALIAS
# define __pmix_attribute_may_alias __attribute__((__may_alias__))
#else
# define __pmix_attribute_may_alias
#endif
#if PMIX_HAVE_ATTRIBUTE_MAY_ALIAS
# define __pmix_attribute_may_alias__ __attribute__((__may_alias__))
#else
# define __pmix_attribute_may_alias__
#endif
#if PMIX_HAVE_ATTRIBUTE_NO_INSTRUMENT_FUNCTION
# define __pmix_attribute_no_instrument_function__ __attribute__((__no_instrument_function__))
#else
# define __pmix_attribute_no_instrument_function__
#endif
#if PMIX_HAVE_ATTRIBUTE_NONNULL
# define __pmix_attribute_nonnull__(a) __attribute__((__nonnull__(a)))
# define __pmix_attribute_nonnull_all__ __attribute__((__nonnull__))
#else
# define __pmix_attribute_nonnull__(a)
# define __pmix_attribute_nonnull_all__
#endif
#if PMIX_HAVE_ATTRIBUTE_NORETURN
# define __pmix_attribute_noreturn__ __attribute__((__noreturn__))
#else
# define __pmix_attribute_noreturn__
#endif
/* Use this __atribute__ on function-ptr declarations, only */
#if PMIX_HAVE_ATTRIBUTE_NORETURN_FUNCPTR
# define __pmix_attribute_noreturn_funcptr__ __attribute__((__noreturn__))
#else
# define __pmix_attribute_noreturn_funcptr__
#endif
#if PMIX_HAVE_ATTRIBUTE_PACKED
# define __pmix_attribute_packed__ __attribute__((__packed__))
#else
# define __pmix_attribute_packed__
#endif
#ifdef PMIX_HAVE_ATTRIBUTE_PURE
# define __PMIX_HAVE_ATTRIBUTE_PURE PMIX_HAVE_ATTRIBUTE_PURE
#elif defined(__GNUC__)
# define __PMIX_HAVE_ATTRIBUTE_PURE (GXX_ABOVE_3_4 || GCC_ABOVE_2_96)
#else
# define __PMIX_HAVE_ATTRIBUTE_PURE 0
#endif
#if __PMIX_HAVE_ATTRIBUTE_PURE
# define __pmix_attribute_pure __attribute__((__pure__))
#else
# define __pmix_attribute_pure
#endif
#if PMIX_HAVE_ATTRIBUTE_PURE
# define __pmix_attribute_pure__ __attribute__((__pure__))
#else
# define __pmix_attribute_pure__
#endif
#if PMIX_HAVE_ATTRIBUTE_SENTINEL
#if OAC_HAVE_SOLARIS
# define __pmix_attribute_sentinel__
#else
# define __pmix_attribute_sentinel__ __attribute__((__sentinel__))
#endif
#else
# define __pmix_attribute_sentinel__
#endif
/* Maybe before gcc 2.95 too */
#ifdef PMIX_HAVE_ATTRIBUTE_UNUSED
# define __PMIX_HAVE_ATTRIBUTE_UNUSED PMIX_HAVE_ATTRIBUTE_UNUSED
#elif defined(__GNUC__)
# define __PMIX_HAVE_ATTRIBUTE_UNUSED (GXX_ABOVE_3_4 || GCC_ABOVE_2_95)
#else
# define __PMIX_HAVE_ATTRIBUTE_UNUSED 0
#endif
#if __PMIX_HAVE_ATTRIBUTE_UNUSED
# define __pmix_attribute_unused __attribute__((__unused__))
#else
# define __pmix_attribute_unused
#endif
#if PMIX_HAVE_ATTRIBUTE_UNUSED
# define __pmix_attribute_unused__ __attribute__((__unused__))
#else
# define __pmix_attribute_unused__
#endif
#if PMIX_HAVE_ATTRIBUTE_WARN_UNUSED_RESULT
# define __pmix_attribute_warn_unused_result__ __attribute__((__warn_unused_result__))
#else
# define __pmix_attribute_warn_unused_result__
#endif
#if PMIX_HAVE_ATTRIBUTE_DESTRUCTOR
# define __pmix_attribute_destructor__ __attribute__((__destructor__))
#else
# define __pmix_attribute_destructor__
#endif
#if PMIX_HAVE_ATTRIBUTE_OPTNONE
# define __pmix_attribute_optnone__ __attribute__((__optnone__))
#else
# define __pmix_attribute_optnone__
#endif
#if PMIX_HAVE_ATTRIBUTE_EXTENSION
# define __pmix_attribute_extension__ __extension__
#else
# define __pmix_attribute_extension__
#endif
/*
* Do we have <stdint.h>?
*/
#ifdef HAVE_STDINT_H
# if !defined(__STDC_LIMIT_MACROS) && (defined(c_plusplus) || defined(__cplusplus))
/* When using a C++ compiler, the max / min value #defines for std
types are only included if __STDC_LIMIT_MACROS is set before
including stdint.h */
# define __STDC_LIMIT_MACROS
# endif
# include "src/include/pmix_config.h"
# include <stdint.h>
#else
# include "src/include/pmix_stdint.h"
#endif
/***********************************************************************
*
* Code that is only for when building PMIx or utilities that are
* using the internals of PMIx. It should not be included when
* building MPI applications
*
**********************************************************************/
#if PMIX_BUILDING
# ifndef HAVE_PTRDIFF_T
typedef PMIX_PTRDIFF_TYPE ptrdiff_t;
# endif
/*
* Maximum size of a filename path.
*/
# include <limits.h>
# ifdef HAVE_SYS_PARAM_H
# include <sys/param.h>
# endif
# if defined(PATH_MAX)
# define PMIX_PATH_MAX (PATH_MAX + 1)
# elif defined(_POSIX_PATH_MAX)
# define PMIX_PATH_MAX (_POSIX_PATH_MAX + 1)
# else
# define PMIX_PATH_MAX 256
# endif
# if defined(MAXHOSTNAMELEN)
# define PMIX_MAXHOSTNAMELEN (MAXHOSTNAMELEN + 1)
# elif defined(HOST_NAME_MAX)
# define PMIX_MAXHOSTNAMELEN (HOST_NAME_MAX + 1)
# else
/* SUSv2 guarantees that "Host names are limited to 255 bytes". */
# define PMIX_MAXHOSTNAMELEN (255 + 1)
# endif
/*
* Set the compile-time path-separator on this system and variable separator
*/
# define PMIX_PATH_SEP "/"
# define PMIX_ENV_SEP ':'
/*
* printf functions for portability (only when building PMIx)
*/
# if !defined(HAVE_VASPRINTF) || !defined(HAVE_VSNPRINTF)
# include <stdarg.h>
# include <stdlib.h>
# endif
# if !defined(HAVE_ASPRINTF) || !defined(HAVE_SNPRINTF) || !defined(HAVE_VASPRINTF) \
|| !defined(HAVE_VSNPRINTF)
# include "src/util/pmix_printf.h"
# endif
# ifndef HAVE_ASPRINTF
# define asprintf pmix_asprintf
# endif
# ifndef HAVE_SNPRINTF
# define snprintf pmix_snprintf
# endif
# ifndef HAVE_VASPRINTF
# define vasprintf pmix_vasprintf
# endif
# ifndef HAVE_VSNPRINTF
# define vsnprintf pmix_vsnprintf
# endif
/*
* Define __func__-preprocessor directive if the compiler does not
* already define it. Define it to __FILE__ so that we at least have
* a clue where the developer is trying to indicate where the error is
* coming from (assuming that __func__ is typically used for
* printf-style debugging).
*/
# if defined(HAVE_DECL___FUNC__) && !HAVE_DECL___FUNC__
# define __func__ __FILE__
# endif
# define IOVBASE_TYPE void
# include <stdbool.h>
/**
* If we generate our own bool type, we need a special way to cast the result
* in such a way to keep the compilers silent.
*/
# define PMIX_INT_TO_BOOL(VALUE) (bool) (VALUE)
# if !defined(HAVE_STRUCT_SOCKADDR_STORAGE) && defined(HAVE_STRUCT_SOCKADDR_IN)
# define sockaddr_storage sockaddr
# define ss_family sa_family
# endif
/* Compatibility structure so that we don't have to have as many
#if checks in the code base */
# if !defined(HAVE_STRUCT_SOCKADDR_IN6) && defined(HAVE_STRUCT_SOCKADDR_IN)
# define sockaddr_in6 sockaddr_in
# define sin6_len sin_len
# define sin6_family sin_family
# define sin6_port sin_port
# define sin6_addr sin_addr
# endif
# if !HAVE_DECL_AF_UNSPEC
# define AF_UNSPEC 0
# endif
# if !HAVE_DECL_PF_UNSPEC
# define PF_UNSPEC 0
# endif
# if !HAVE_DECL_AF_INET6
# define AF_INET6 AF_UNSPEC
# endif
# if !HAVE_DECL_PF_INET6
# define PF_INET6 PF_UNSPEC
# endif
# if defined(__APPLE__) && defined(HAVE_INTTYPES_H)
/* Prior to Mac OS X 10.3, the length modifier "ll" wasn't
supported, but "q" was for long long. This isn't ANSI
C and causes a warning when using PRI?64 macros. We
don't support versions prior to OS X 10.3, so we don't
need such backward compatibility. Instead, redefine
the macros to be "ll", which is ANSI C and doesn't
cause a compiler warning. */
# include <inttypes.h>
# if defined(__PRI_64_LENGTH_MODIFIER__)
# undef __PRI_64_LENGTH_MODIFIER__
# define __PRI_64_LENGTH_MODIFIER__ "ll"
# endif
# if defined(__SCN_64_LENGTH_MODIFIER__)
# undef __SCN_64_LENGTH_MODIFIER__
# define __SCN_64_LENGTH_MODIFIER__ "ll"
# endif
# endif
# ifdef MCS_VXWORKS
/* VXWorks puts some common functions in oddly named headers. Rather
than update all the places the functions are used, which would be a
maintenance disatster, just update here... */
# ifdef HAVE_IOLIB_H
/* pipe(), ioctl() */
# include <ioLib.h>
# endif
# ifdef HAVE_SOCKLIB_H
/* socket() */
# include <sockLib.h>
# endif
# ifdef HAVE_HOSTLIB_H
/* gethostname() */
# include <hostLib.h>
# endif
# endif
/* If we're in C++, then just undefine restrict and then define it to
nothing. "restrict" is not part of the C++ language, and we don't
have a corresponding AC_CXX_RESTRICT to figure out what the C++
compiler supports. */
# if defined(c_plusplus) || defined(__cplusplus)
# undef restrict
# define restrict
# endif
# if (__GNUC__ > 2 || (__GNUC__ == 2 && __GNUC_MINOR__ >= 95))
# define __pmix_restrict __restrict
# else
# if __STDC_VERSION__ >= 199901L
# define __pmix_restrict restrict
# else
# define __pmix_restrict
# endif
# endif
#else
/* For a similar reason to what is listed in pmix_config_top.h, we
want to protect others from the autoconf/automake-generated
PACKAGE_<foo> macros in pmix_config.h. We can't put these undef's
directly in pmix_config.h because they'll be turned into #defines'
via autoconf.
So put them here in case any one else includes PMIX's
config.h files. */
# undef PACKAGE_BUGREPORT
# undef PACKAGE_NAME
# undef PACKAGE_STRING
# undef PACKAGE_TARNAME
# undef PACKAGE_VERSION
# undef PACKAGE_URL
# undef HAVE_CONFIG_H
#endif /* PMIX_BUILDING */
#endif /* PMIX_CONFIG_BOTTOM_H */

View File

@@ -0,0 +1,41 @@
/*
* Copyright (c) 2011 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2013-2015 Intel, Inc. All rights reserved
* Copyright (c) 2016 IBM Corporation. All rights reserved.
* Copyright (c) 2021 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*
* This file is included at the top of pmix_config.h, and is
* therefore a) before all the #define's that were output from
* configure, and b) included in most/all files in PMIx.
*
* Since this file is *only* ever included by pmix_config.h, and
* pmix_config.h already has #ifndef/#endif protection, there is no
* need to #ifndef/#endif protection here.
*/
#ifndef PMIX_CONFIG_H
# error "pmix_config_top.h should only be included from config.h(.in)"
#endif
/* The only purpose of this file is to undef the PACKAGE_<foo> macros
that are put in by autoconf/automake projects. Specifically, if
you include a .h file from another project that defines these
macros (e.g., gmp.h) and then include PMIX's config.h,
you'll get a preprocessor conflict. So put these undef's here to
protect us from other package's PACKAGE_<foo> macros.
Note that we can't put them directly in pmix_config.h (e.g., via
AH_TOP) because they will be turned into #define's by autoconf. */
#undef PACKAGE_BUGREPORT
#undef PACKAGE_NAME
#undef PACKAGE_STRING
#undef PACKAGE_TARNAME
#undef PACKAGE_VERSION
#undef PACKAGE_URL
#undef HAVE_CONFIG_H

View File

@@ -0,0 +1,22 @@
/*
* This file is autogenerated by construct_dictionary.py.
* Do not edit this file by hand.
*/
#include "src/include/pmix_config.h"
#include "src/include/pmix_globals.h"
#include "include/pmix_common.h"
#ifndef PMIX_DICTIONARY_H
#define PMIX_DICTIONARY_H
BEGIN_C_DECLS
PMIX_EXPORT extern const pmix_regattr_input_t pmix_dictionary[564];
#define PMIX_INDEX_BOUNDARY 564
END_C_DECLS
#endif

View File

@@ -0,0 +1,22 @@
/*
* This file is autogenerated by construct_event_strings.py.
* Do not edit this file by hand.
*/
#include "src/include/pmix_config.h"
#include "src/include/pmix_globals.h"
#include "include/pmix_common.h"
#ifndef PMIX_EVENT_STRINGS_H
#define PMIX_EVENT_STRINGS_H
BEGIN_C_DECLS
PMIX_EXPORT extern const pmix_event_string_t pmix_event_strings[163];
#define PMIX_EVENT_INDEX_BOUNDARY 162
END_C_DECLS
#endif

View File

@@ -0,0 +1,31 @@
/*
* This file is autogenerated by autogen.pl. Do not edit this file by hand.
*/
#ifndef PMIX_FRAMEWORKS_H
#define PMIX_FRAMEWORKS_H
#include "src/mca/base/pmix_mca_base_framework.h"
extern pmix_mca_base_framework_t pmix_bfrops_base_framework;
extern pmix_mca_base_framework_t pmix_gds_base_framework;
extern pmix_mca_base_framework_t pmix_pcompress_base_framework;
extern pmix_mca_base_framework_t pmix_pdl_base_framework;
extern pmix_mca_base_framework_t pmix_pif_base_framework;
extern pmix_mca_base_framework_t pmix_pinstalldirs_base_framework;
extern pmix_mca_base_framework_t pmix_plog_base_framework;
extern pmix_mca_base_framework_t pmix_pmdl_base_framework;
extern pmix_mca_base_framework_t pmix_pnet_base_framework;
extern pmix_mca_base_framework_t pmix_preg_base_framework;
extern pmix_mca_base_framework_t pmix_psec_base_framework;
extern pmix_mca_base_framework_t pmix_psensor_base_framework;
extern pmix_mca_base_framework_t pmix_psquash_base_framework;
extern pmix_mca_base_framework_t pmix_pstat_base_framework;
extern pmix_mca_base_framework_t pmix_ptl_base_framework;
PMIX_EXPORT extern pmix_mca_base_framework_t *pmix_frameworks[];
PMIX_EXPORT extern char *pmix_framework_names[];
#endif /* PMIX_FRAMEWORKS_H */

View File

@@ -0,0 +1,923 @@
/* -*- Mode: C; c-basic-offset:4 ; indent-tabs-mode:nil -*- */
/*
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2005 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2014-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2019 Research Organization for Information Science
* and Technology (RIST). All rights reserved.
* Copyright (c) 2019 Mellanox Technologies, Inc.
* All rights reserved.
* Copyright (c) 2021-2024 Nanook Consulting All rights reserved.
* Copyright (c) 2023 Triad National Security, LLC. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
#ifndef PMIX_GLOBALS_H
#define PMIX_GLOBALS_H
#include "src/include/pmix_config.h"
#include "src/include/pmix_types.h"
#include <unistd.h>
#ifdef HAVE_SYS_TYPES_H
# include <sys/types.h>
#endif
#include <event.h>
#include "pmix.h"
#include "pmix_common.h"
#include "pmix_tool.h"
#include "src/class/pmix_hash_table.h"
#include "src/class/pmix_hotel.h"
#include "src/class/pmix_list.h"
#include "src/event/pmix_event.h"
#include "src/runtime/pmix_init_util.h"
#include "src/threads/pmix_threads.h"
#include "src/mca/bfrops/bfrops.h"
#include "src/mca/gds/gds.h"
#include "src/mca/psec/psec.h"
#include "src/mca/ptl/ptl.h"
#include "src/util/pmix_name_fns.h"
BEGIN_C_DECLS
/* some limits */
#define PMIX_MAX_CRED_SIZE 131072 // set max at 128kbytes
#define PMIX_MAX_ERR_CONSTANT INT_MIN
/* internal-only attributes */
#define PMIX_BFROPS_MODULE \
"pmix.bfrops.mod" // (char*) name of bfrops plugin in-use by a given nspace
#define PMIX_PNET_SETUP_APP \
"pmix.pnet.setapp" // (pmix_byte_object_t) blob containing info to be given to
// pnet framework on remote nodes
// define some bit handling macros
#define PMIX_SET_BIT(a, f) \
(a) |= (f)
#define PMIX_UNSET_BIT(a, f) \
(a) &= ~(f)
#define PMIX_CHECK_BIT_IS_SET(a, f) \
((a) & (f))
#define PMIX_CHECK_BIT_NOT_SET(a, f) \
!PMIX_CHECK_BIT_IS_SET(a, f)
#define PMIX_INFO_OP_COMPLETE 0x80000000
#define PMIX_INFO_OP_COMPLETED(m) \
PMIX_SET_BIT((m)->flags, PMIX_INFO_OP_COMPLETE)
#define PMIX_INFO_OP_IS_COMPLETE(m) \
PMIX_CHECK_BIT_IS_SET((m)->flags, PMIX_INFO_OP_COMPLETE)
/* define an internal-only object for creating
* lists of names */
typedef struct {
pmix_list_item_t super;
pmix_name_t *pname;
} pmix_namelist_t;
PMIX_CLASS_DECLARATION(pmix_namelist_t);
/* define a struct for holding entries in the
* dictionary of attributes */
typedef struct {
uint32_t index;
char *name;
char *string;
pmix_data_type_t type;
char **description;
} pmix_regattr_input_t;
#define PMIX_REGATTR_INPUT_NEW(a, i, n, s, t, d) \
do { \
(a) = (pmix_regattr_input_t*)pmix_malloc(sizeof(pmix_regattr_input_t)); \
if (NULL != (a)) { \
memset((a), 0, sizeof(pmix_regattr_input_t)); \
(a)->index = (i); \
if (NULL != (n)) { \
(a)->name = strdup((n)); \
} \
if (NULL != (s)) { \
(a)->string = strdup((s)); \
} \
(a)->type = (t); \
if (NULL != (d)) { \
(a)->description = PMIx_Argv_copy((d)); \
} \
} \
} while(0)
#define PMIX_REGATTR_INPUT_FREE(a) \
do { \
if (NULL != (a)) { \
if (NULL != (a)->name) { \
free((a)->name); \
} \
if (NULL != (a)->string) \
free((a)->string); \
} \
if (NULL != (a)->description) { \
free((a)->description); \
} \
} \
} while(0)
/* define a struct for holding entries in the
* dictionary of event strings */
typedef struct {
uint32_t index;
char *name;
int32_t code;
} pmix_event_string_t;
/* define a struct for storing data in memory */
typedef struct {
uint32_t index;
pmix_value_t *value;
} pmix_qual_t;
#define PMIX_QUAL_NEW(d, k) \
do { \
(d) = (pmix_qual_t*)pmix_malloc(sizeof(pmix_qual_t)); \
if (NULL != (d)) { \
(d)->index = k; \
(d)->value = NULL; \
} \
} while(0)
#define PMIX_QUAL_RELEASE(d) \
do { \
if (NULL != (d)->value) { \
PMIX_VALUE_RELEASE((d)->value); \
} \
} while(0)
typedef struct {
uint32_t index;
uint32_t qualindex;
pmix_value_t *value;
} pmix_dstor_t;
PMIX_EXPORT pmix_dstor_t *
pmix_dstor_new_tma(
uint32_t index,
pmix_tma_t *tma
);
PMIX_EXPORT void
pmix_dstor_release_tma(
pmix_dstor_t *d,
pmix_tma_t *tma
);
#define PMIX_DSTOR_NEW(d, k) \
do { \
(d) = pmix_dstor_new_tma((k), NULL); \
} while(0)
#define PMIX_DSTOR_RELEASE(d) \
do { \
pmix_dstor_release_tma((d), NULL); \
} while(0)
/* define a struct for passing topology objects */
typedef struct {
pmix_object_t super;
char *source;
void *object;
} pmix_topo_obj_t;
PMIX_CLASS_DECLARATION(pmix_topo_obj_t);
/* define a command type for communicating to the
* pmix server */
typedef uint8_t pmix_cmd_t;
/* define some commands */
#define PMIX_REQ_CMD 0
#define PMIX_ABORT_CMD 1
#define PMIX_COMMIT_CMD 2
#define PMIX_FENCENB_CMD 3
#define PMIX_GETNB_CMD 4
#define PMIX_FINALIZE_CMD 5
#define PMIX_PUBLISHNB_CMD 6
#define PMIX_LOOKUPNB_CMD 7
#define PMIX_UNPUBLISHNB_CMD 8
#define PMIX_SPAWNNB_CMD 9
#define PMIX_CONNECTNB_CMD 10
#define PMIX_DISCONNECTNB_CMD 11
#define PMIX_NOTIFY_CMD 12
#define PMIX_REGEVENTS_CMD 13
#define PMIX_DEREGEVENTS_CMD 14
#define PMIX_QUERY_CMD 15
#define PMIX_LOG_CMD 16
#define PMIX_ALLOC_CMD 17
#define PMIX_JOB_CONTROL_CMD 18
#define PMIX_MONITOR_CMD 19
#define PMIX_GET_CREDENTIAL_CMD 20
#define PMIX_VALIDATE_CRED_CMD 21
#define PMIX_IOF_PULL_CMD 22
#define PMIX_IOF_PUSH_CMD 23
#define PMIX_GROUP_CONSTRUCT_CMD 24
#define PMIX_GROUP_JOIN_CMD 25
#define PMIX_GROUP_INVITE_CMD 26
#define PMIX_GROUP_LEAVE_CMD 27
#define PMIX_GROUP_DESTRUCT_CMD 28
#define PMIX_IOF_DEREG_CMD 29
#define PMIX_FABRIC_REGISTER_CMD 30
#define PMIX_FABRIC_UPDATE_CMD 31
#define PMIX_COMPUTE_DEVICE_DISTANCES_CMD 32
#define PMIX_REFRESH_CACHE 33
/* provide a "pretty-print" function for cmds */
const char *pmix_command_string(pmix_cmd_t cmd);
/* provide a hook to init tool data */
PMIX_EXPORT extern pmix_status_t pmix_tool_init_info(void);
/* define a set of flags to direct collection
* of data during operations */
typedef enum {
PMIX_COLLECT_INVALID = -1,
PMIX_COLLECT_NO,
PMIX_COLLECT_YES,
PMIX_COLLECT_MAX
} pmix_collect_t;
/**** PEER STRUCTURES ****/
/* clients can only talk to their server, and servers are
* assumed to all have the same personality. Thus, each
* process only needs to track a single set of personality
* modules. All interactions between a client and its local
* server, or between servers, are done thru these modules */
typedef struct pmix_personality_t {
pmix_bfrop_buffer_type_t type;
pmix_bfrops_module_t *bfrops;
pmix_psec_module_t *psec;
pmix_gds_base_module_t *gds;
} pmix_personality_t;
/* define a set of structs for tracking post-termination cleanup */
typedef struct pmix_epilog_t {
uid_t uid;
gid_t gid;
pmix_list_t cleanup_dirs;
pmix_list_t cleanup_files;
pmix_list_t ignores;
} pmix_epilog_t;
typedef struct {
pmix_list_item_t super;
char *path;
} pmix_cleanup_file_t;
PMIX_CLASS_DECLARATION(pmix_cleanup_file_t);
typedef struct {
pmix_list_item_t super;
char *path;
bool recurse;
bool leave_topdir;
} pmix_cleanup_dir_t;
PMIX_CLASS_DECLARATION(pmix_cleanup_dir_t);
/* define a struct to hold booleans controlling the
* format/contents of the output */
typedef struct {
bool set;
bool xml;
bool timestamp;
bool tag;
bool tag_detailed;
bool tag_fullname;
bool rank;
char *file;
char *directory;
bool nocopy;
bool merge;
bool local_output;
bool local_output_given;
bool pattern;
bool raw;
} pmix_iof_flags_t;
#define PMIX_IOF_FLAGS_STATIC_INIT \
{ \
.set = false, \
.xml = false, \
.timestamp = false, \
.tag = false, \
.tag_detailed = false, \
.tag_fullname = false, \
.rank = false, \
.file = NULL, \
.directory = NULL, \
.nocopy = false, \
.merge = false, \
.local_output = false, \
.local_output_given = false, \
.pattern = false, \
.raw = false \
}
/* objects used by servers for tracking active nspaces */
typedef struct {
pmix_list_item_t super;
char *nspace;
struct {
uint8_t major;
uint8_t minor;
uint8_t release;
} version;
pmix_rank_t nprocs; // num procs in this nspace
size_t nlocalprocs;
size_t num_waiting; // number of local procs waiting for debugger attach/release
bool all_registered; // all local ranks have been defined
bool version_stored; // the version string used by this nspace has been stored
pmix_buffer_t *jobbkt; // packed version of jobinfo
size_t ndelivered; // count of #local clients that have received the jobinfo
size_t nfinalized; // count of #local clients that have finalized
pmix_list_t ranks; // list of pmix_rank_info_t for connection support of my clients
/* all members of an nspace are required to have the
* same personality, but it can differ between nspaces.
* Since servers may support clients from multiple nspaces,
* track their respective compatibility modules here */
pmix_personality_t compat;
pmix_epilog_t epilog; // things to do upon termination of all local clients
// from this nspace
pmix_list_t setup_data; // list of pmix_kval_t containing info structs having blobs
// for setting up the local node for this nspace/application
pmix_iof_flags_t iof_flags; // output formatting flags
pmix_list_t sinks; // IOF write events for output to files or directories
} pmix_namespace_t;
PMIX_CLASS_DECLARATION(pmix_namespace_t);
/* define a caddy for quickly creating a list of pmix_namespace_t
* objects for local, dedicated purposes */
typedef struct {
pmix_list_item_t super;
pmix_namespace_t *ns;
} pmix_nspace_caddy_t;
PMIX_CLASS_DECLARATION(pmix_nspace_caddy_t);
typedef struct {
pmix_list_item_t super;
pmix_namespace_t *ns;
pmix_list_t envars;
} pmix_nspace_env_cache_t;
PMIX_CLASS_DECLARATION(pmix_nspace_env_cache_t);
typedef struct {
pmix_list_item_t super;
pmix_envar_t envar;
} pmix_envar_list_item_t;
PMIX_CLASS_DECLARATION(pmix_envar_list_item_t);
typedef struct pmix_rank_info_t {
pmix_list_item_t super;
int peerid; // peer object index into the local clients array on the server
pmix_name_t pname;
uid_t uid;
gid_t gid;
bool modex_recvd;
int proc_cnt; // #clones of this rank we know about
void *server_object; // pointer to rank-specific object provided by server
} pmix_rank_info_t;
PMIX_CLASS_DECLARATION(pmix_rank_info_t);
/* define a very simple caddy for dealing with pmix_info_t
* and pmix_query_t objects when transferring portions of arrays */
typedef struct {
pmix_list_item_t super;
pmix_info_t *info;
size_t ninfo;
} pmix_info_caddy_t;
PMIX_CLASS_DECLARATION(pmix_info_caddy_t);
typedef struct {
pmix_list_item_t super;
pmix_info_t info;
} pmix_infolist_t;
PMIX_CLASS_DECLARATION(pmix_infolist_t);
typedef struct {
pmix_list_item_t super;
pmix_query_t query;
} pmix_querylist_t;
PMIX_CLASS_DECLARATION(pmix_querylist_t);
typedef struct {
pmix_list_item_t super;
pmix_proc_t proc;
} pmix_proclist_t;
PMIX_CLASS_DECLARATION(pmix_proclist_t);
/* object for tracking peers - each peer can have multiple
* connections. This can occur if the initial app executes
* a fork/exec, and the child initiates its own connection
* back to the PMIx server. Thus, the trackers should be "indexed"
* by the socket, not the process nspace/rank */
typedef struct pmix_peer_t {
pmix_object_t super;
pmix_namespace_t *nptr; // point to the nspace object for this process
pmix_rank_info_t *info;
pmix_proc_type_t proc_type;
pmix_listener_protocol_t protocol;
int proc_cnt;
int index; // index into the local clients array on the server
int sd;
bool finalized; // peer has called finalize
pmix_event_t send_event; /**< registration with event thread for send events */
bool send_ev_active;
pmix_event_t recv_event; /**< registration with event thread for recv events */
bool recv_ev_active;
pmix_list_t send_queue; /**< list of messages to send */
pmix_ptl_send_t *send_msg; /**< current send in progress */
pmix_ptl_recv_t *recv_msg; /**< current recv in progress */
int commit_cnt;
pmix_epilog_t epilog; /**< things to be performed upon
termination of this peer */
} pmix_peer_t;
PMIX_CLASS_DECLARATION(pmix_peer_t);
/* tracker for IOF requests */
typedef struct {
pmix_object_t super;
pmix_event_t ev;
pmix_peer_t *requestor;
size_t local_id;
size_t remote_id;
pmix_proc_t *procs;
size_t nprocs;
pmix_iof_flags_t flags;
pmix_iof_channel_t channels;
pmix_iof_cbfunc_t cbfunc;
pmix_hdlr_reg_cbfunc_t regcbfunc;
void *cbdata;
} pmix_iof_req_t;
PMIX_CLASS_DECLARATION(pmix_iof_req_t);
/* caddy for query requests */
typedef struct {
pmix_object_t super;
pmix_event_t ev;
pmix_lock_t lock;
bool host_called;
pmix_status_t status;
pmix_query_t *queries;
size_t nqueries;
pmix_proc_t *targets;
size_t ntargets;
pmix_info_t *info;
pmix_info_t *dirs;
size_t ninfo;
size_t ndirs;
pmix_list_t results;
size_t nreplies;
size_t nrequests;
pmix_byte_object_t bo;
pmix_info_cbfunc_t cbfunc;
pmix_value_cbfunc_t valcbfunc;
pmix_release_cbfunc_t relcbfunc;
pmix_credential_cbfunc_t credcbfunc;
pmix_validation_cbfunc_t validcbfunc;
void *cbdata;
} pmix_query_caddy_t;
PMIX_CLASS_DECLARATION(pmix_query_caddy_t);
typedef struct {
pmix_list_item_t super;
char *grpid;
pmix_proc_t *members;
size_t nmbrs;
} pmix_group_t;
PMIX_CLASS_DECLARATION(pmix_group_t);
typedef struct {
pmix_list_item_t super;
pmix_proc_t proc;
pmix_byte_object_t blob; // packed blob of info provided by this proc
} pmix_grpinfo_t;
PMIX_CLASS_DECLARATION(pmix_grpinfo_t);
/* define a tracker for collective operations
* - instanced in pmix_server_ops.c */
typedef struct {
pmix_list_item_t super;
pmix_event_t ev;
bool event_active;
bool host_called; // tracker has been passed up to host
bool local; // operation is strictly local
char *id; // string identifier for the collective
pmix_cmd_t type;
pmix_proc_t pname;
bool hybrid; // true if participating procs are from more than one nspace
pmix_proc_t *pcs; // copy of the original array of participants
size_t npcs; // number of procs in the array
pmix_list_t nslist; // unique nspace list of participants
pmix_lock_t lock; // flag for waiting for completion
bool def_complete; // all local procs have been registered and the trk definition is complete
pmix_list_t local_cbs; // list of pmix_server_caddy_t for sending result to the local participants
// Note: there may be multiple entries for a given proc if that proc
// has fork/exec'd clones that are also participating
uint32_t nlocal; // number of local participants
uint32_t local_cnt; // number of local participants who have contributed
pmix_info_t *info; // array of info structs
size_t ninfo; // number of info structs in array
pmix_list_t grpinfo; // list of group info to be distributed
int grpop; // the group operation being tracked
pmix_collect_t collect_type; // whether or not data is to be returned at completion
pmix_modex_cbfunc_t modexcbfunc;
pmix_op_cbfunc_t op_cbfunc;
void *cbdata;
} pmix_server_trkr_t;
PMIX_CLASS_DECLARATION(pmix_server_trkr_t);
/* define an object for moving a send
* request into the server's event base and
* dealing with some request timeouts
* - instanced in pmix_server_ops.c */
typedef struct {
pmix_list_item_t super;
pmix_event_t ev;
bool event_active;
pmix_server_trkr_t *trk;
pmix_ptl_hdr_t hdr;
pmix_peer_t *peer;
pmix_info_t *info;
size_t ninfo;
} pmix_server_caddy_t;
PMIX_CLASS_DECLARATION(pmix_server_caddy_t);
/**** THREAD-RELATED ****/
/* define a caddy for thread-shifting operations */
typedef struct {
pmix_object_t super;
pmix_event_t ev;
pmix_lock_t lock;
pmix_status_t status;
pmix_status_t *codes;
size_t ncodes;
uint32_t sessionid;
pmix_name_t pname;
pmix_proc_t *proc;
pmix_peer_t *peer;
const char *data;
size_t ndata;
const char *key;
pmix_info_t *info;
size_t ninfo;
pmix_info_t *directives;
size_t ndirs;
pmix_notification_fn_t evhdlr;
pmix_iof_req_t *iofreq;
pmix_kval_t *kv;
pmix_value_t *vptr;
pmix_server_caddy_t *cd;
pmix_server_trkr_t *tracker;
bool enviro;
union {
pmix_release_cbfunc_t relfn;
pmix_hdlr_reg_cbfunc_t hdlrregcbfn;
pmix_op_cbfunc_t opcbfn;
pmix_modex_cbfunc_t modexcbfunc;
pmix_info_cbfunc_t infocbfunc;
} cbfunc;
void *cbdata;
size_t ref;
} pmix_shift_caddy_t;
PMIX_CLASS_DECLARATION(pmix_shift_caddy_t);
typedef struct {
pmix_object_t super;
pmix_proc_t p;
bool pntrval;
bool stval;
bool optional;
bool immediate;
bool add_immediate;
bool refresh_cache;
pmix_scope_t scope;
bool sessioninfo;
bool sessiondirective;
uint32_t sessionid;
bool nodeinfo;
bool nodedirective;
char *hostname;
uint32_t nodeid;
bool appinfo;
bool appdirective;
uint32_t appnum;
} pmix_get_logic_t;
PMIX_CLASS_DECLARATION(pmix_get_logic_t);
/* struct for tracking ops */
typedef struct {
pmix_list_item_t super;
pmix_event_t ev;
pmix_lock_t lock;
bool checked;
int status;
pmix_status_t pstatus;
pmix_scope_t scope;
pmix_buffer_t data;
union {
pmix_ptl_cbfunc_t ptlfn;
pmix_op_cbfunc_t opfn;
pmix_value_cbfunc_t valuefn;
pmix_lookup_cbfunc_t lookupfn;
pmix_spawn_cbfunc_t spawnfn;
pmix_hdlr_reg_cbfunc_t hdlrregfn;
pmix_info_cbfunc_t infofn;
pmix_device_dist_cbfunc_t distfn;
} cbfunc;
size_t errhandler_ref;
void *cbdata;
pmix_name_t pname;
char *key;
pmix_value_t *value;
pmix_proc_t *proc;
pmix_proc_t *procs;
size_t nprocs;
pmix_info_t *info;
size_t ninfo;
pmix_device_distance_t *dist;
bool infocopy;
size_t nvals;
pmix_list_t kvs;
bool copy;
pmix_get_logic_t *lg;
bool timer_running;
pmix_fabric_t *fabric;
pmix_topology_t *topo;
} pmix_cb_t;
PMIX_CLASS_DECLARATION(pmix_cb_t);
#define PMIX_THREADSHIFT(r, c) \
do { \
pmix_event_assign(&((r)->ev), pmix_globals.evbase, -1, EV_WRITE, (c), (r)); \
PMIX_POST_OBJECT((r)); \
pmix_event_active(&((r)->ev), EV_WRITE, 1); \
} while (0)
#define PMIX_THREADSHIFT_DELAY(r, c, t) \
do { \
struct timeval _tv = {0, 0}; \
pmix_event_evtimer_set(pmix_globals.evbase, &(r)->ev, (c), (r)); \
_tv.tv_sec = (int) (t); \
_tv.tv_usec = ((t) -_tv.tv_sec) * 1000000.0; \
PMIX_POST_OBJECT((r)); \
pmix_event_evtimer_add(&(r)->ev, &_tv); \
} while (0)
typedef struct {
pmix_object_t super;
pmix_event_t ev;
pmix_lock_t lock;
/* timestamp receipt of the notification so we
* can evict the oldest one if we get overwhelmed */
time_t ts;
/* what room of the hotel they are in */
int room;
pmix_status_t status;
pmix_proc_t source;
pmix_data_range_t range;
/* For notification, we use the targets field to track
* any custom range of procs that are to receive the
* event.
*/
pmix_proc_t *targets;
size_t ntargets;
size_t nleft; // number of targets left to be notified
/* When generating a notification, the originator can
* specify the range of procs affected by this event.
* For example, when creating a JOB_TERMINATED event,
* the RM can specify the nspace of the job that has
* ended, thus allowing users to provide a different
* callback object based on the nspace being monitored.
* We use the "affected" field to track these values
* when processing the event chain.
*/
pmix_proc_t *affected;
size_t naffected;
/* track if the event generator stipulates that default
* event handlers are/are not to be given the event */
bool nondefault;
/* carry along any other provided info so the individual
* handlers can look at it */
pmix_info_t *info;
size_t ninfo;
/* allow for a buffer to be carried across internal processing */
pmix_buffer_t *buf;
/* the final callback to be executed upon completion of the event */
pmix_op_cbfunc_t cbfunc;
void *cbdata;
} pmix_notify_caddy_t;
PMIX_CLASS_DECLARATION(pmix_notify_caddy_t);
typedef struct {
pmix_object_t super;
/** Points to key <--> index translation table. */
pmix_pointer_array_t *table;
/** Stores the next ID. */
uint32_t next_id;
} pmix_keyindex_t;
PMIX_CLASS_DECLARATION(pmix_keyindex_t);
#define PMIX_KEYINDEX_STATIC_INIT \
{ \
.super = PMIX_OBJ_STATIC_INIT(pmix_object_t), \
.table = NULL, \
.next_id = PMIX_INDEX_BOUNDARY \
}
/**** GLOBAL STORAGE ****/
/* define a global construct that includes values that must be shared
* between various parts of the code library. The client, tool,
* and server libraries must instance this structure */
typedef struct {
int init_cntr; // #times someone called Init - #times called Finalize
pmix_proc_t myid;
pmix_value_t myidval;
pmix_value_t myrankval;
pmix_peer_t *mypeer; // my own peer object
uid_t uid; // my effective uid
gid_t gid; // my effective gid
char *hostname; // my hostname
uint32_t appnum; // my appnum
pid_t pid; // my local pid
uint32_t nodeid; // my nodeid, if given
uint32_t sessionid; // my sessionid, if given
int pindex;
pmix_event_base_t *evbase;
pmix_event_base_t *evauxbase;
int debug_output;
pmix_events_t events; // my event handler registrations.
bool connected;
bool commits_pending;
struct timeval event_window;
pmix_list_t cached_events; // events waiting in the window prior to processing
pmix_pointer_array_t iof_requests; // array of pmix_iof_req_t IOF requests
int max_events; // size of the notifications hotel
int event_eviction_time; // max time to cache notifications
pmix_hotel_t notifications; // hotel of pending notifications
/* IOF controls */
bool pushstdin;
pmix_list_t stdin_targets; // list of pmix_namelist_t
bool tag_output;
bool xml_output;
bool timestamp_output;
size_t output_limit;
pmix_list_t nspaces;
pmix_topology_t topology;
pmix_cpuset_t cpuset;
bool external_topology;
bool external_progress;
pmix_iof_flags_t iof_flags;
pmix_keyindex_t keyindex;
} pmix_globals_t;
/* provide access to a function to cleanup epilogs */
PMIX_EXPORT void pmix_execute_epilog(pmix_epilog_t *ep);
PMIX_EXPORT pmix_status_t pmix_notify_event_cache(pmix_notify_caddy_t *cd);
PMIX_EXPORT extern pmix_globals_t pmix_globals;
PMIX_EXPORT extern pmix_lock_t pmix_global_lock;
PMIX_EXPORT extern const char* PMIX_PROXY_VERSION;
PMIX_EXPORT extern const char* PMIX_PROXY_BUGREPORT;
PMIX_EXPORT void pmix_log_local_op(int sd, short args, void *cbdata_);
static inline bool pmix_check_node_info(const char *key)
{
char *keys[] = {
PMIX_HOSTNAME, PMIX_HOSTNAME_ALIASES,
PMIX_NODEID, PMIX_AVAIL_PHYS_MEMORY,
PMIX_LOCAL_PEERS, PMIX_LOCAL_PROCS,
PMIX_LOCAL_CPUSETS, PMIX_LOCAL_SIZE,
PMIX_NODE_SIZE, PMIX_LOCALLDR,
PMIX_NODE_OVERSUBSCRIBED, PMIX_FABRIC_DEVICES,
PMIX_FABRIC_COORDINATES, PMIX_FABRIC_DEVICE,
PMIX_FABRIC_DEVICE_INDEX, PMIX_FABRIC_DEVICE_NAME,
PMIX_FABRIC_DEVICE_VENDOR, PMIX_FABRIC_DEVICE_BUS_TYPE,
PMIX_FABRIC_DEVICE_VENDORID, PMIX_FABRIC_DEVICE_DRIVER,
PMIX_FABRIC_DEVICE_FIRMWARE, PMIX_FABRIC_DEVICE_ADDRESS,
PMIX_FABRIC_DEVICE_MTU, PMIX_FABRIC_DEVICE_COORDINATES,
PMIX_FABRIC_DEVICE_SPEED, PMIX_FABRIC_DEVICE_STATE,
PMIX_FABRIC_DEVICE_TYPE, PMIX_FABRIC_DEVICE_PCI_DEVID,
NULL
};
size_t n;
for (n = 0; NULL != keys[n]; n++) {
if (0 == strncmp(key, keys[n], PMIX_MAX_KEYLEN)) {
return true;
}
}
return false;
}
static inline bool pmix_check_app_info(const char *key)
{
char *keys[] = {
PMIX_APP_SIZE, PMIX_APPLDR, PMIX_APP_ARGV, PMIX_WDIR,
PMIX_PSET_NAME, PMIX_PSET_MEMBERS, PMIX_APP_MAP_TYPE, PMIX_APP_MAP_REGEX,
NULL
};
size_t n;
for (n = 0; NULL != keys[n]; n++) {
if (0 == strncmp(key, keys[n], PMIX_MAX_KEYLEN)) {
return true;
}
}
return false;
}
static inline bool pmix_check_session_info(const char *key)
{
char *keys[] = {
PMIX_SESSION_ID, PMIX_CLUSTER_ID, PMIX_UNIV_SIZE,
PMIX_TMPDIR, PMIX_TDIR_RMCLEAN, PMIX_HOSTNAME_KEEP_FQDN,
PMIX_RM_NAME, PMIX_RM_VERSION,
NULL
};
size_t n;
for (n = 0; NULL != keys[n]; n++) {
if (0 == strncmp(key, keys[n], PMIX_MAX_KEYLEN)) {
return true;
}
}
return false;
}
static inline bool pmix_check_special_key(const char *key)
{
char *keys[] = {
PMIX_GROUP_CONTEXT_ID,
PMIX_GROUP_LOCAL_CID,
NULL
};
size_t n;
for (n = 0; NULL != keys[n]; n++) {
if (0 == strncmp(key, keys[n], PMIX_MAX_KEYLEN)) {
return true;
}
}
return false;
}
#if PMIX_PICKY_COMPILERS
#define PMIX_HIDE_UNUSED_PARAMS(...) \
do { \
int __x = 3; \
pmix_hide_unused_params(__x, __VA_ARGS__); \
} while(0)
PMIX_EXPORT void pmix_hide_unused_params(int x, ...);
#else
#define PMIX_HIDE_UNUSED_PARAMS(...)
#endif
#define PMIX_TRACE_KEY_ACTUAL(s, k, v) \
do { \
if (0 == strcmp(s, k)) { \
char *_v = PMIx_Value_string(v); \
pmix_output(0, "[%s:%s:%d] %s\n%s\n", \
__FILE__, __func__, __LINE__, \
PMIx_Get_attribute_name(k), _v); \
free(_v); \
} \
} while(0)
#define PMIX_TRACE_KEY(c, s, k, v) \
do { \
if (0 == strcasecmp(c, "SERVER") && \
PMIX_PEER_IS_SERVER(pmix_globals.mypeer)) { \
PMIX_TRACE_KEY_ACTUAL(s, k, v); \
} else if (0 == strcasecmp(c, "CLIENT") && \
!PMIX_PEER_IS_SERVER(pmix_globals.mypeer)) { \
PMIX_TRACE_KEY_ACTUAL(s, k, v); \
} \
} while (0)
END_C_DECLS
#endif /* PMIX_GLOBALS_H */

View File

@@ -0,0 +1,70 @@
/*
* Copyright (c) 2004-2007 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2021-2022 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
/** @file
*
* Simple macros to quickly compute a hash value from a string.
*
*/
#ifndef PMIX_HASH_STRING_H
#define PMIX_HASH_STRING_H
/**
* Compute the hash value and the string length simultaneously
*
* @param str (IN) The string which will be parsed (char*)
* @param hash (OUT) Where the hash value will be stored (uint32_t)
* @param length (OUT) The computed length of the string (uint32_t)
*/
#define PMIX_HASH_STRLEN(str, hash, length) \
do { \
register const char *_str = (str); \
register uint32_t _hash = 0; \
register uint32_t _len = 0; \
\
while (*_str) { \
_len++; \
_hash += *_str++; \
_hash += (_hash << 10); \
_hash ^= (_hash >> 6); \
} \
\
_hash += (_hash << 3); \
_hash ^= (_hash >> 11); \
(hash) = (_hash + (_hash << 15)); \
(length) = _len; \
} while (0)
/**
* Compute the hash value
*
* @param str (IN) The string which will be parsed (char*)
* @param hash (OUT) Where the hash value will be stored (uint32_t)
*/
#define PMIX_HASH_STR(str, hash) \
do { \
register const char *_str = (str); \
register uint32_t _hash = 0; \
\
while (*_str) { \
_hash += *_str++; \
_hash += (_hash << 10); \
_hash ^= (_hash >> 6); \
} \
\
_hash += (_hash << 3); \
_hash ^= (_hash >> 11); \
(hash) = (_hash + (_hash << 15)); \
} while (0)
#endif /* PMIX_HASH_STRING_H */

View File

@@ -0,0 +1,20 @@
/*
* Copyright (c) 2021 Amazon.com, Inc. or its affiliates. All Rights
* reserved.
* Copyright (c) 2021-2024 Nanook Consulting All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*
* Wrapper around GASNet's gasnet_portable_platform.h to avoid
* compiler warnings
*/
#ifndef PMIX_PORTABLE_PLATFORM_H
#define PMIX_PORTABLE_PLATFORM_H 1
#include "src/include/pmix_portable_platform_real.h"
#endif

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,40 @@
/*
* Copyright (c) 2004-2006 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2014-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2021-2022 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
/** @file
*
* Compiler-specific prefetch functions
*
* A small set of prefetch / prediction interfaces for using compiler
* directives to improve memory prefetching and branch prediction
*/
#ifndef PMIX_PREFETCH_H
#define PMIX_PREFETCH_H
#include "src/include/pmix_config.h"
#if PMIX_C_HAVE_BUILTIN_EXPECT
# define PMIX_LIKELY(expression) __builtin_expect(!!(expression), 1)
# define PMIX_UNLIKELY(expression) __builtin_expect(!!(expression), 0)
#else
# define PMIX_LIKELY(expression) (expression)
# define PMIX_UNLIKELY(expression) (expression)
#endif
#if PMIX_C_HAVE_BUILTIN_PREFETCH
# define PMIX_PREFETCH(address, rw, locality) __builtin_prefetch(address, rw, locality)
#else
# define PMIX_PREFETCH(address, rw, locality)
#endif
#endif

View File

@@ -0,0 +1,26 @@
/*
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2005 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2015 Intel, Inc. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
#ifndef PMIX_GET_SOCKET_ERROR_H
#define PMIX_GET_SOCKET_ERROR_H
#include <errno.h>
#define pmix_socket_errno errno
#endif /* PMIX_GET_ERROR_H */

View File

@@ -0,0 +1,62 @@
/* -*- Mode: C; c-basic-offset:4 ; indent-tabs-mode:nil -*- */
/*
* Copyright (c) 2018 Los Alamos National Security, LLC.
* All rights reserved.
* Copyright (c) 2019 Intel, Inc. All rights reserved.
* Copyright (c) 2020 Cisco Systems, Inc. All rights reserved
* Copyright (c) 2021-2023 Nanook Consulting. All rights reserved.
* Copyright (c) 2021 Amazon.com, Inc. or its affiliates.
* All Rights reserved.
* Copyright (c) 2023 Triad National Security, LLC. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
#ifndef PMIX_STDATOMIC_H
#define PMIX_STDATOMIC_H
#include "pmix_stdint.h"
#include <stdbool.h>
#if PMIX_USE_C11_ATOMICS
#ifdef HAVE_STDATOMIC_H
#include <stdatomic.h>
#endif
typedef atomic_int pmix_atomic_int_t;
typedef atomic_long pmix_atomic_long_t;
typedef _Atomic bool pmix_atomic_bool_t;
typedef _Atomic int32_t pmix_atomic_int32_t;
typedef _Atomic uint32_t pmix_atomic_uint32_t;
typedef _Atomic int64_t pmix_atomic_int64_t;
typedef _Atomic uint64_t pmix_atomic_uint64_t;
typedef _Atomic size_t pmix_atomic_size_t;
typedef _Atomic ssize_t pmix_atomic_ssize_t;
typedef _Atomic intptr_t pmix_atomic_intptr_t;
typedef _Atomic uintptr_t pmix_atomic_uintptr_t;
#else
typedef volatile int pmix_atomic_int_t;
typedef volatile long pmix_atomic_long_t;
typedef volatile bool pmix_atomic_bool_t;
typedef volatile int32_t pmix_atomic_int32_t;
typedef volatile uint32_t pmix_atomic_uint32_t;
typedef volatile int64_t pmix_atomic_int64_t;
typedef volatile uint64_t pmix_atomic_uint64_t;
typedef volatile size_t pmix_atomic_size_t;
typedef volatile ssize_t pmix_atomic_ssize_t;
typedef volatile intptr_t pmix_atomic_intptr_t;
typedef volatile uintptr_t pmix_atomic_uintptr_t;
#endif
#endif

View File

@@ -0,0 +1,131 @@
/* -*- Mode: C; c-basic-offset:4 ; indent-tabs-mode:nil -*- */
/*
* Copyright (c) 2004-2007 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2023 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2015 Los Alamos National Security, LLC. All rights
* reserved.
* Copyright (c) 2016 Research Organization for Information Science
* and Technology (RIST). All rights reserved.
* Copyright (c) 2018 Intel, Inc. All rights reserved.
* Copyright (c) 2021-2022 Nanook Consulting. All rights reserved.
* Copyright (c) 2023 Triad National Security, LLC. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*
* This file includes the C99 stdint.h file if available, and otherwise
* defines fixed-width types according to the SIZEOF information
* gathered by configure.
*/
#ifndef PMIX_STDINT_H
#define PMIX_STDINT_H 1
#include "src/include/pmix_config.h"
/*
* Include what we can and define what is missing.
*/
#include <limits.h>
#include <stdint.h>
#ifdef HAVE_SYS_TYPES_H
# include <sys/types.h>
#endif
/* 128-bit */
#ifdef HAVE_INT128_T
typedef int128_t pmix_int128_t;
typedef uint128_t pmix_uint128_t;
# define HAVE_PMIX_INT128_T 1
#elif defined(HAVE___INT128)
/* suppress warning about __int128 type */
# pragma GCC diagnostic push
/* Clang won't quietly accept "-pedantic", but GCC versions older than ~4.8
* won't quietly accept "-Wpedanic". The whole "#pragma GCC diagnostic ..."
* facility only was added to GCC as of version 4.6. */
# if defined(__clang__) || (defined(__GNUC__) && __GNUC__ >= 6)
# pragma GCC diagnostic ignored "-Wpedantic"
# else
# pragma GCC diagnostic ignored "-pedantic"
# endif
typedef __int128 pmix_int128_t;
typedef unsigned __int128 pmix_uint128_t;
# pragma GCC diagnostic pop
# define HAVE_PMIX_INT128_T 1
#else
# define HAVE_PMIX_INT128_T 0
#endif
/* Pointers */
#if SIZEOF_VOID_P == SIZEOF_INT
# ifndef HAVE_INTPTR_T
typedef signed int intptr_t;
# endif
# ifndef HAVE_UINTPTR_T
typedef unsigned int uintptr_t;
# endif
#elif SIZEOF_VOID_P == SIZEOF_LONG
# ifndef HAVE_INTPTR_T
typedef signed long intptr_t;
# endif
# ifndef HAVE_UINTPTR_T
typedef unsigned long uintptr_t;
# endif
#elif HAVE_LONG_LONG && defined(SIZEOF_LONG_LONG) && SIZEOF_VOID_P == SIZEOF_LONG_LONG
# ifndef HAVE_INTPTR_T
typedef signed long long intptr_t;
# endif
# ifndef HAVE_UINTPTR_T
typedef unsigned long long uintptr_t;
# endif
#else
# error Failed to define pointer-sized integer types
#endif
/* inttypes.h printf specifiers */
#include <inttypes.h>
#ifndef PRIsize_t
# if defined(ACCEPT_C99)
# define PRIsize_t "zu"
# elif SIZEOF_SIZE_T == SIZEOF_LONG
# define PRIsize_t "lu"
# elif defined(SIZEOF_LONG_LONG) && SIZEOF_SIZE_T == SIZEOF_LONG_LONG
# define PRIsize_t "llu"
# else
# define PRIsize_t "u"
# endif
#endif
#endif /* PMIX_STDINT_H */

View File

@@ -0,0 +1,310 @@
/*
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2005 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2014-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2015 Mellanox Technologies, Inc.
* All rights reserved.
* Copyright (c) 2019 Research Organization for Information Science
* and Technology (RIST). All rights reserved.
* Copyright (c) 2021-2022 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
#ifndef PMIX_TYPES_H
#define PMIX_TYPES_H
#include "src/include/pmix_config.h"
#include "pmix_common.h"
#ifdef HAVE_STDINT_H
# include <stdint.h>
#endif
#ifdef HAVE_SYS_TYPES_H
# include <sys/types.h>
#endif
#ifdef HAVE_SYS_SOCKET_H
# include <sys/socket.h>
#endif
#ifdef HAVE_SYS_SELECT_H
# include <sys/select.h>
#endif
#ifdef HAVE_NETINET_IN_H
# include <netinet/in.h>
#endif
#ifdef HAVE_ARPA_INET_H
# include <arpa/inet.h>
#endif
#include <event.h>
#if !PMIX_HAVE_LIBEV
# include <event2/thread.h>
#endif
#if PMIX_ENABLE_DEBUG
# include "src/util/pmix_output.h"
#endif
#include <pthread.h>
/*
* portable assignment of pointer to int
*/
typedef union {
uint64_t lval;
uint32_t ival;
void *pval;
struct {
uint32_t uval;
uint32_t lval;
} sval;
} pmix_ptr_t;
/*
* handle differences in iovec
*/
#if defined(__APPLE__) || defined(__WINDOWS__)
typedef char *pmix_iov_base_ptr_t;
# define PMIX_IOVBASE char
#else
# define PMIX_IOVBASE void
typedef void *pmix_iov_base_ptr_t;
#endif
/*
* handle differences in socklen_t
*/
#if defined(HAVE_SOCKLEN_T)
typedef socklen_t pmix_socklen_t;
#else
typedef int pmix_socklen_t;
#endif
#define pmix_htons htons
#define pmix_ntohs ntohs
/*
* Convert a 64 bit value to network byte order.
*/
static inline uint64_t pmix_hton64(uint64_t val) __pmix_attribute_const__;
static inline uint64_t pmix_hton64(uint64_t val)
{
#ifdef HAVE_UNIX_BYTESWAP
union {
uint64_t ll;
uint32_t l[2];
} w, r;
/* platform already in network byte order? */
if (htonl(1) == 1L)
return val;
w.ll = val;
r.l[0] = htonl(w.l[1]);
r.l[1] = htonl(w.l[0]);
return r.ll;
#else
return val;
#endif
}
/*
* Convert a 64 bit value from network to host byte order.
*/
static inline uint64_t pmix_ntoh64(uint64_t val) __pmix_attribute_const__;
static inline uint64_t pmix_ntoh64(uint64_t val)
{
#ifdef HAVE_UNIX_BYTESWAP
union {
uint64_t ll;
uint32_t l[2];
} w, r;
/* platform already in network byte order? */
if (htonl(1) == 1L)
return val;
w.ll = val;
r.l[0] = ntohl(w.l[1]);
r.l[1] = ntohl(w.l[0]);
return r.ll;
#else
return val;
#endif
}
/* Convert size_t value from host to network byte order and back */
#if SIZEOF_SIZE_T == 4
# define pmix_htonsizet(x) htonl(x)
# define pmix_ntohsizet(x) ntohl(x)
#elif SIZEOF_SIZE_T == 8
# define pmix_htonsizet(x) pmix_hton64(x)
# define pmix_ntohsizet(x) pmix_ntoh64(x)
#endif
/**
* Convert between a local representation of pointer and a 64 bits value.
*/
static inline uint64_t pmix_ptr_ptol(void *ptr) __pmix_attribute_const__;
static inline uint64_t pmix_ptr_ptol(void *ptr)
{
return (uint64_t)(uintptr_t) ptr;
}
static inline void *pmix_ptr_ltop(uint64_t value) __pmix_attribute_const__;
static inline void *pmix_ptr_ltop(uint64_t value)
{
#if SIZEOF_VOID_P == 4 && PMIX_ENABLE_DEBUG
if (value > ((1ULL << 32) - 1ULL)) {
pmix_output(0, "Warning: truncating value in pmix_ptr_ltop");
}
#endif
return (void *) (uintptr_t) value;
}
#if defined(WORDS_BIGENDIAN) || !defined(HAVE_UNIX_BYTESWAP)
static inline uint16_t pmix_swap_bytes2(uint16_t val) __pmix_attribute_const__;
static inline uint16_t pmix_swap_bytes2(uint16_t val)
{
union {
uint16_t bigval;
uint8_t arrayval[2];
} w, r;
w.bigval = val;
r.arrayval[0] = w.arrayval[1];
r.arrayval[1] = w.arrayval[0];
return r.bigval;
}
static inline uint32_t pmix_swap_bytes4(uint32_t val) __pmix_attribute_const__;
static inline uint32_t pmix_swap_bytes4(uint32_t val)
{
union {
uint32_t bigval;
uint8_t arrayval[4];
} w, r;
w.bigval = val;
r.arrayval[0] = w.arrayval[3];
r.arrayval[1] = w.arrayval[2];
r.arrayval[2] = w.arrayval[1];
r.arrayval[3] = w.arrayval[0];
return r.bigval;
}
static inline uint64_t pmix_swap_bytes8(uint64_t val) __pmix_attribute_const__;
static inline uint64_t pmix_swap_bytes8(uint64_t val)
{
union {
uint64_t bigval;
uint8_t arrayval[8];
} w, r;
w.bigval = val;
r.arrayval[0] = w.arrayval[7];
r.arrayval[1] = w.arrayval[6];
r.arrayval[2] = w.arrayval[5];
r.arrayval[3] = w.arrayval[4];
r.arrayval[4] = w.arrayval[3];
r.arrayval[5] = w.arrayval[2];
r.arrayval[6] = w.arrayval[1];
r.arrayval[7] = w.arrayval[0];
return r.bigval;
}
#else
# define pmix_swap_bytes2 htons
# define pmix_swap_bytes4 htonl
# define pmix_swap_bytes8 hton64
#endif /* WORDS_BIGENDIAN || !HAVE_UNIX_BYTESWAP */
#define PMIX_EV_TIMEOUT EV_TIMEOUT
#define PMIX_EV_READ EV_READ
#define PMIX_EV_WRITE EV_WRITE
#define PMIX_EV_SIGNAL EV_SIGNAL
/* Persistent event: won't get removed automatically when activated. */
#define PMIX_EV_PERSIST EV_PERSIST
#define PMIX_EVLOOP_ONCE EVLOOP_ONCE /**< Block at most once. */
#define PMIX_EVLOOP_NONBLOCK EVLOOP_NONBLOCK /**< Do not block. */
#define PMIX_EVENT_SIGNAL(ev) pmix_event_get_signal(ev)
typedef struct event_base pmix_event_base_t;
typedef struct event pmix_event_t;
#define pmix_event_base_create() event_base_new()
#define pmix_event_base_free(b) event_base_free(b)
#if PMIX_HAVE_LIBEV
# define pmix_event_use_threads()
# define pmix_event_free(b) free(b)
# define pmix_event_get_signal(x) (x)->ev_fd
#else
/* thread support APIs */
# define pmix_event_use_threads() evthread_use_pthreads()
# define pmix_event_free(x) event_free(x)
# define pmix_event_get_signal(x) event_get_signal(x)
#endif
/* Basic event APIs */
#define pmix_event_enable_debug_mode() event_enable_debug_mode()
PMIX_EXPORT int pmix_event_assign(struct event *ev, pmix_event_base_t *evbase, int fd, short arg,
event_callback_fn cbfn, void *cbd);
#define pmix_event_set(b, x, fd, fg, cb, arg) \
pmix_event_assign((x), (b), (fd), (fg), (event_callback_fn)(cb), (arg))
#if PMIX_HAVE_LIBEV
PMIX_EXPORT int pmix_event_add(struct event *ev, struct timeval *tv);
PMIX_EXPORT int pmix_event_del(struct event *ev);
PMIX_EXPORT void pmix_event_active(struct event *ev, int res, short ncalls);
PMIX_EXPORT void pmix_event_base_loopexit(pmix_event_base_t *b);
#else
# define pmix_event_add(ev, tv) event_add((ev), (tv))
# define pmix_event_del(ev) event_del((ev))
# define pmix_event_active(x, y, z) event_active((x), (y), (z))
# define pmix_event_base_loopexit(b) event_base_loopexit(b, NULL)
#endif
PMIX_EXPORT pmix_event_t *pmix_event_new(pmix_event_base_t *b, int fd, short fg,
event_callback_fn cbfn, void *cbd);
#define pmix_event_loop(b, fg) event_base_loop((b), (fg))
#define pmix_event_evtimer_new(b, cb, arg) pmix_event_new((b), -1, 0, (cb), (arg))
#define pmix_event_evtimer_add(x, tv) pmix_event_add((x), (tv))
#define pmix_event_evtimer_set(b, x, cb, arg) \
pmix_event_assign((x), (b), -1, 0, (event_callback_fn)(cb), (arg))
#define pmix_event_evtimer_del(x) pmix_event_del((x))
#define pmix_event_signal_set(b, x, fd, cb, arg) \
pmix_event_assign((x), (b), (fd), EV_SIGNAL | EV_PERSIST, (event_callback_fn)(cb), (arg))
#endif /* PMIX_TYPES_H */

View File

@@ -0,0 +1,251 @@
/* -*- Mode: C; c-basic-offset:4 ; indent-tabs-mode:nil -*- */
/*
* Copyright (c) 2004-2008 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2007 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2009 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2013-2015 Los Alamos National Security, LLC. All rights
* reserved.
* Copyright (c) 2015 Research Organization for Information Science
* and Technology (RIST). All rights reserved.
* Copyright (c) 2016-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2021-2022 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
#ifndef PMIX_MCA_BASE_H
#define PMIX_MCA_BASE_H
#include "src/include/pmix_config.h"
#include "src/class/pmix_list.h"
#include "src/class/pmix_object.h"
/*
* These units are large enough to warrant their own .h files
*/
#include "src/mca/base/pmix_mca_base_framework.h"
#include "src/mca/base/pmix_mca_base_var.h"
#include "src/mca/mca.h"
#include "src/util/pmix_cmd_line.h"
#include "src/util/pmix_output.h"
BEGIN_C_DECLS
/*
* Structure for making plain lists of components
*/
struct pmix_mca_base_component_list_item_t {
pmix_list_item_t super;
const pmix_mca_base_component_t *cli_component;
};
typedef struct pmix_mca_base_component_list_item_t pmix_mca_base_component_list_item_t;
PMIX_EXPORT PMIX_CLASS_DECLARATION(pmix_mca_base_component_list_item_t);
/*
* Structure for making priority lists of components
*/
struct pmix_mca_base_component_priority_list_item_t {
pmix_mca_base_component_list_item_t super;
int cpli_priority;
};
typedef struct pmix_mca_base_component_priority_list_item_t
pmix_mca_base_component_priority_list_item_t;
PMIX_EXPORT PMIX_CLASS_DECLARATION(pmix_mca_base_component_priority_list_item_t);
/*
* Public variables
*/
PMIX_EXPORT extern char *pmix_mca_base_component_path;
PMIX_EXPORT extern char *pmix_mca_base_component_show_load_errors;
PMIX_EXPORT extern bool pmix_mca_base_component_abort_on_load_error;
PMIX_EXPORT extern bool pmix_mca_base_component_track_load_errors;
PMIX_EXPORT extern bool pmix_mca_base_component_disable_dlopen;
PMIX_EXPORT extern char *pmix_mca_base_system_default_path;
PMIX_EXPORT extern char *pmix_mca_base_user_default_path;
/*
* Standard verbosity levels
*/
enum {
/** total silence */
PMIX_MCA_BASE_VERBOSE_NONE = -1,
/** only errors are printed */
PMIX_MCA_BASE_VERBOSE_ERROR = 0,
/** emit messages about component selection, open, and unloading */
PMIX_MCA_BASE_VERBOSE_COMPONENT = 10,
/** also emit warnings */
PMIX_MCA_BASE_VERBOSE_WARN = 20,
/** also emit general, user-relevant information, such as rationale as to why certain choices
* or code paths were taken, information gleaned from probing the local system, etc. */
PMIX_MCA_BASE_VERBOSE_INFO = 40,
/** also emit relevant tracing information (e.g., which functions were invoked /
* call stack entry/exit info) */
PMIX_MCA_BASE_VERBOSE_TRACE = 60,
/** also emit PMIX-developer-level (i.e,. highly detailed) information */
PMIX_MCA_BASE_VERBOSE_DEBUG = 80,
/** also output anything else that might be useful */
PMIX_MCA_BASE_VERBOSE_MAX = 100,
};
/*
* Public functions
*/
/**
* First function called in the MCA.
*
* @return PMIX_SUCCESS Upon success
* @return PMIX_ERROR Upon failure
*
* This function starts up the entire MCA. It initializes a bunch
* of built-in MCA parameters, and initialized the MCA component
* repository.
*
* It must be the first MCA function invoked. It is normally
* invoked during the initialization stage and specifically
* invoked in the special case of the *_info command.
*/
PMIX_EXPORT int pmix_mca_base_open(const char *add_path);
/**
* Last function called in the MCA
*
* @return PMIX_SUCCESS Upon success
* @return PMIX_ERROR Upon failure
*
* This function closes down the entire MCA. It clears all MCA
* parameters and closes down the MCA component repository.
*
* It must be the last MCA function invoked. It is normally invoked
* during the finalize stage.
*/
PMIX_EXPORT int pmix_mca_base_close(void);
/**
* A generic select function
*
*/
PMIX_EXPORT int pmix_mca_base_select(const char *type_name, int output_id,
pmix_list_t *components_available,
pmix_mca_base_module_t **best_module,
pmix_mca_base_component_t **best_component, int *priority_out);
/**
* A function for component query functions to discover if they have
* been explicitly required to or requested to be selected.
*
* exclusive: If the specified component is the only component that is
* available for selection.
*
*/
PMIX_EXPORT int pmix_mca_base_is_component_required(pmix_list_t *components_available,
pmix_mca_base_component_t *component,
bool exclusive, bool *is_required);
/* pmix_mca_base_component_compare.c */
PMIX_EXPORT int
pmix_mca_base_component_compare_priority(pmix_mca_base_component_priority_list_item_t *a,
pmix_mca_base_component_priority_list_item_t *b);
PMIX_EXPORT int pmix_mca_base_component_compare(const pmix_mca_base_component_t *a,
const pmix_mca_base_component_t *b);
PMIX_EXPORT int pmix_mca_base_component_compatible(const pmix_mca_base_component_t *a,
const pmix_mca_base_component_t *b);
PMIX_EXPORT char *pmix_mca_base_component_to_string(const pmix_mca_base_component_t *a);
/* pmix_mca_base_component_find.c */
PMIX_EXPORT int pmix_mca_base_component_find(const char *directory,
pmix_mca_base_framework_t *framework,
bool ignore_requested, bool open_dso_components);
/**
* Parse the requested component string and return an pmix_argv of the requested
* (or not requested) components.
*/
PMIX_EXPORT int pmix_mca_base_component_parse_requested(const char *requested, bool *include_mode,
char ***requested_component_names);
/**
* Filter a list of components based on a comma-delimted list of names
*
* @param[in] framework
*
* @returns PMIX_SUCCESS On success
* @returns PMIX_ERR_NOT_FOUND If some component in {filter_names} is not found in
* {components}. Does not apply to negated filters.
* @returns pmix error code On other error.
*
* This function closes and releases any components that do not match the filter_name and
* filter flags.
*/
PMIX_EXPORT int pmix_mca_base_components_filter(pmix_mca_base_framework_t *framework);
/* Safely release some memory allocated by pmix_mca_base_component_find()
(i.e., is safe to call even if you never called
pmix_mca_base_component_find()). */
PMIX_EXPORT int pmix_mca_base_component_find_finalize(void);
/* pmix_mca_base_components_register.c */
PMIX_EXPORT int
pmix_mca_base_framework_components_register(struct pmix_mca_base_framework_t *framework,
pmix_mca_base_register_flag_t flags);
/* pmix_mca_base_components_open.c */
PMIX_EXPORT int pmix_mca_base_show_load_errors_init(void);
PMIX_EXPORT int pmix_mca_base_show_load_errors_finalize(void);
PMIX_EXPORT bool pmix_mca_base_show_load_errors(const char *framework_name,
const char *component_name);
PMIX_EXPORT int pmix_mca_base_framework_components_open(struct pmix_mca_base_framework_t *framework,
pmix_mca_base_open_flag_t flags);
PMIX_EXPORT int pmix_mca_base_components_open(const char *type_name, int output_id,
const pmix_mca_base_component_t **static_components,
pmix_list_t *components_available,
bool open_dso_components);
/* pmix_mca_base_components_close.c */
/**
* Close and release a component.
*
* @param[in] component Component to close
* @param[in] output_id Output id for debugging output
*
* After calling this function the component may no longer be used.
*/
PMIX_EXPORT void pmix_mca_base_component_close(const pmix_mca_base_component_t *component,
int output_id);
/**
* Release a component without closing it.
* @param[in] component Component to close
* @param[in] output_id Output id for debugging output
*
* After calling this function the component may no longer be used.
*/
PMIX_EXPORT void pmix_mca_base_component_unload(const pmix_mca_base_component_t *component,
int output_id);
PMIX_EXPORT int pmix_mca_base_components_close(int output_id, pmix_list_t *components_available,
const pmix_mca_base_component_t *skip);
PMIX_EXPORT int
pmix_mca_base_framework_components_close(struct pmix_mca_base_framework_t *framework,
const pmix_mca_base_component_t *skip);
END_C_DECLS
#endif /* MCA_BASE_H */

View File

@@ -0,0 +1,87 @@
/* -*- Mode: C; c-basic-offset:4 ; indent-tabs-mode:nil -*- */
/*
* Copyright (c) 2020 Google, LLC. All rights reserved.
* Copyright (c) 2021-2022 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
#ifndef PMIX_MCA_BASE_ALIAS_H
#define PMIX_MCA_BASE_ALIAS_H
#include "src/include/pmix_config.h"
#include "src/class/pmix_list.h"
BEGIN_C_DECLS
enum pmix_mca_base_alias_flags_t {
PMIX_MCA_BASE_ALIAS_FLAG_NONE = 0,
/** The aliased name has been deprecated. */
PMIX_MCA_BASE_ALIAS_FLAG_DEPRECATED = 1,
};
typedef enum pmix_mca_base_alias_flags_t pmix_mca_base_alias_flags_t;
struct pmix_mca_base_alias_item_t {
pmix_list_item_t super;
/** Name aias. */
char *component_alias;
/** Alias flags. */
uint32_t alias_flags;
};
typedef struct pmix_mca_base_alias_item_t pmix_mca_base_alias_item_t;
PMIX_CLASS_DECLARATION(pmix_mca_base_alias_item_t);
struct pmix_mca_base_alias_t {
pmix_object_t super;
/** List of name aliases. */
pmix_list_t component_aliases;
};
typedef struct pmix_mca_base_alias_t pmix_mca_base_alias_t;
PMIX_CLASS_DECLARATION(pmix_mca_base_alias_t);
/**
* @brief Create a alias for a component name.
*
* @param[in] project Project name (may be NULL)
* @param[in] framework Framework name (may be NULL)
* @param[in] component_name Name of component to alias (may not be NULL)
* @param[in] component_alias Aliased name (may not be NULL)
* @param[in] alias_flags Flags (see mca_base_alias_flags_t)
*
* This function aliases one component name to another. When aliased
* any variable registered with this project, framework, and
* component_name will have synonyms created. For example, if
* pmix_btl_vader is aliased to sm then registers a variable
* named btl_vader_flags then a synonym will be created with the
* name btl_sm_flags. If an alias is registered early enough
* (during framework registration for example) then the alias can
* also be used for component selection. In the previous example
* --mca btl vader and --mca btl sm would select the same
* component if the synonym is registered in the btl framework
* registration function.
*/
PMIX_EXPORT int pmix_mca_base_alias_register(const char *project, const char *framework,
const char *component_name,
const char *component_alias, uint32_t alias_flags);
/**
* @brief Check for aliases for a component.
*
* @param[in] project Project name (may be NULL)
* @param[in] frameworek Framework name (may be NULL)
* @param[in] component_name Component name (may not be NULL)
*/
PMIX_EXPORT const pmix_mca_base_alias_t *
pmix_mca_base_alias_lookup(const char *project, const char *framework, const char *component_name);
PMIX_EXPORT void pmix_mca_base_alias_cleanup(void);
#endif /* PMIX_MCA_BASE_ALIAS_H */

View File

@@ -0,0 +1,149 @@
/* -*- Mode: C; c-basic-offset:4 ; indent-tabs-mode:nil -*- */
/*
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2005 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2015 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2015 Los Alamos National Security, LLC. All rights
* reserved.
* Copyright (c) 2016-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2021-2022 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
/**
* @file pmix_mca_base_component_repository.h
*
* This file provide the external interface to our base component
* module. Most of the components that depend on it, will use the
* retain_component() function to increase the reference count on a
* particular component (as opposed to the retain() function, which is
* internal to the pmix/mca/base). But it's convenient to have all
* the functions exported from one header file rather than to separate
* retain_component() and retain() into two separate header files
* (i.e., have a separate header file just for retain()).
*/
#ifndef PMIX_MCA_BASE_COMPONENT_REPOSITORY_H
#define PMIX_MCA_BASE_COMPONENT_REPOSITORY_H
#include "src/include/pmix_config.h"
#include "src/mca/pdl/base/base.h"
#include "src/mca/pdl/pdl.h"
BEGIN_C_DECLS
struct pmix_mca_base_component_repository_item_t {
pmix_list_item_t super;
char *ri_project;
char ri_type[PMIX_MCA_BASE_MAX_TYPE_NAME_LEN + 1];
char ri_name[PMIX_MCA_BASE_MAX_COMPONENT_NAME_LEN + 1];
char *ri_path;
char *ri_base;
pmix_pdl_handle_t *ri_dlhandle;
const pmix_mca_base_component_t *ri_component_struct;
int ri_refcnt;
};
typedef struct pmix_mca_base_component_repository_item_t pmix_mca_base_component_repository_item_t;
PMIX_EXPORT PMIX_CLASS_DECLARATION(pmix_mca_base_component_repository_item_t);
/*
* Structure to track information about why a component failed to load.
*/
struct pmix_mca_base_failed_component_t {
pmix_list_item_t super;
pmix_mca_base_component_repository_item_t *comp;
char *error_msg;
};
typedef struct pmix_mca_base_failed_component_t pmix_mca_base_failed_component_t;
PMIX_EXPORT PMIX_CLASS_DECLARATION(pmix_mca_base_failed_component_t);
/**
* @brief initialize the component repository
*
* This function must be called before any frameworks are registered or
* opened. It is responsible for setting up the repository of dynamically
* loaded components. The initial search path is taken from the
* pmix_mca_base_component_path MCA parameter. pmix_mca_base_open () is a
* prerequisite call as it registers the pmix_mca_base_component_path parameter.
*/
PMIX_EXPORT int pmix_mca_base_component_repository_init(void);
/**
* @brief add search path for dynamically loaded components
*
* @param[in] path delimited list of search paths to add
*/
PMIX_EXPORT int pmix_mca_base_component_repository_add(const char *project,
const char *path);
/**
* @brief return the list of components that match a given framework
*
* @param[in] framework framework to match
* @param[out] framework_components components that match this framework
*
* The list returned in {framework_components} is owned by the component
* repository and CAN NOT be modified by the caller.
*/
PMIX_EXPORT int
pmix_mca_base_component_repository_get_components(pmix_mca_base_framework_t *framework,
pmix_list_t **framework_components);
/**
* @brief finalize the mca component repository
*/
PMIX_EXPORT void pmix_mca_base_component_repository_finalize(void);
/**
* @brief open the repository item and add it to the framework's component
* list
*
* @param[in] framework framework that matches the component
* @param[in] ri dynamic component to open
*/
PMIX_EXPORT int
pmix_mca_base_component_repository_open(pmix_mca_base_framework_t *framework,
pmix_mca_base_component_repository_item_t *ri);
/**
* @brief Reduce the reference count of a component and dlclose it if necessary
*/
PMIX_EXPORT void
pmix_mca_base_component_repository_release(const pmix_mca_base_component_t *component);
/**
* @brief Increase the reference count of a component
*
* Each component repository item starts with a reference count of 0. This ensures that
* when a framework closes it's components the repository items are all correctly
* dlclosed. This function can be used to prevent the dlclose if a component is needed
* after its framework has closed the associated component. Users of this function
* should call pmix_mca_base_component_repository_release() once they are finished with the
* component.
*
* @note all components are automatically unloaded by the
* pmix_mca_base_component_repository_finalize() call.
*/
PMIX_EXPORT int pmix_mca_base_component_repository_retain_component(const char *type,
const char *name);
END_C_DECLS
#endif /* MCA_BASE_COMPONENT_REPOSITORY_H */

View File

@@ -0,0 +1,244 @@
/* -*- Mode: C; c-basic-offset:4 ; indent-tabs-mode:nil -*- */
/*
* Copyright (c) 2012-2015 Los Alamos National Security, LLC. All rights
* reserved.
* Copyright (c) 2016-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2021-2022 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
#if !defined(PMIX_MCA_BASE_FRAMEWORK_H)
# define PMIX_MCA_BASE_FRAMEWORK_H
# include "src/include/pmix_config.h"
# include "src/class/pmix_list.h"
# include "src/mca/mca.h"
/*
* Register and open flags
*/
enum pmix_mca_base_register_flag_t {
PMIX_MCA_BASE_REGISTER_DEFAULT = 0,
/** Register all components (ignore selection MCA variables) */
PMIX_MCA_BASE_REGISTER_ALL = 1,
/** Do not register DSO components */
PMIX_MCA_BASE_REGISTER_STATIC_ONLY = 2
};
typedef enum pmix_mca_base_register_flag_t pmix_mca_base_register_flag_t;
enum pmix_mca_base_open_flag_t {
PMIX_MCA_BASE_OPEN_DEFAULT = 0,
/** Find components in pmix_mca_base_components_find. Used by
pmix_mca_base_framework_open() when NOREGISTER is specified
by the framework */
PMIX_MCA_BASE_OPEN_FIND_COMPONENTS = 1,
/** Do not open DSO components */
PMIX_MCA_BASE_OPEN_STATIC_ONLY = 2,
};
typedef enum pmix_mca_base_open_flag_t pmix_mca_base_open_flag_t;
/**
* Register the MCA framework parameters
*
* @param[in] flags Registration flags (see mca/base/pmix_base.h)
*
* @retval PMIX_SUCCESS on success
* @retval pmix error code on failure
*
* This function registers all framework MCA parameters. This
* function should not call pmix_mca_base_framework_components_register().
*
* Frameworks are NOT required to provide this function. It
* may be NULL.
*/
typedef int (*pmix_mca_base_framework_register_params_fn_t)(pmix_mca_base_register_flag_t flags);
/**
* Initialize the MCA framework
*
* @retval PMIX_SUCCESS Upon success
* @retval PMIX_ERROR Upon failure
*
* This must be the first function invoked in the MCA framework.
* It initializes the MCA framework, finds and opens components,
* populates the components list, etc.
*
* This function is invoked during pmix_init() and during the
* initialization of the special case of the ompi_info command.
*
* This function fills in the components framework value, which
* is a list of all components that were successfully opened.
* This variable should \em only be used by other framework base
* functions or by ompi_info -- it is not considered a public
* interface member -- and is only mentioned here for completeness.
*
* Any resources allocated by this function must be freed
* in the framework close function.
*
* Frameworks are NOT required to provide this function. It may
* be NULL. If a framework does not provide an open function the
* default behavior of pmix_mca_base_framework_open() is to call
* pmix_mca_base_framework_components_open(). If a framework provides
* an open function it will need to call pmix_mca_base_framework_components_open()
* if it needs to open any components.
*/
typedef int (*pmix_mca_base_framework_open_fn_t)(pmix_mca_base_open_flag_t flags);
/**
* Shut down the MCA framework.
*
* @retval PMIX_SUCCESS Always
*
* This function should shut downs everything in the MCA
* framework, and is called during pmix_finalize() and the
* special case of the ompi_info command.
*
* It must be the last function invoked on the MCA framework.
*
* Frameworks are NOT required to provide this function. It may
* be NULL. If a framework does not provide a close function the
* default behavior of pmix_mca_base_framework_close() is to call
* pmix_mca_base_framework_components_close(). If a framework provide
* a close function it will need to call pmix_mca_base_framework_components_close()
* if any components were opened.
*/
typedef int (*pmix_mca_base_framework_close_fn_t)(void);
typedef enum {
PMIX_MCA_BASE_FRAMEWORK_FLAG_DEFAULT = 0,
/** Don't register any variables for this framework */
PMIX_MCA_BASE_FRAMEWORK_FLAG_NOREGISTER = 1,
/** Internal. Don't set outside pmix_mca_base_framework.h */
PMIX_MCA_BASE_FRAMEWORK_FLAG_REGISTERED = 2,
/** Framework does not have any DSO components */
PMIX_MCA_BASE_FRAMEWORK_FLAG_NO_DSO = 4,
/** Internal. Don't set outside pmix_mca_base_framework.h */
PMIX_MCA_BASE_FRAMEWORK_FLAG_OPEN = 8,
/**
* The upper 16 bits are reserved for project specific flags.
*/
} pmix_mca_base_framework_flags_t;
typedef struct pmix_mca_base_framework_t {
/** Project name for this component (ex "pmix") */
char *framework_project;
/** Framework name */
char *framework_name;
/** Description of this framework or NULL */
const char *framework_description;
/** Framework register function or NULL if the framework
and all its components have nothing to register */
pmix_mca_base_framework_register_params_fn_t framework_register;
/** Framework open function or NULL */
pmix_mca_base_framework_open_fn_t framework_open;
/** Framework close function or NULL */
pmix_mca_base_framework_close_fn_t framework_close;
/** Framework flags (future use) set to 0 */
pmix_mca_base_framework_flags_t framework_flags;
/** Framework open count */
int framework_refcnt;
/** List of static components */
const pmix_mca_base_component_t **framework_static_components;
/** Component selection. This will be registered with the MCA
variable system and should be either NULL (all components) or
a heap allocated, comma-delimited list of components. */
char *framework_selection;
/** Verbosity level (0-100) */
int framework_verbose;
/** Pmix output for this framework (or -1) */
int framework_output;
/** List of selected components (filled in by pmix_mca_base_framework_register()
or pmix_mca_base_framework_open() */
pmix_list_t framework_components;
/** List of components that failed to load */
pmix_list_t framework_failed_components;
} pmix_mca_base_framework_t;
/**
* Register a framework with MCA.
*
* @param[in] framework framework to register
*
* @retval PMIX_SUCCESS Upon success
* @retval PMIX_ERROR Upon failure
*
* Call a framework's register function.
*/
PMIX_EXPORT int pmix_mca_base_framework_register(pmix_mca_base_framework_t *framework,
pmix_mca_base_register_flag_t flags);
/**
* Open a framework
*
* @param[in] framework framework to open
*
* @retval PMIX_SUCCESS Upon success
* @retval PMIX_ERROR Upon failure
*
* Call a framework's open function.
*/
PMIX_EXPORT int pmix_mca_base_framework_open(pmix_mca_base_framework_t *framework,
pmix_mca_base_open_flag_t flags);
/**
* Close a framework
*
* @param[in] framework framework to close
*
* @retval PMIX_SUCCESS Upon success
* @retval PMIX_ERROR Upon failure
*
* Call a framework's close function.
*/
PMIX_EXPORT int pmix_mca_base_framework_close(pmix_mca_base_framework_t *framework);
/**
* Check if a framework is already registered
*
* @param[in] framework framework to query
*
* @retval true if the framework's mca variables are registered
* @retval false if not
*/
PMIX_EXPORT bool pmix_mca_base_framework_is_registered(struct pmix_mca_base_framework_t *framework);
/**
* Check if a framework is already open
*
* @param[in] framework framework to query
*
* @retval true if the framework is open
* @retval false if not
*/
PMIX_EXPORT bool pmix_mca_base_framework_is_open(struct pmix_mca_base_framework_t *framework);
/**
* Macro to declare an MCA framework
*
* Example:
* PMIX_MCA_BASE_FRAMEWORK_DECLARE(pmix, foo, NULL, pmix_foo_open, pmix_foo_close,
* MCA_BASE_FRAMEWORK_FLAG_LAZY)
*/
# define PMIX_MCA_BASE_FRAMEWORK_DECLARE(project, name, description, registerfn, openfn, \
closefn, static_components, flags) \
pmix_mca_base_framework_t project##_##name##_base_framework \
= {.framework_project = #project, \
.framework_name = #name, \
.framework_description = description, \
.framework_register = registerfn, \
.framework_open = openfn, \
.framework_close = closefn, \
.framework_flags = flags, \
.framework_refcnt = 0, \
.framework_static_components = static_components, \
.framework_selection = NULL, \
.framework_verbose = 0, \
.framework_output = -1}
#endif /* PMIX_MCA_BASE_FRAMEWORK_H */

View File

@@ -0,0 +1,594 @@
/* -*- Mode: C; c-basic-offset:4 ; indent-tabs-mode:nil -*- */
/*
* Copyright (c) 2004-2007 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2006 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2008-2011 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2012-2015 Los Alamos National Security, LLC. All rights
* reserved.
* Copyright (c) 2016-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2021-2022 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
/** @file
* This file presents the MCA variable interface.
*
* Note that there are two scopes for MCA variables: "normal" and
* attributes. Specifically, all MCA variables are "normal" -- some
* are special and may also be found on attributes on communicators,
* datatypes, or windows.
*
* In general, these functions are intended to be used as follows:
*
* - Creating MCA variables
* -# Register a variable, get an index back
* - Using MCA variables
* -# Lookup a "normal" variable value on a specific index, or
* -# Lookup an attribute variable on a specific index and
* communicator / datatype / window.
*
* MCA variables can be defined in multiple different places. As
* such, variables are \em resolved to find their value. The order
* of resolution is as follows:
*
* - An "override" location that is only available to be set via the
* pmix_mca_base_param API.
* - Look for an environment variable corresponding to the MCA
* variable.
* - See if a file contains the MCA variable (MCA variable files are
* read only once -- when the first time any mca_param_t function is
* invoked).
* - If nothing else was found, use the variable's default value.
*
* Note that there is a second header file (pmix_mca_base_vari.h)
* that contains several internal type declarations for the variable
* system. The internal file is only used within the variable system
* itself; it should not be required by any other PMIX entities.
*/
#ifndef PMIX_MCA_BASE_VAR_H
#define PMIX_MCA_BASE_VAR_H
#include "src/include/pmix_config.h"
#include "src/class/pmix_list.h"
#include "src/class/pmix_value_array.h"
#include "src/mca/base/pmix_mca_base_framework.h"
#include "src/mca/base/pmix_mca_base_var_enum.h"
#include "src/mca/base/pmix_mca_base_var_group.h"
#include "src/mca/mca.h"
/**
* The types of MCA variables.
*/
typedef enum {
/** The variable is of type int. */
PMIX_MCA_BASE_VAR_TYPE_INT,
/** The variable is of type unsigned int */
PMIX_MCA_BASE_VAR_TYPE_UNSIGNED_INT,
/** The variable is of type unsigned long */
PMIX_MCA_BASE_VAR_TYPE_UNSIGNED_LONG,
/** The variable is of type unsigned long long */
PMIX_MCA_BASE_VAR_TYPE_UNSIGNED_LONG_LONG,
/** The variable is of type size_t */
PMIX_MCA_BASE_VAR_TYPE_SIZE_T,
/** The variable is of type string. */
PMIX_MCA_BASE_VAR_TYPE_STRING,
/** The variable is of type string and contains version. */
PMIX_MCA_BASE_VAR_TYPE_VERSION_STRING,
/** The variable is of type bool */
PMIX_MCA_BASE_VAR_TYPE_BOOL,
/** The variable is of type double */
PMIX_MCA_BASE_VAR_TYPE_DOUBLE,
/** Maximum variable type. */
PMIX_MCA_BASE_VAR_TYPE_MAX
} pmix_mca_base_var_type_t;
PMIX_EXPORT extern const char *pmix_var_type_names[];
/**
* Source of an MCA variable's value
*/
typedef enum {
/** The default value */
PMIX_MCA_BASE_VAR_SOURCE_DEFAULT,
/** The value came from the command line */
PMIX_MCA_BASE_VAR_SOURCE_COMMAND_LINE,
/** The value came from the environment */
PMIX_MCA_BASE_VAR_SOURCE_ENV,
/** The value came from a file */
PMIX_MCA_BASE_VAR_SOURCE_FILE,
/** The value came a "set" API call */
PMIX_MCA_BASE_VAR_SOURCE_SET,
/** The value came from the override file */
PMIX_MCA_BASE_VAR_SOURCE_OVERRIDE,
/** Maximum source type */
PMIX_MCA_BASE_VAR_SOURCE_MAX
} pmix_mca_base_var_source_t;
typedef enum {
PMIX_MCA_BASE_VAR_SYN_FLAG_DEPRECATED = 0x0001
} pmix_mca_base_var_syn_flag_t;
typedef enum {
PMIX_MCA_BASE_VAR_FLAG_NONE = 0x0000,
/** Variable is deprecated */
PMIX_MCA_BASE_VAR_FLAG_DEPRECATED = 0x0008,
/** Variable is valid */
PMIX_MCA_BASE_VAR_FLAG_VALID = 0x00010000,
/** Variable is a synonym */
PMIX_MCA_BASE_VAR_FLAG_SYNONYM = 0x00020000,
/** mbv_source_file needs to be freed */
PMIX_MCA_BASE_VAR_FLAG_SOURCE_FILE_NEEDS_FREE = 0x00040000
} pmix_mca_base_var_flag_internal_t;
/**
* Types for MCA parameters.
*/
typedef union {
/** integer value */
int intval;
/** unsigned int value */
unsigned int uintval;
/** string value */
char *stringval;
/** boolean value */
bool boolval;
/** unsigned long value */
unsigned long ulval;
/** unsigned long long value */
unsigned long long ullval;
/** size_t value */
size_t sizetval;
/** double value */
double lfval;
} pmix_mca_base_var_storage_t;
/**
* Entry for holding information about an MCA variable.
*/
struct pmix_mca_base_var_t {
/** Allow this to be an PMIX OBJ */
pmix_object_t super;
/** Variable index. This will remain constant until pmix_mca_base_var_finalize()
is called. */
int mbv_index;
/** Group index. This will remain constant until pmix_mca_base_var_finalize()
is called. This variable will be deregistered if the associated group
is deregistered with pmix_mca_base_var_group_deregister() */
int mbv_group_index;
/** Enum indicating the type of the variable (integer, string, boolean) */
pmix_mca_base_var_type_t mbv_type;
/** String of the variable name */
char *mbv_variable_name;
/** Full variable name, in case it is not <framework>_<component>_<param> */
char *mbv_full_name;
/** Long variable name <project>_<framework>_<component>_<name> */
char *mbv_long_name;
char *mbv_prefix;
/** List of synonym names for this variable. This *must* be a
pointer (vs. a plain pmix_list_t) because we copy this whole
struct into a new var for permanent storage
(pmix_vale_array_append_item()), and the internal pointers in
the pmix_list_t will be invalid when that happens. Hence, we
simply keep a pointer to an external pmix_list_t. Synonyms
are uncommon enough that this is not a big performance hit. */
pmix_value_array_t mbv_synonyms;
/** Variable flags */
pmix_mca_base_var_flag_internal_t mbv_flags;
/** Source of the current value */
pmix_mca_base_var_source_t mbv_source;
/** Synonym for */
int mbv_synonym_for;
/** Variable description */
char *mbv_description;
/** File the value came from */
char *mbv_source_file;
/** Value enumerator (only valid for integer variables) */
pmix_mca_base_var_enum_t *mbv_enumerator;
/** Bind value for this variable (0 - none) */
int mbv_bind;
/** Storage for this variable */
pmix_mca_base_var_storage_t *mbv_storage;
/** File value structure */
void *mbv_file_value;
};
/**
* Convenience typedef.
*/
typedef struct pmix_mca_base_var_t pmix_mca_base_var_t;
/*
* Global functions for MCA
*/
BEGIN_C_DECLS
/**
* Object declarayion for pmix_mca_base_var_t
*/
PMIX_EXPORT PMIX_CLASS_DECLARATION(pmix_mca_base_var_t);
/**
* Initialize the MCA variable system.
*
* @retval PMIX_SUCCESS
*
* This function initializes the MCA variable system. It is
* invoked internally (by pmix_mca_base_open()) and is only documented
* here for completeness.
*/
PMIX_EXPORT int pmix_mca_base_var_init(void);
/**
* Register an MCA variable
*
* @param[in] project_name The name of the project associated with
* this variable
* @param[in] framework_name The name of the framework associated with
* this variable
* @param[in] component_name The name of the component associated with
* this variable
* @param[in] variable_name The name of this variable
* @param[in] description A string describing the use and valid
* values of the variable (string).
* @param[in] type The type of this variable (string, int, bool).
* @param[in] enumerator Enumerator describing valid values.
* @param[in] bind Hint for MPIT to specify type of binding (0 = none)
* @param[in] flags Flags for this variable.
* @param[in] info_lvl Info level of this variable
* @param[in] scope Indicates the scope of this variable
* @param[in,out] storage Pointer to the value's location.
*
* @retval index Index value representing this variable.
* @retval PMIX_ERR_OUT_OF_RESOURCE Upon failure to allocate memory.
* @retval PMIX_ERROR Upon failure to register the variable.
*
* This function registers an MCA variable and associates it
* with a specific group.
*
* {description} is a string of arbitrary length (verbose is good!)
* for explaining what the variable is for and what its valid values
* are. This message is used in help messages, such as the output
* from the ompi_info executable. The {description} string is copied
* internally; the caller can free {description} upon successful
* return.
*
* {enumerator} is either NULL or a handle that was created via
* pmix_mca_base_var_enum_create(), and describes the valid values of an
* integer variable (i.e., one with type MCA_BASE_VAR_TYPE_INT). When
* a non-NULL {enumerator} is used, the value set for this variable by
* the user will be compared against the values in the enumerator.
* The MCA variable system will allow the parameter to be set to
* either one of the enumerator values (0, 1, 2, etc) or a string
* representing one of those values. {enumerator} is retained until
* either the variable is deregistered using
* pmix_mca_base_var_deregister(), pmix_mca_base_var_group_deregister(), or
* pmix_mca_base_var_finalize(). {enumerator} should be NULL for
* parameters that do not support enumerated values.
*
* {flags} indicate attributes of this variable (internal, settable,
* default only, etc.), as listed below.
*
* If MCA_BASE_VAR_FLAG_INTERNAL is set in {flags}, this variable
* is not shown by default in the output of ompi_info. That is,
* this variable is considered internal to the PMIX implementation
* and is not supposed to be viewed / changed by the user.
*
* If MCA_BASE_VAR_FLAG_DEFAULT_ONLY is set in {flags}, then the value
* provided in storage will not be modified by the MCA variable system
* (i.e., users cannot set the value of this variable via CLI
* parameter, environment variable, file, etc.). It is up to the
* caller to specify (using the scope) if this value may change
* (MCA_BASE_VAR_SCOPE_READONLY) or remain constant
* (MCA_BASE_VAR_SCOPE_CONSTANT). MCA_BASE_VAR_FLAG_DEFAULT_ONLY must
* not be specified with MCA_BASE_VAR_FLAG_SETTABLE.
*
* Set MCA_BASE_VAR_FLAG_DEPRECATED in {flags} to indicate that
* this variable name is deprecated. The user will get a warning
* if they set this variable.
*
* {scope} is for informational purposes to indicate how this variable
* can be set, or if it is considered constant or readonly (which, by
* MPI_T's definitions, are different things). See the comments in
* the description of pmix_mca_base_var_scope_t for information about the
* different scope meanings.
*
* {storage} points to a (char *), (int), or (bool) where the value of
* this variable is stored ({type} indicates the type of this
* pointer). The location pointed to by {storage} must exist until
* the variable is deregistered. Note that the initial value in
* {storage} may be overwritten if the MCA_BASE_VAR_FLAG_DEFAULT_ONLY
* flag is not set (e.g., if the user sets this variable via CLI
* option, environment variable, or file value). If input value of
* {storage} points to a (char *), the pointed-to string will be
* duplicated and maintained internally by the MCA variable system;
* the caller may free the original string after this function returns
* successfully.
*/
PMIX_EXPORT int pmix_mca_base_var_register(const char *project_name, const char *framework_name,
const char *component_name, const char *variable_name,
const char *description, pmix_mca_base_var_type_t type,
void *storage);
/**
* Convenience function for registering a variable associated with a
* component.
*
* While quite similar to pmix_mca_base_var_register(), there is one key
* difference: vars registered this this function will automatically
* be unregistered / made unavailable when that component is closed by
* its framework.
*/
PMIX_EXPORT int pmix_mca_base_component_var_register(
const pmix_mca_base_component_t *component, const char *variable_name, const char *description,
pmix_mca_base_var_type_t type, void *storage);
/**
* Convenience function for registering a variable associated with a framework. This
* function is equivalent to pmix_mca_base_var_register with component_name = "base" and
* with the MCA_BASE_VAR_FLAG_DWG set. See pmix_mca_base_var_register().
*/
PMIX_EXPORT int pmix_mca_base_framework_var_register(
const pmix_mca_base_framework_t *framework, const char *variable_name, const char *help_msg,
pmix_mca_base_var_type_t type, void *storage);
/**
* Register a synonym name for an MCA variable.
*
* @param[in] synonym_for The index of the original variable. This index
* must not refer to a synonym.
* @param[in] project_name The project this synonym belongs to. Should
* not be NULL (except for legacy reasons).
* @param[in] framework_name The framework this synonym belongs to.
* @param[in] component_name The component this synonym belongs to.
* @param[in] synonym_name The synonym name.
* @param[in] flags Flags for this synonym.
*
* @returns index Variable index for new synonym on success.
* @returns PMIX_ERR_BAD_VAR If synonym_for does not reference a valid
* variable.
* @returns PMIX_ERR_OUT_OF_RESOURCE If memory could not be allocated.
* @returns PMIX_ERROR For all other errors.
*
* Upon success, this function creates a synonym MCA variable
* that will be treated almost exactly like the original. The
* type (int or string) is irrelevant; this function simply
* creates a new name that by which the same variable value is
* accessible.
*
* Note that the original variable name has precedence over all
* synonyms. For example, consider the case if variable is
* originally registered under the name "A" and is later
* registered with synonyms "B" and "C". If the user sets values
* for both MCA variable names "A" and "B", the value associated
* with the "A" name will be used and the value associated with
* the "B" will be ignored (and will not even be visible by the
* pmix_mca_base_var_*() API). If the user sets values for both MCA
* variable names "B" and "C" (and does *not* set a value for
* "A"), it is undefined as to which value will be used.
*/
PMIX_EXPORT int pmix_mca_base_var_register_synonym(int synonym_for, const char *project_name,
const char *framework_name,
const char *component_name,
const char *synonym_name,
pmix_mca_base_var_syn_flag_t flags);
/**
* Deregister a MCA variable or synonym
*
* @param vari Index returned from pmix_mca_base_var_register() or
* pmix_mca_base_var_register_synonym().
*
* Deregistering a variable does not free the variable or any memory associated
* with it. All memory will be freed and the variable index released when
* pmix_mca_base_var_finalize() is called.
*
* If an enumerator is associated with this variable it will be dereferenced.
*/
PMIX_EXPORT int pmix_mca_base_var_deregister(int vari);
/**
* Get the current value of an MCA variable.
*
* @param[in] vari Index of variable
* @param[in,out] value Pointer to copy the value to. Can be NULL.
* @param[in,out] value_size Size of memory pointed to by value.
* copied size will be returned in value_size.
* @param[out] source Source of current value. Can be NULL.
* @param[out] source_file Source file for the current value if
* it was set from a file.
*
* @return PMIX_ERROR Upon failure. The contents of value are
* undefined.
* @return PMIX_SUCCESS Upon success. value (if not NULL) will be filled
* with the variable's current value. value_size will contain the size
* copied. source (if not NULL) will contain the source of the variable.
*
* Note: The value can be changed by the registering code without using
* the pmix_mca_base_var_* interface so the source may be incorrect.
*/
PMIX_EXPORT int pmix_mca_base_var_get_value(int vari, void *value,
pmix_mca_base_var_source_t *source,
const char **source_file);
/**
* Find the index for an MCA variable based on its names.
*
* @param project_name Name of the project
* @param type_name Name of the type containing the variable.
* @param component_name Name of the component containing the variable.
* @param param_name Name of the variable.
*
* @retval PMIX_ERROR If the variable was not found.
* @retval vari If the variable was found.
*
* It is not always convenient to widely propagate a variable's index
* value, or it may be necessary to look up the variable from a
* different component. This function can be used to look up the index
* of any registered variable. The returned index can be used with
* pmix_mca_base_var_get() and pmix_mca_base_var_get_value().
*/
PMIX_EXPORT int pmix_mca_base_var_find(const char *project_name, const char *type_name,
const char *component_name, const char *param_name);
/**
* Find the index for a variable based on its full name
*
* @param full_name [in] Full name of the variable
* @param vari [out] Index of the variable
*
* See pmix_mca_base_var_find().
*/
PMIX_EXPORT int pmix_mca_base_var_find_by_name(const char *full_name, int *vari);
/**
* Check that two MCA variables were not both set to non-default
* values.
*
* @param type_a [in] Framework name of variable A (string).
* @param component_a [in] Component name of variable A (string).
* @param param_a [in] Variable name of variable A (string.
* @param type_b [in] Framework name of variable A (string).
* @param component_b [in] Component name of variable A (string).
* @param param_b [in] Variable name of variable A (string.
*
* This function is useful for checking that the user did not set both
* of 2 mutually-exclusive MCA variables.
*
* This function will print an pmix_show_help() message and return
* PMIX_ERR_BAD_VAR if it finds that the two variables both have
* value sources that are not MCA_BASE_VAR_SOURCE_DEFAULT. This
* means that both variables have been set by the user (i.e., they're
* not default values).
*
* Note that pmix_show_help() allows itself to be hooked, so if this
* happens after the aggregated pmix_show_help() system is
* initialized, the messages will be aggregated (w00t).
*
* @returns PMIX_ERR_BAD_VAR if the two variables have sources that
* are not MCA_BASE_VAR_SOURCE_DEFAULT.
* @returns PMIX_SUCCESS otherwise.
*/
PMIX_EXPORT int pmix_mca_base_var_check_exclusive(const char *project, const char *type_a,
const char *component_a, const char *param_a,
const char *type_b, const char *component_b,
const char *param_b);
/**
* Obtain basic info on a single variable (name, help message, etc)
*
* @param[in] vari Valid variable index.
* @param[out] var Storage for the variable pointer.
*
* @retval PMIX_SUCCESS Upon success.
* @retval pmix error code Upon failure.
*
* The returned pointer belongs to the MCA variable system. Do not
* modify/free/retain the pointer.
*/
PMIX_EXPORT int pmix_mca_base_var_get(int vari, const pmix_mca_base_var_t **var);
/**
* Obtain the number of variables that have been registered.
*
* @retval count on success
* @return pmix error code on error
*
* Note: This function does not return the number of valid MCA variables as
* pmix_mca_base_var_deregister() has no impact on the variable count. The count
* returned is equal to the number of calls to pmix_mca_base_var_register with
* unique names. ie. two calls with the same name will not affect the count.
*/
PMIX_EXPORT int pmix_mca_base_var_get_count(void);
/**
* Obtain a list of environment variables describing the all
* valid (non-default) MCA variables and their sources.
*
* @param[out] env A pointer to an argv-style array of key=value
* strings, suitable for use in an environment
* @param[out] num_env A pointer to an int, containing the length
* of the env array (not including the final NULL entry).
*
* @retval PMIX_SUCCESS Upon success.
* @retval PMIX_ERROR Upon failure.
*
* This function is similar to pmix_mca_base_var_dump() except that
* its output is in terms of an argv-style array of key=value
* strings, suitable for using in an environment.
*/
PMIX_EXPORT int pmix_mca_base_var_build_env(char ***env, int *num_env);
/**
* Shut down the MCA variable system (normally only invoked by the
* MCA framework itself).
*
* @returns PMIX_SUCCESS This function never fails.
*
* This function shuts down the MCA variable repository and frees all
* associated memory. No other pmix_mca_base_var*() functions can be
* invoked after this function.
*
* This function is normally only invoked by the MCA framework itself
* when the process is shutting down (e.g., during MPI_FINALIZE). It
* is only documented here for completeness.
*/
PMIX_EXPORT int pmix_mca_base_var_finalize(void);
typedef enum {
/* Dump human-readable strings */
PMIX_MCA_BASE_VAR_DUMP_READABLE = 0,
/* Dump easily parsable strings */
PMIX_MCA_BASE_VAR_DUMP_PARSABLE = 1,
/* Dump simple name=value string */
PMIX_MCA_BASE_VAR_DUMP_SIMPLE = 2
} pmix_mca_base_var_dump_type_t;
/**
* Dump strings describing the MCA variable at an index.
*
* @param[in] vari Variable index
* @param[out] out Array of strings describing this variable
* @param[in] output_type Type of output desired
*
* This function returns an array of strings describing the variable. All strings
* and the array must be freed by the caller.
*/
PMIX_EXPORT int pmix_mca_base_var_dump(int vari, char ***out,
pmix_mca_base_var_dump_type_t output_type);
#define MCA_COMPILETIME_VER "print_compiletime_version"
#define MCA_RUNTIME_VER "print_runtime_version"
PMIX_EXPORT int pmix_mca_base_var_cache_files(bool rel_path_search);
END_C_DECLS
#endif /* PMIX_MCA_BASE_VAR_H */

View File

@@ -0,0 +1,247 @@
/* -*- Mode: C; c-basic-offset:4 ; indent-tabs-mode:nil -*- */
/*
* Copyright (c) 2004-2007 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2006 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2008-2011 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2012-2016 Los Alamos National Security, LLC. All rights
* reserved.
* Copyright (c) 2016-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2021-2022 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
#if !defined(PMIX_MCA_BASE_VAR_ENUM_H)
# define PMIX_MCA_BASE_VAR_ENUM_H
# include "src/include/pmix_config.h"
# include "pmix_common.h"
# include "src/class/pmix_object.h"
typedef struct pmix_mca_base_var_enum_t pmix_mca_base_var_enum_t;
/**
* Get the number of values in the enumerator
*
* @param[in] self the enumerator
* @param[out] count the number of values in the enumerator
*/
typedef int (*pmix_mca_base_var_enum_get_count_fn_t)(pmix_mca_base_var_enum_t *self, int *count);
/**
* Get the value and its string representation for an index 0..get_count()
*
* @param[in] self the enumerator
* @param[in] index the index to get the value of
* @param[out] value integer value
* @param[out] string_value string value
*/
typedef int (*pmix_mca_base_var_enum_get_value_fn_t)(pmix_mca_base_var_enum_t *self, int index,
int *value, const char **string_value);
/**
* Look up the integer value of a string
*
* @param[in] self the enumerator
* @param[in] string_value string to lookup
* @param[out] value integer value for the string
*
* @retval PMIX_SUCCESS if found
* @retval PMIX_ERR_VALUE_OUT_OF_BOUNDS if not
*/
typedef int (*pmix_mca_base_var_enum_vfs_fn_t)(pmix_mca_base_var_enum_t *self,
const char *string_value, int *value);
/**
* Dump a textual representation of all the values in an enumerator
*
* @param[in] self the enumerator
* @param[out] out the string representation
*
* @retval PMIX_SUCCESS on success
* @retval pmix error on error
*/
typedef int (*pmix_mca_base_var_enum_dump_fn_t)(pmix_mca_base_var_enum_t *self, char **out);
/**
* Get the string representation for an enumerator value
*
* @param[in] self the enumerator
* @param[in] value integer value
* @param[out] string_value string value for value
*
* @retval PMIX_SUCCESS on success
* @retval PMIX_ERR_VALUE_OUT_OF_BOUNDS if not found
*
* @long This function returns the string value for a given integer value in the
* {string_value} parameter. The {string_value} parameter may be NULL in which case
* no string is returned. If a string is returned in {string_value} the caller
* must free the string with free().
*/
typedef int (*pmix_mca_base_var_enum_sfv_fn_t)(pmix_mca_base_var_enum_t *self, const int value,
char **string_value);
/**
* The default enumerator class takes in a list of integer-string pairs. If a
* string is read from an environment variable or a file value the matching
* integer value is used for the MCA variable.
*/
struct pmix_mca_base_var_enum_value_t {
int value;
const char *string;
};
typedef struct pmix_mca_base_var_enum_value_t pmix_mca_base_var_enum_value_t;
/**
* enumerator base class
*/
struct pmix_mca_base_var_enum_t {
pmix_object_t super;
/** Is the enumerator statically allocated */
bool enum_is_static;
/** Name of this enumerator. This value is duplicated from the argument provided to
pmix_mca_base_var_enum_create() */
char *enum_name;
/** Get the number of values this enumerator represents. Subclasses should override
the default function. */
pmix_mca_base_var_enum_get_count_fn_t get_count;
/** Get the value and string representation for a particular index. Subclasses should
override the default function */
pmix_mca_base_var_enum_get_value_fn_t get_value;
/** Given a string return corresponding integer value. If the string does not match a
valid value return PMIX_ERR_VALUE_OUT_OF_BOUNDS */
pmix_mca_base_var_enum_vfs_fn_t value_from_string;
/** Given an integer return the corresponding string value. If the integer does not
match a valid value return PMIX_ERR_VALUE_OUT_OF_BOUNDS */
pmix_mca_base_var_enum_sfv_fn_t string_from_value;
/** Dump a textual representation of the enumerator. The caller is responsible for
freeing the string */
pmix_mca_base_var_enum_dump_fn_t dump;
int enum_value_count;
/** Copy of the enumerators values (used by the default functions). This array and
and the strings it contains are freed by the destructor if not NULL. */
pmix_mca_base_var_enum_value_t *enum_values;
};
/**
* The default flag enumerator class takes in a list of integer-string pairs. If a
* string is read from an environment variable or a file value the matching
* flag value is used for the MCA variable. The conflicting_flag is used to
* indicate any flags that should conflict.
*/
struct pmix_mca_base_var_enum_value_flag_t {
/** flag value (must be power-of-two) */
int flag;
/** corresponding string name */
const char *string;
/** conflicting flag(s) if any */
int conflicting_flag;
};
typedef struct pmix_mca_base_var_enum_value_flag_t pmix_mca_base_var_enum_value_flag_t;
/**
* flag enumerator base class
*/
struct pmix_mca_base_var_enum_flag_t {
/** use the existing enumerator interface */
pmix_mca_base_var_enum_t super;
/** flag value(s) */
pmix_mca_base_var_enum_value_flag_t *enum_flags;
};
typedef struct pmix_mca_base_var_enum_flag_t pmix_mca_base_var_enum_flag_t;
/**
* Object declaration for pmix_mca_base_var_enum_t
*/
PMIX_CLASS_DECLARATION(pmix_mca_base_var_enum_t);
/**
* Create a new default enumerator
*
* @param[in] name Name for this enumerator
* @param[in] values List of values terminated with a NULL .string
* member.
* @param[out] enumerator Newly created enumerator.
*
* @retval PMIX_SUCCESS On success
* @retval pmix error code On error
*
* This function creates a value enumerator for integer variables. The
* OUT enumerator value will be a newly OBJ_NEW'ed object that should
* be released by the caller via OBJ_RELEASE.
*
* Note that the output enumerator can be OBJ_RELEASE'd after it has
* been used in a cvar or pvar registration, because the variable
* registration functions will OBJ_RETAIN the enumberator.
*
* Note that all the strings in the values[] array are strdup'ed into
* internal storage, meaning that the caller can free all of the
* strings passed in values[] after pmix_mca_base_var_enum_create()
* returns.
*/
int pmix_mca_base_var_enum_create(const char *name, const pmix_mca_base_var_enum_value_t values[],
pmix_mca_base_var_enum_t **enumerator);
/**
* Create a new default flag enumerator
*
* @param[in] name Name for this enumerator
* @param[in] flags List of flags terminated with a NULL .string
* member.
* @param[out] enumerator Newly created enumerator.
*
* @retval PMIX_SUCCESS On success
* @retval pmix error code On error
*
* This function creates a flag enumerator for integer variables. The
* OUT enumerator value will be a newly OBJ_NEW'ed object that should
* be released by the caller via OBJ_RELEASE.
*
* Note that the output enumerator can be OBJ_RELEASE'd after it has
* been used in a cvar or pvar registration, because the variable
* registration functions will OBJ_RETAIN the enumberator.
*
* Note that all the strings in the values[] array are strdup'ed into
* internal storage, meaning that the caller can free all of the
* strings passed in values[] after pmix_mca_base_var_enum_create()
* returns.
*/
int pmix_mca_base_var_enum_create_flag(const char *name,
const pmix_mca_base_var_enum_value_flag_t flags[],
pmix_mca_base_var_enum_flag_t **enumerator);
/* standard enumerators. it is invalid to call OBJ_RELEASE on any of these enumerators */
/**
* Boolean enumerator
*
* This enumerator maps:
* positive integer, true, yes, enabled, t -> 1
* 0, false, no, disabled, f -> 0
*/
extern pmix_mca_base_var_enum_t pmix_mca_base_var_enum_bool;
/**
* Verbosity level enumerator
*/
extern pmix_mca_base_var_enum_t pmix_mca_base_var_enum_verbose;
#endif /* !defined(MCA_BASE_VAR_ENUM_H) */

View File

@@ -0,0 +1,160 @@
/* -*- Mode: C; c-basic-offset:4 ; indent-tabs-mode:nil -*- */
/*
* Copyright (c) 2004-2007 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2006 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2008-2011 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2012-2013 Los Alamos National Security, LLC. All rights
* reserved.
* Copyright (c) 2016-2017 Intel, Inc. All rights reserved.
* Copyright (c) 2021-2022 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
#ifndef PMIX_MCA_BASE_VAR_GROUP_H
#define PMIX_MCA_BASE_VAR_GROUP_H
#include "src/mca/mca.h"
struct pmix_mca_base_var_group_t {
pmix_list_item_t super;
/** Index of group */
int group_index;
/** Group is valid (registered) */
bool group_isvalid;
/** Group name */
char *group_full_name;
char *group_project;
char *group_framework;
char *group_component;
/** Group help message (description) */
char *group_description;
/** Integer value array of subgroup indices */
pmix_value_array_t group_subgroups;
/** Integer array of group variables */
pmix_value_array_t group_vars;
};
typedef struct pmix_mca_base_var_group_t pmix_mca_base_var_group_t;
/**
* Object declaration for pmix_mca_base_var_group_t
*/
PMIX_EXPORT PMIX_CLASS_DECLARATION(pmix_mca_base_var_group_t);
/**
* Register an MCA variable group
*
* @param[in] project_name Project name for this group.
* @param[in] framework_name Framework name for this group.
* @param[in] component_name Component name for this group.
* @param[in] description Description of this group.
*
* @retval index Unique group index
* @return pmix error code on Error
*
* Create an MCA variable group. If the group already exists
* this call is equivalent to pmix_mca_base_ver_find_group().
*/
PMIX_EXPORT int pmix_mca_base_var_group_register(const char *project_name,
const char *framework_name,
const char *component_name,
const char *description);
/**
* Register an MCA variable group for a component
*
* @param[in] component [in] Pointer to the component for which the
* group is being registered.
* @param[in] description Description of this group.
*
* @retval index Unique group index
* @return pmix error code on Error
*/
PMIX_EXPORT int
pmix_mca_base_var_group_component_register(const pmix_mca_base_component_t *component,
const char *description);
/**
* Deregister an MCA param group
*
* @param group_index [in] Group index from pmix_mca_base_var_group_register (),
* pmix_mca_base_var_group_find().
*
* This call deregisters all associated variables and subgroups.
*/
PMIX_EXPORT int pmix_mca_base_var_group_deregister(int group_index);
/**
* Find an MCA group
*
* @param[in] project_name Project name
* @param[in] framework_name Framework name
* @param[in] component_name Component name
*
* @returns PMIX_SUCCESS if found
* @returns PMIX_ERR_NOT_FOUND if not found
*/
PMIX_EXPORT int pmix_mca_base_var_group_find(const char *project_name, const char *framework_name,
const char *component_name);
/**
* Find an MCA group by its full name
*
* @param[in] full_name Full name of MCA variable group. Ex: shmem_mmap
* @param[out] index Index of group if found
*
* @returns PMIX_SUCCESS if found
* @returns PMIX_ERR_NOT_FOUND if not found
*/
PMIX_EXPORT int pmix_mca_base_var_group_find_by_name(const char *full_name, int *index);
/**
* Get the group at a specified index
*
* @param[in] group_index Group index
* @param[out] group Storage for the group object pointer.
*
* @retval PMIX_ERR_NOT_FOUND If the group specified by group_index does not exist.
* @retval PMIX_SUCCESS If the group is found
*
* The returned pointer belongs to the MCA variable system. Do not modify/release/retain
* the pointer.
*/
PMIX_EXPORT int pmix_mca_base_var_group_get(const int group_index,
const pmix_mca_base_var_group_t **group);
/**
* Get the number of registered MCA groups
*
* @retval count Number of registered MCA groups
*/
PMIX_EXPORT int pmix_mca_base_var_group_get_count(void);
/**
* Get a relative timestamp for the MCA group system
*
* @retval stamp
*
* This value will change if groups or variables are either added or removed.
*/
PMIX_EXPORT int pmix_mca_base_var_group_get_stamp(void);
#endif /* PMIX_MCA_BASE_VAR_GROUP_H */

View File

@@ -0,0 +1,150 @@
/* -*- Mode: C; c-basic-offset:4 ; indent-tabs-mode:nil -*- */
/*
* Copyright (c) 2004-2007 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2006 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2008 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2012-2013 Los Alamos National Security, LLC. All rights
* reserved.
* Copyright (c) 2016-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2021-2023 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
/**
* @file
*
* This is the private declarations for the MCA variable system.
* This file is internal to the MCA variable system and should not
* need to be used by any other elements in PMIX except the
* special case of the ompi_info command.
*
* All the rest of the doxygen documentation in this file is marked as
* "internal" and won't show up unless you specifically tell doxygen
* to generate internal documentation (by default, it is skipped).
*/
#ifndef PMIX_MCA_BASE_VAR_INTERNAL_H
#define PMIX_MCA_BASE_VAR_INTERNAL_H
#include "src/include/pmix_config.h"
#include "src/class/pmix_hash_table.h"
#include "src/class/pmix_list.h"
#include "src/class/pmix_object.h"
#include "src/class/pmix_pointer_array.h"
#include "src/class/pmix_value_array.h"
#include "src/mca/base/pmix_mca_base_var.h"
BEGIN_C_DECLS
/* Internal flags start at bit 16 */
#define PMIX_MCA_BASE_VAR_FLAG_EXTERNAL_MASK 0x0000ffff
#define PMIX_VAR_FLAG_ISSET(var, flag) (!!((var).mbp_flags & (flag)))
#define PMIX_VAR_IS_VALID(var) (!!((var).mbv_flags & PMIX_MCA_BASE_VAR_FLAG_VALID))
#define PMIX_VAR_IS_SYNONYM(var) (!!((var).mbv_flags & PMIX_MCA_BASE_VAR_FLAG_SYNONYM))
#define PMIX_VAR_IS_DEPRECATED(var) (!!((var).mbv_flags & PMIX_MCA_BASE_VAR_FLAG_DEPRECATED))
PMIX_EXPORT extern const char *pmix_var_type_names[];
PMIX_EXPORT extern const size_t pmix_var_type_sizes[];
PMIX_EXPORT extern bool pmix_mca_base_var_initialized;
PMIX_EXPORT extern pmix_list_t pmix_mca_base_var_file_values;
PMIX_EXPORT extern pmix_list_t pmix_mca_base_var_override_values;
/**
* \internal
*
* Structure for holding param names and values read in from files.
*/
struct pmix_mca_base_var_file_value_t {
/** Allow this to be an PMIX OBJ */
pmix_list_item_t super;
/** Parameter name */
char *mbvfv_var;
/** Parameter value */
char *mbvfv_value;
/** File it came from */
char *mbvfv_file;
/** Line it came from */
int mbvfv_lineno;
};
/**
* \internal
*
* Convenience typedef
*/
typedef struct pmix_mca_base_var_file_value_t pmix_mca_base_var_file_value_t;
/**
* Object declaration for pmix_mca_base_var_file_value_t
*/
PMIX_CLASS_DECLARATION(pmix_mca_base_var_file_value_t);
/**
* \internal
*
* Get a group
*
* @param[in] group_index Group index
* @param[out] group Returned group if it exists
* @param[in] invalidok Return group even if it has been deregistered
*/
PMIX_EXPORT int pmix_mca_base_var_group_get_internal(const int group_index,
pmix_mca_base_var_group_t **group,
bool invalidok);
/**
* \internal
*
* Parse a parameter file.
*/
PMIX_EXPORT int pmix_mca_base_parse_paramfile(const char *paramfile, pmix_list_t *list);
/**
* \internal
*
* Add a variable to a group
*/
PMIX_EXPORT int pmix_mca_base_var_group_add_var(const int group_index, const int param_index);
/**
* \internal
*
* Generate a full name with _ between all of the non-NULL arguments
*/
PMIX_EXPORT int pmix_mca_base_var_generate_full_name4(const char *project, const char *framework,
const char *component, const char *variable,
char **full_name);
/**
* \internal
*
* Call save_value callback for generated internal mca parameter storing env variables
*/
PMIX_EXPORT int pmix_mca_base_internal_env_store(void);
/**
* \internal
*
* Initialize/finalize MCA variable groups
*/
PMIX_EXPORT int pmix_mca_base_var_group_init(void);
PMIX_EXPORT int pmix_mca_base_var_group_finalize(void);
END_C_DECLS
#endif /* PMIX_MCA_BASE_VAR_INTERNAL_H */

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,457 @@
/* -*- Mode: C; c-basic-offset:4 ; -*- */
/*
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2005 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2012 Los Alamos National Security, Inc. All rights reserved.
* Copyright (c) 2013-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2015 Research Organization for Information Science
* and Technology (RIST). All rights reserved.
* Copyright (c) 2016 Mellanox Technologies, Inc.
* All rights reserved.
* Copyright (c) 2021-2022 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
/**
* @file
*
* Data packing subsystem.
*/
#ifndef PMIX_BFROP_H_
#define PMIX_BFROP_H_
#include "src/include/pmix_config.h"
#include "pmix_common.h"
#include "src/include/pmix_types.h"
#include "src/mca/mca.h"
#include "bfrops_types.h"
BEGIN_C_DECLS
/* The overall objective of this framework is to provide seamless
* cross-version support for communications by allowing a process
* to communicate with a peer:
*
* (a) using a different version of the buffer operations. We are
* allowing changes in the structure compositions and/or data
* type definitions between versions. This specifically affects
* our ability to pack/unpack across versions.
*
* (b) using a different buffer type (described vs non-described).
* This resolves conflicts when one side was compiled with a
* debug option, while the other side has been "optimized".
*
* This is a mult-select framework - i.e., multiple components
* are selected and "active" at the same time. The intent is
* to have one component for each data type variation, with the
* expectation that the community will do its best not to revise
* existing data type definitions. Thus, new variations should be
* rare, and only a few components will exist.
*
* The framework itself reflects the fact that any given peer
* will utilize only one variation of the data type definitions.
* Thus, once a peer is identified, it will pass its version string
* to this framework's "assign_module" function, which will then
* pass it to each component until one returns a module capable of
* processing the given version. This module is then "attached" to
* the pmix_peer_t object so it can be used for all subsequent
* communication to/from that peer.
*
* Buffer type is included in the buffer metadata. Unfortunately,
* the metadata is not communicated at each exchange. Thus, the
* peers will indicate during the connection handshake the type
* of buffer they will use for all subsequent communications. The
* peer must then utilize that same buffer type for all messages
* sent to that remote proc, so we provide new macros for creating
* and constructing buffers that ensures the correct buffer type
* is marked.
*
* Accordingly, there are two levels of APIs defined for this
* framework:
*
* (a) component level - these allow for init/finalize of the
* component, and assignment of a module to a given peer
* based on the version that peer is using
*
* (b) module level - implement pack/unpack/copy/recv/etc. of
* the various datatypes. Note that the module only needs
* to provide those functions that differ from the base
* functions - they don't need to duplicate all that code!
*/
/* The following functions are exposed to the user - they
* therefore are implemented in the bfrops/base functions
* as wrappers to the real functions.
*
* NOTE: THESE FUNCTIONS ARE NOT TO BE USED INTERNALLY -
* USE THE MACROS INSTEAD
*/
bool pmix_value_cmp(pmix_value_t *p, pmix_value_t *p1);
/**** MODULE INTERFACE DEFINITION ****/
/* initialize the module - the module is expected
* to register its datatype functions at this time */
typedef pmix_status_t (*pmix_bfrop_init_fn_t)(void);
/* finalize the module */
typedef void (*pmix_bfrop_finalize_fn_t)(void);
/**
* Pack one or more values into a buffer.
*
* The pack function packs one or more values of a specified type into
* the specified buffer. The buffer must have already been
* initialized via an PMIX_NEW or PMIX_CONSTRUCT call - otherwise, the
* pack_value function will return an error. Providing an unsupported
* type flag will likewise be reported as an error.
*
* Note that any data to be packed that is not hard type cast (i.e.,
* not type cast to a specific size) may lose precision when unpacked
* by a non-homogeneous recipient. The BFROP will do its best to deal
* with heterogeneity issues between the packer and unpacker in such
* cases. Sending a number larger than can be handled by the recipient
* will return an error code (generated by the BFROP upon unpacking) -
* the BFROP cannot detect such errors during packing.
*
* @param *buffer A pointer to the buffer into which the value is to
* be packed.
*
* @param *src A void* pointer to the data that is to be packed. This
* is interpreted as a pointer to an array of that data type containing
* length num_values. Note that strings are of data type char*, and so
* they are to be passed as (char **) - i.e., the caller must
* pass the address of the pointer to the string as the void*. This
* allows the BFROP to use a single interface function, but still allow
* the caller to pass multiple strings in a single call.
*
* @param num_values An int32_t indicating the number of values that are
* to be packed, beginning at the location pointed to by src. A string
* value is counted as a single value regardless of length. The values
* must be contiguous in memory. Arrays of pointers (e.g., string
* arrays) should be contiguous, although (obviously) the data pointed
* to need not be contiguous across array entries.
*
* @param type The type of the data to be packed - must be one of the
* PMIX defined data types.
*
* @retval PMIX_SUCCESS The data was packed as requested.
*
* @retval PMIX_ERROR(s) An appropriate PMIX error code indicating the
* problem encountered. This error code should be handled
* appropriately.
*
* @code
* pmix_buffer_t *buffer;
* int32_t src;
*
* status_code = pmix_bfrop.pack(buffer, &src, 1, PMIX_INT32);
* @endcode
*/
typedef pmix_status_t (*pmix_bfrop_pack_fn_t)(pmix_buffer_t *buffer, const void *src,
int32_t num_values, pmix_data_type_t type);
/**
* Unpack values from a buffer.
*
* The unpack function unpacks the next value (or values) of a
* specified type from the specified buffer.
*
* The buffer must have already been initialized via an PMIX_NEW or
* PMIX_CONSTRUCT call (and assumedly filled with some data) -
* otherwise, the unpack_value function will return an
* error. Providing an unsupported type flag will likewise be reported
* as an error, as will specifying a data type that DOES NOT match the
* type of the next item in the buffer. An attempt to read beyond the
* end of the stored data held in the buffer will also return an
* error.
*
* NOTE: it is possible for the buffer to be corrupted and that
* the BFROP will *think* there is a proper variable type at the
* beginning of an unpack region - but that the value is bogus (e.g., just
* a byte field in a string array that so happens to have a value that
* matches the specified data type flag). Therefore, the data type error check
* is NOT completely safe. This is true for ALL unpack functions.
*
* Warning: The caller is responsible for providing adequate memory
* storage for the requested data. As noted below, the user
* must provide a parameter indicating the maximum number of values that
* can be unpacked into the allocated memory. If more values exist in the
* buffer than can fit into the memory storage, then the bfrop will unpack
* what it can fit into that location and return an error code indicating
* that the buffer was only partially unpacked.
*
* Note that any data that was not hard type cast (i.e., not type cast
* to a specific size) when packed may lose precision when unpacked by
* a non-homogeneous recipient. The BFROP will do its best to deal with
* heterogeneity issues between the packer and unpacker in such
* cases. Sending a number larger than can be handled by the recipient
* will return an error code generated by the BFROP upon unpacking - the
* BFROP cannot detect such errors during packing.
*
* @param *buffer A pointer to the buffer from which the value will be
* extracted.
*
* @param *dest A void* pointer to the memory location into which the
* data is to be stored. Note that these values will be stored
* contiguously in memory. For strings, this pointer must be to (char
* **) to provide a means of supporting multiple string
* operations. The BFROP unpack function will allocate memory for each
* string in the array - the caller must only provide adequate memory
* for the array of pointers.
*
* @param type The type of the data to be unpacked - must be one of
* the BFROP defined data types.
*
* @retval *max_num_values The number of values actually unpacked. In
* most cases, this should match the maximum number provided in the
* parameters - but in no case will it exceed the value of this
* parameter. Note that if you unpack fewer values than are actually
* available, the buffer will be in an unpackable state - the bfrop will
* return an error code to warn of this condition.
*
* @note The unpack function will return the actual number of values
* unpacked in this location.
*
* @retval PMIX_SUCCESS The next item in the buffer was successfully
* unpacked.
*
* @retval PMIX_ERROR(s) The unpack function returns an error code
* under one of several conditions: (a) the number of values in the
* item exceeds the max num provided by the caller; (b) the type of
* the next item in the buffer does not match the type specified by
* the caller; or (c) the unpack failed due to either an error in the
* buffer or an attempt to read past the end of the buffer.
*
* @code
* pmix_buffer_t *buffer;
* int32_t dest;
* char **string_array;
* int32_t num_values;
*
* num_values = 1;
* status_code = pmix_bfrop.unpack(buffer, (void*)&dest, &num_values, PMIX_INT32);
*
* num_values = 5;
* string_array = malloc(num_values*sizeof(char *));
* status_code = pmix_bfrop.unpack(buffer, (void*)(string_array), &num_values, PMIX_STRING);
*
* @endcode
*/
typedef pmix_status_t (*pmix_bfrop_unpack_fn_t)(pmix_buffer_t *buffer, void *dest,
int32_t *max_num_values, pmix_data_type_t type);
/**
* Copy a payload from one buffer to another
* This function will append a copy of the payload in one buffer into
* another buffer. If the destination buffer is NOT empty, then the
* type of the two buffers MUST match or else an
* error will be returned. If the destination buffer IS empty, then
* its type will be set to that of the source buffer.
* NOTE: This is NOT a destructive procedure - the
* source buffer's payload will remain intact, as will any pre-existing
* payload in the destination's buffer.
*/
typedef pmix_status_t (*pmix_bfrop_copy_payload_fn_t)(pmix_buffer_t *dest, pmix_buffer_t *src);
/**
* Copy a data value from one location to another.
*
* Since registered data types can be complex structures, the system
* needs some way to know how to copy the data from one location to
* another (e.g., for storage in the registry). This function, which
* can call other copy functions to build up complex data types, defines
* the method for making a copy of the specified data type.
*
* @param **dest The address of a pointer into which the
* address of the resulting data is to be stored.
*
* @param *src A pointer to the memory location from which the
* data is to be copied.
*
* @param type The type of the data to be copied - must be one of
* the BFROP defined data types.
*
* @retval PMIX_SUCCESS The value was successfully copied.
*
* @retval PMIX_ERROR(s) An appropriate error code.
*
*/
typedef pmix_status_t (*pmix_bfrop_copy_fn_t)(void **dest, void *src, pmix_data_type_t type);
/**
* Print a data value.
*
* Since registered data types can be complex structures, the system
* needs some way to know how to print them (i.e., convert them to a string
* representation). Provided for debug purposes.
*
* @retval PMIX_SUCCESS The value was successfully printed.
*
* @retval PMIX_ERROR(s) An appropriate error code.
*/
typedef pmix_status_t (*pmix_bfrop_print_fn_t)(char **output, char *prefix, void *src,
pmix_data_type_t type);
/**
* Transfer a value from one pmix_value_t to another. Ordinarily,
* this would be executed as a base function. However, it is
* possible that future versions may add new data types, and
* thus the xfer function may differ
*
* @retval PMIX_SUCCESS The value was successfully transferred
*
* @retval PMIX_ERROR(s) An appropriate error code
*/
typedef pmix_status_t (*pmix_bfrop_value_xfer_fn_t)(pmix_value_t *dest, const pmix_value_t *src);
/**
* Load data into a pmix_value_t object. Again, this is provided
* as a component function to support different data types
*/
typedef void (*pmix_bfrop_value_load_fn_t)(pmix_value_t *v, const void *data,
pmix_data_type_t type);
/**
* Unload data from a pmix_value_t object
*
* @retval PMIX_SUCCESS The value was successfully unloaded
*
* @retval PMIX_ERROR(s) An appropriate error code
*/
typedef pmix_status_t (*pmix_bfrop_value_unload_fn_t)(pmix_value_t *kv, void **data, size_t *sz);
/**
* Compare two pmix_value_t structs
*/
typedef pmix_value_cmp_t (*pmix_bfrop_value_cmp_fn_t)(pmix_value_t *p1, pmix_value_t *p2);
/* return the string name of a provided data type */
typedef const char *(*pmix_bfrop_data_type_string_fn_t)(pmix_data_type_t type);
/**
* Base structure for a BFROP module
*/
typedef struct {
char *version;
pmix_bfrop_init_fn_t init;
pmix_bfrop_finalize_fn_t finalize;
pmix_bfrop_pack_fn_t pack;
pmix_bfrop_unpack_fn_t unpack;
pmix_bfrop_copy_fn_t copy;
pmix_bfrop_print_fn_t print;
pmix_bfrop_copy_payload_fn_t copy_payload;
pmix_bfrop_value_xfer_fn_t value_xfer;
pmix_bfrop_value_load_fn_t value_load;
pmix_bfrop_value_unload_fn_t value_unload;
pmix_bfrop_value_cmp_fn_t value_cmp;
pmix_bfrop_data_type_string_fn_t data_type_string;
} pmix_bfrops_module_t;
/* get a list of available versions - caller must free results
* when done */
PMIX_EXPORT char *pmix_bfrops_base_get_available_modules(void);
/* Select a bfrops module for a given version */
PMIX_EXPORT pmix_bfrops_module_t *pmix_bfrops_base_assign_module(const char *version);
/* provide a backdoor to access the framework debug output */
PMIX_EXPORT extern int pmix_bfrops_base_output;
/* MACROS FOR EXECUTING BFROPS FUNCTIONS */
#define PMIX_BFROPS_ASSIGN_TYPE(p, b) (b)->type = (p)->nptr->compat.type
#define PMIX_BFROPS_PACK(r, p, b, s, n, t) \
do { \
pmix_output_verbose(2, pmix_bfrops_base_output, "[%s:%d] PACK version %s type %s", \
__FILE__, __LINE__, (p)->nptr->compat.bfrops->version, \
PMIx_Data_type_string(t)); \
if (PMIX_BFROP_BUFFER_UNDEF == (b)->type) { \
(b)->type = (p)->nptr->compat.type; \
(r) = (p)->nptr->compat.bfrops->pack(b, s, n, t); \
} else if ((b)->type == (p)->nptr->compat.type) { \
(r) = (p)->nptr->compat.bfrops->pack(b, s, n, t); \
} else { \
(r) = PMIX_ERR_PACK_MISMATCH; \
} \
} while (0)
#define PMIX_BFROPS_UNPACK(r, p, b, d, m, t) \
do { \
pmix_output_verbose(2, pmix_bfrops_base_output, "[%s:%d] UNPACK version %s type %s", \
__FILE__, __LINE__, (p)->nptr->compat.bfrops->version, \
PMIx_Data_type_string(t)); \
if ((b)->type == (p)->nptr->compat.type) { \
(r) = (p)->nptr->compat.bfrops->unpack(b, d, m, t); \
} else { \
(r) = PMIX_ERR_UNPACK_FAILURE; \
} \
} while (0)
#define PMIX_BFROPS_COPY(r, p, d, s, t) (r) = (p)->nptr->compat.bfrops->copy(d, s, t)
#define PMIX_BFROPS_PRINT(r, p, o, pr, s, t) (r) = (p)->nptr->compat.bfrops->print(o, pr, s, t)
#define PMIX_BFROPS_COPY_PAYLOAD(r, p, d, s) \
do { \
if (PMIX_BFROP_BUFFER_UNDEF == (d)->type) { \
(d)->type = (p)->nptr->compat.type; \
(r) = (p)->nptr->compat.bfrops->copy_payload(d, s); \
} else if ((d)->type == (p)->nptr->compat.type) { \
(r) = (p)->nptr->compat.bfrops->copy_payload(d, s); \
} else { \
(r) = PMIX_ERR_PACK_MISMATCH; \
} \
} while (0)
#define PMIX_BFROPS_VALUE_XFER(r, p, d, s) (r) = (p)->nptr->compat.bfrops->value_xfer(d, s)
#define PMIX_BFROPS_VALUE_LOAD(p, v, d, t) (p)->nptr->compat.bfrops->value_load(v, d, t)
#define PMIX_BFROPS_VALUE_UNLOAD(r, p, k, d, s) \
(r) = (p)->nptr->compat.bfrops->value_unload(k, , d, s)
#define PMIX_BFROPS_VALUE_CMP(r, p, q, s) (r) = (p)->nptr->compat.bfrops->value_cmp(q, s)
#define PMIX_BFROPS_REGISTER(r, p, n, t, pk, u, c, pr) \
(r) = (p)->nptr->compat.bfrops->register_type(n, t, pk, u, c, pr)
#define PMIX_BFROPS_PRINT_TYPE(c, p, t) (c) = (p)->nptr->compat.bfrops->data_type_string(t)
/**** COMPONENT STRUCTURE DEFINITION ****/
/* define a component-level API for getting a module */
typedef pmix_bfrops_module_t *(*pmix_bfrop_base_component_assign_module_fn_t)(void);
/*
* the standard component data structure
*/
struct pmix_bfrops_base_component_t {
pmix_mca_base_component_t base;
int priority;
pmix_pointer_array_t types;
pmix_bfrop_base_component_assign_module_fn_t assign_module;
};
typedef struct pmix_bfrops_base_component_t pmix_bfrops_base_component_t;
/*
* Macro for use in components that are of type bfrops
*/
#define PMIX_BFROPS_BASE_VERSION_1_0_0 PMIX_MCA_BASE_VERSION_1_0_0("bfrops", 1, 0, 0)
END_C_DECLS
#endif /* PMIX_BFROP_H */

View File

@@ -0,0 +1,191 @@
/* -*- C -*-
*
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2006 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2007-2011 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2012-2013 Los Alamos National Security, Inc. All rights reserved.
* Copyright (c) 2014-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2021-2022 Nanook Consulting. All rights reserved.
* Copyright (c) 2023 Triad National Security, LLC. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
/**
* @file
*
* Buffer management types.
*/
#ifndef PMIX_MCA_BFROP_TYPES_H_
#define PMIX_MCA_BFROP_TYPES_H_
#include "src/include/pmix_config.h"
#include "pmix_common.h"
#include "src/class/pmix_list.h"
#include "src/class/pmix_object.h"
#include "src/class/pmix_pointer_array.h"
BEGIN_C_DECLS
/* set the bfrops module */
#define PMIX_BFROPS_SET_MODULE(r, mp, p, v) \
do { \
(mp)->nptr->compat.bfrops = pmix_bfrops_base_assign_module((v)); \
if (NULL == (mp)->nptr->compat.bfrops) { \
(r) = PMIX_ERR_INIT; \
} else { \
(p)->nptr->compat.bfrops = (mp)->nptr->compat.bfrops; \
(mp)->protocol = PMIX_PROTOCOL_V2; \
(r) = PMIX_SUCCESS; \
} \
} while (0)
/**
* buffer type
*/
typedef uint8_t pmix_bfrop_buffer_type_t;
#define PMIX_BFROP_BUFFER_UNDEF 0x00
#define PMIX_BFROP_BUFFER_NON_DESC 0x01
#define PMIX_BFROP_BUFFER_FULLY_DESC 0x02
#define PMIX_BFROP_BUFFER_TYPE_HTON(h)
#define PMIX_BFROP_BUFFER_TYPE_NTOH(h)
/* internally used object for transferring data
* to/from the server and for storing in the
* hash tables */
typedef struct {
pmix_list_item_t super;
char *key;
pmix_value_t *value;
} pmix_kval_t;
PMIX_EXPORT PMIX_CLASS_DECLARATION(pmix_kval_t);
static inline pmix_kval_t *
pmix_bfrop_tma_kval_new(
const char *key,
pmix_tma_t *tma
) {
pmix_kval_t *k = PMIX_NEW(pmix_kval_t, tma);
if (PMIX_LIKELY(NULL != k)) {
k->key = pmix_tma_strdup(tma, key);
k->value = (pmix_value_t *)pmix_tma_malloc(tma, sizeof(pmix_value_t));
if (PMIX_UNLIKELY(NULL == k->value)) {
PMIX_RELEASE(k);
k = NULL;
}
}
return k;
}
/* helpful macro extension of the usual PMIX_NEW */
#define PMIX_KVAL_NEW(k, s) \
do { \
(k) = pmix_bfrop_tma_kval_new((s), NULL); \
} while (0)
/**
* Structure for holding a buffer */
typedef struct {
/** First member must be the object's parent */
pmix_object_t parent;
/** type of buffer */
pmix_bfrop_buffer_type_t type;
/** Start of my memory */
char *base_ptr;
/** Where the next data will be packed to (within the allocated
memory starting at base_ptr) */
char *pack_ptr;
/** Where the next data will be unpacked from (within the
allocated memory starting as base_ptr) */
char *unpack_ptr;
/** Number of bytes allocated (starting at base_ptr) */
size_t bytes_allocated;
/** Number of bytes used by the buffer (i.e., amount of data --
including overhead -- packed in the buffer) */
size_t bytes_used;
} pmix_buffer_t;
PMIX_EXPORT PMIX_CLASS_DECLARATION(pmix_buffer_t);
/* Convenience macro for loading a data blob into a pmix_buffer_t
*
* p - the pmix_peer_t of the process that provided the blob. This
* is needed so we can set the buffer type for later unpacking
*
* b - pointer to pmix_buffer_t
*
* d - pointer to the data blob
*
* s - number of bytes in the blob
*
* NOTE: the macro does NOT copy the data, but simply assigns
* its address to the buffer. Accordingly, the macro will
* set the provided data blob pointer to NULL and the size
* to zero.
*/
#define PMIX_LOAD_BUFFER(p, b, d, s) \
do { \
(b)->type = (p)->nptr->compat.type; \
(b)->base_ptr = (char *) (d); \
(b)->bytes_used = (s); \
(b)->bytes_allocated = (s); \
(b)->pack_ptr = ((char *) (b)->base_ptr) + (s); \
(b)->unpack_ptr = (b)->base_ptr; \
(d) = NULL; \
(s) = 0; \
} while (0)
#define PMIX_LOAD_BUFFER_NON_DESTRUCT(p, b, d, s) \
do { \
(b)->type = (p)->nptr->compat.type; \
(b)->base_ptr = (char *) (d); \
(b)->bytes_used = (s); \
(b)->bytes_allocated = (s); \
(b)->pack_ptr = ((char *) (b)->base_ptr) + (s); \
(b)->unpack_ptr = (b)->base_ptr; \
} while (0)
/* Convenience macro for extracting a pmix_buffer_t's payload
* as a data blob
*
* b - pointer to the pmix_buffer_t
*
* d - char* pointer to the data blob
*
* s - number of bytes in the blob
*
* NOTE: the macro does NOT copy the data, but simply assigns
* the address of the buffer's payload to the provided pointer.
* Accordingly, the macro will set all pmix_buffer_t internal
* tracking pointers to NULL and all counters to zero */
#define PMIX_UNLOAD_BUFFER(b, d, s) \
do { \
(d) = (char *) (b)->unpack_ptr; \
(s) = (b)->bytes_used; \
(b)->base_ptr = NULL; \
(b)->bytes_used = 0; \
(b)->bytes_allocated = 0; \
(b)->pack_ptr = NULL; \
(b)->unpack_ptr = NULL; \
} while (0)
/* Convenience macro to check for empty buffer without
* exposing the internals */
#define PMIX_BUFFER_IS_EMPTY(b) (0 == (b)->bytes_used || (b)->pack_ptr == (b)->unpack_ptr)
END_C_DECLS
#endif /* PMIX_BFROP_TYPES_H */

View File

@@ -0,0 +1,137 @@
/* -*- C -*-
*
* Copyright (c) 2004-2007 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2006 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2012 Los Alamos National Security, Inc. All rights reserved.
* Copyright (c) 2014-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2015-2020 Research Organization for Information Science
* and Technology (RIST). All rights reserved.
* Copyright (c) 2018 IBM Corporation. All rights reserved.
* Copyright (c) 2019 Mellanox Technologies, Inc.
* All rights reserved.
* Copyright (c) 2021 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*
*/
#ifndef PMIX_GDS_BASE_H_
#define PMIX_GDS_BASE_H_
#include "src/include/pmix_config.h"
#ifdef HAVE_SYS_TIME_H
# include <sys/time.h> /* for struct timeval */
#endif
#ifdef HAVE_STRING_H
# include <string.h>
#endif
#include "src/class/pmix_list.h"
#include "src/mca/base/pmix_mca_base_framework.h"
#include "src/mca/mca.h"
#include "src/mca/gds/gds.h"
BEGIN_C_DECLS
/*
* MCA Framework
*/
PMIX_EXPORT extern pmix_mca_base_framework_t pmix_gds_base_framework;
/**
* GDS select function
*
* Cycle across available components and construct the list
* of active modules
*/
PMIX_EXPORT pmix_status_t pmix_gds_base_select(pmix_info_t info[], size_t ninfo);
/**
* Track an active component / module
*/
struct pmix_gds_base_active_module_t {
pmix_list_item_t super;
int pri;
pmix_gds_base_module_t *module;
pmix_gds_base_component_t *component;
};
typedef struct pmix_gds_base_active_module_t pmix_gds_base_active_module_t;
PMIX_CLASS_DECLARATION(pmix_gds_base_active_module_t);
/* framework globals */
struct pmix_gds_globals_t {
pmix_list_t actives;
bool initialized;
bool selected;
char *all_mods;
};
typedef enum {
PMIX_MODEX_KEY_INVALID = -1,
PMIX_MODEX_KEY_NATIVE_FMT,
PMIX_MODEX_KEY_KEYMAP_FMT,
PMIX_MODEX_KEY_MAX
} pmix_gds_modex_key_fmt_t;
/* define a modex blob info */
typedef uint8_t pmix_gds_modex_blob_info_t;
#define PMIX_GDS_COLLECT_BIT 0x0001
#define PMIX_GDS_KEYMAP_BIT 0x0002
#define PMIX_GDS_KEYMAP_IS_SET(byte) (PMIX_GDS_KEYMAP_BIT & (byte))
#define PMIX_GDS_COLLECT_IS_SET(byte) (PMIX_GDS_COLLECT_BIT & (byte))
typedef struct pmix_gds_globals_t pmix_gds_globals_t;
typedef void *pmix_gds_base_ctx_t;
typedef pmix_status_t (*pmix_gds_base_store_modex_cb_fn_t)(pmix_gds_base_ctx_t ctx,
pmix_proc_t *proc,
pmix_gds_modex_key_fmt_t key_fmt,
char **kmap, pmix_buffer_t *pbkt);
PMIX_EXPORT extern pmix_gds_globals_t pmix_gds_globals;
/* get a list of available support - caller must free results
* when done. The list is returned as a comma-delimited string
* of available components in priority order */
PMIX_EXPORT char *pmix_gds_base_get_available_modules(void);
/* Select a gds module based on the provided directives */
PMIX_EXPORT pmix_gds_base_module_t *pmix_gds_base_assign_module(pmix_info_t *info, size_t ninfo);
/**
* Add any envars to a peer's environment that the module needs
* to communicate. The API stub will rotate across all active modules, giving
* each a chance to contribute
*
* @return PMIX_SUCCESS on success.
*/
PMIX_EXPORT pmix_status_t pmix_gds_base_setup_fork(const pmix_proc_t *proc, char ***env);
PMIX_EXPORT pmix_status_t pmix_gds_base_store_modex(struct pmix_namespace_t *nspace,
pmix_buffer_t *buff, pmix_gds_base_ctx_t ctx,
pmix_gds_base_store_modex_cb_fn_t cb_fn,
void *cbdata);
PMIX_EXPORT
pmix_status_t pmix_gds_base_modex_pack_kval(pmix_gds_modex_key_fmt_t key_fmt, pmix_buffer_t *buf,
char ***kmap, pmix_kval_t *kv);
PMIX_EXPORT
pmix_status_t pmix_gds_base_modex_unpack_kval(pmix_gds_modex_key_fmt_t key_fmt, pmix_buffer_t *buf,
char **kmap, pmix_kval_t *kv);
END_C_DECLS
#endif

View File

@@ -0,0 +1,491 @@
/* -*- Mode: C; c-basic-offset:4 ; indent-tabs-mode:nil -*- */
/*
* Copyright (c) 2016-2020 Mellanox Technologies, Inc.
* All rights reserved.
* Copyright (c) 2016-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2018 IBM Corporation. All rights reserved.
* Copyright (c) 2021-2024 Nanook Consulting All rights reserved.
* Copyright (c) 2022 Triad National Security, LLC. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
#ifndef PMIX_GDS_H
#define PMIX_GDS_H
#include "src/include/pmix_config.h"
#include "pmix_common.h"
#include "src/mca/base/pmix_mca_base_framework.h"
#include "src/mca/base/pmix_mca_base_var.h"
#include "src/mca/bfrops/bfrops_types.h"
#include "src/mca/mca.h"
/* The client dictates the GDS module that will be used to interact
* with the server - this module is stored in pmix_globals.mypeer->compat.gds
* Because that is a long address to keep typing out, convenience macros
* are provided for when that module is to be used in an operation.
*
* However, an application can open any number of GDS modules for
* purposes other than exchanging info with the server. For example,
* an application may wish to utilize a DHT module for its own
* peer-to-peer data sharing. Thus, the public and private interfaces
* are deliberately designed to be generic. The macros should make
* things easier for the typical internal operations
*
* NOTE: ALTHOUGH SOME GDS COMPONENTS MAY UTILIZE THEIR OWN INTERNAL
* PROGRESS THREADS, THE GDS IS NOT GUARANTEED TO BE THREAD-SAFE.
* GDS FUNCTIONS SHOULD THEREFORE ALWAYS BE CALLED IN A THREAD-SAFE
* CONDITION - E.G., FROM WITHIN AN EVENT
*/
BEGIN_C_DECLS
/* forward declaration */
struct pmix_peer_t;
struct pmix_namespace_t;
/* backdoor to base verbosity */
PMIX_EXPORT extern int pmix_gds_base_output;
/**
* Initialize the module. Returns an error if the module cannot
* run, success if it can.
*/
typedef pmix_status_t (*pmix_gds_base_module_init_fn_t)(pmix_info_t info[], size_t ninfo);
/**
* Finalize the module. Tear down any allocated storage, disconnect
* from any system support.
*/
typedef void (*pmix_gds_base_module_fini_fn_t)(void);
/**
* Assign a module per the requested directives. Modules should
* review the provided directives to determine if they can support
* the request. Modules are "scanned" in component priority order
* and given an opportunity to respond. If a module offers itself,
* it will provide a priority (which can be based on the directives
* and therefore different from the component priority). The highest
* returned priority received from a responder will be selected
* and a pointer to its module returned */
typedef pmix_status_t (*pmix_gds_base_assign_module_fn_t)(pmix_info_t *info, size_t ninfo,
int *priority);
#define PMIX_GDS_CHECK_COMPONENT(p, s) (0 == strcmp((p)->nptr->compat.gds->name, (s)))
#define PMIX_GDS_CHECK_PEER_COMPONENT(p1, p2) \
(0 == strcmp((p1)->nptr->compat.gds->name, (p2)->nptr->compat.gds->name))
/* SERVER FN: assemble the keys buffer for server answer */
typedef pmix_status_t (*pmix_gds_base_module_assemb_kvs_req_fn_t)(const pmix_proc_t *proc,
pmix_list_t *kvs,
pmix_buffer_t *buf, void *cbdata);
/* define a macro for server keys answer based on peer */
#define PMIX_GDS_ASSEMB_KVS_REQ(s, p, r, k, b, c) \
do { \
pmix_gds_base_module_t *_g = (p)->nptr->compat.gds; \
(s) = PMIX_SUCCESS; \
if (NULL == _g->assemb_kvs_req) { \
if (0 == strcmp(_g->name, "hash")) { \
(s) = PMIX_ERR_NOT_SUPPORTED; \
} else { \
_g = pmix_globals.mypeer->nptr->compat.gds; \
} \
} \
if (NULL != _g->assemb_kvs_req) { \
pmix_output_verbose(1, pmix_gds_base_output, \
"[%s:%d] GDS ASSEMBLE REQ WITH %s", \
__FILE__, __LINE__, _g->name); \
(s) = _g->assemb_kvs_req(r, k, b, (void *) c); \
} \
} while (0)
/* CLIENT FN: unpack buffer and key processing */
typedef pmix_status_t (*pmix_gds_base_module_accept_kvs_resp_fn_t)(pmix_buffer_t *buf);
/* define a macro for client key processing from a server response based on peer */
#define PMIX_GDS_ACCEPT_KVS_RESP(s, p, b) \
do { \
pmix_gds_base_module_t *_g = (p)->nptr->compat.gds; \
(s) = PMIX_SUCCESS; \
if (NULL == _g->accept_kvs_resp) { \
if (0 == strcmp(_g->name, "hash")) { \
(s) = PMIX_ERR_NOT_SUPPORTED; \
} else { \
_g = pmix_globals.mypeer->nptr->compat.gds; \
} \
} \
if (NULL != _g->accept_kvs_resp) { \
pmix_output_verbose(1, pmix_gds_base_output, \
"[%s:%d] GDS ACCEPT RESP WITH %s", \
__FILE__, __LINE__, _g->name); \
(s) = _g->accept_kvs_resp(b); \
} \
} while (0)
/* SERVER FN: cache job-level info in the server's GDS until client
* procs connect and we discover which GDS module to use for them.
* Note that this is essentially the same function as store_job_info,
* only we don't have packed data on the server side, and don't want
* to incur the overhead of packing it just to unpack it in the function.
*/
typedef pmix_status_t (*pmix_gds_base_module_cache_job_info_fn_t)(struct pmix_namespace_t *ns,
pmix_info_t info[], size_t ninfo);
/* define a convenience macro for caching job info */
#define PMIX_GDS_CACHE_JOB_INFO(s, p, n, i, ni) \
do { \
pmix_gds_base_module_t *_g = (p)->nptr->compat.gds; \
pmix_output_verbose(1, pmix_gds_base_output, "[%s:%d] GDS CACHE JOB INFO WITH %s", \
__FILE__, __LINE__, _g->name); \
(s) = _g->cache_job_info((struct pmix_namespace_t *) (n), (i), (ni)); \
} while (0)
/* register job-level info - this is provided as a special function
* to allow for optimization. Called solely by the server. We cannot
* prepare the job-level info provided at PMIx_Register_nspace, because
* we don't know the GDS component to use for that application until
* a local client contacts us. Thus, the module is required to process
* the job-level info cached in the pmix_namespace_t for this job and
* do whatever is necessary to support the client, packing any required
* return message into the provided buffer.
*
* This function will be called once for each local client of
* a given nspace. PMIx assumes that all peers of a given nspace
* will use the same GDS module. Thus, the module is free to perform
* any relevant optimizations (e.g., packing the data only once and
* then releasing the cached buffer once all local clients have
* been serviced, or storing it once in shared memory and simply
* returning the shared memory rendezvous information for subsequent
* calls).
*
* Info provided in the reply buffer will be given to the "store_job_info"
* API of the GDS module on the client. Since this should match the
* module used by the server, each module has full knowledge and control
* over what is in the reply buffer.
*
* The pmix_peer_t of the requesting client is provided here so that
* the module can access the job-level info cached on the corresponding
* pmix_namespace_t pointed to by the pmix_peer_t
*/
typedef pmix_status_t (*pmix_gds_base_module_register_job_info_fn_t)(struct pmix_peer_t *pr,
pmix_buffer_t *reply);
/* define a convenience macro for registering job info for
* a given peer */
#define PMIX_GDS_REGISTER_JOB_INFO(s, p, b) \
do { \
pmix_gds_base_module_t *_g = (p)->nptr->compat.gds; \
pmix_output_verbose(1, pmix_gds_base_output, "[%s:%d] GDS REG JOB INFO WITH %s", __FILE__, \
__LINE__, _g->name); \
(s) = _g->register_job_info((struct pmix_peer_t *) (p), b); \
} while (0)
/* update job-level info - this is provided as a special function
* to allow for optimization. Called solely by the client. The buffer
* provided to this API is the same one given to the server by the
* corresponding "register_job_info" function
*/
typedef pmix_status_t (*pmix_gds_base_module_store_job_info_fn_t)(const char *nspace,
pmix_buffer_t *buf);
/* define a convenience macro for storing job info based on peer */
#define PMIX_GDS_STORE_JOB_INFO(s, p, n, b) \
do { \
pmix_gds_base_module_t *_g = (p)->nptr->compat.gds; \
pmix_output_verbose(1, pmix_gds_base_output, "[%s:%d] GDS STORE JOB INFO WITH %s", \
__FILE__, __LINE__, _g->name); \
(s) = _g->store_job_info(n, b); \
} while (0)
/**
* store key/value pair - these will either be values committed by the peer
* and transmitted to the server, or values stored locally by the peer.
* The format of the data depends on the GDS module. Note that data stored
* with PMIX_INTERNAL scope should be stored solely within the process and
* is never shared.
*
* @param peer pointer to pmix_peer_t object of the peer that
* provided the data
*
* @param proc the proc that the data describes
*
* @param scope scope of the data
*
* @param kv key/value pair.
*
* @return PMIX_SUCCESS on success.
*/
typedef pmix_status_t (*pmix_gds_base_module_store_fn_t)(const pmix_proc_t *proc,
pmix_scope_t scope, pmix_kval_t *kv);
/* define a convenience macro for storing key-val pairs based on peer */
#define PMIX_GDS_STORE_KV(s, p, pc, sc, k) \
do { \
pmix_gds_base_module_t *_g = (p)->nptr->compat.gds; \
(s) = PMIX_SUCCESS; \
if (NULL == _g->store) { \
if (0 == strcmp(_g->name, "hash")) { \
(s) = PMIX_ERR_NOT_SUPPORTED; \
} else { \
_g = pmix_globals.mypeer->nptr->compat.gds; \
} \
} \
if (NULL != _g->store) { \
pmix_output_verbose(1, pmix_gds_base_output, \
"[%s:%d] GDS STORE KV WITH %s", \
__FILE__, __LINE__, _g->name); \
(s) = _g->store(pc, sc, k); \
} \
} while (0)
/**
* unpack and store a data "blob" from a peer so that the individual
* elements can later be retrieved. This is an optimization path to
* avoid repeatedly storing pmix_kval_t's for multiple local procs
* from the same nspace.
*
* ranks - a list of pmix_rank_info_t for the local ranks from this
* nspace - this is to be used to filter the cbs list
*
* cbdata - pointer to modex callback data
*
* bo - pointer to the byte object containing the data
*
*/
typedef pmix_status_t (*pmix_gds_base_module_store_modex_fn_t)(struct pmix_namespace_t *ns,
pmix_buffer_t *buff, void *cbdata);
/**
* define a convenience macro for storing modex byte objects
*
* r - return status code
*
* n - pointer to the pmix_namespace_t this blob is to be stored for
*
* b - pointer to pmix_buffer_t containing the data
*
* t - pointer to the modex server tracker
*/
#define PMIX_GDS_STORE_MODEX(r, n, b, t) \
do { \
pmix_gds_base_module_t *_g = pmix_globals.mypeer->nptr->compat.gds; \
pmix_output_verbose(1, pmix_gds_base_output, \
"[%s:%d] GDS STORE MODEX WITH %s", __FILE__, \
__LINE__, _g->name); \
(r) = _g->store_modex((struct pmix_namespace_t *)n, b, t); \
} while (0)
typedef pmix_status_t (*pmix_gds_base_module_mark_modex_complete_fn_t)(struct pmix_peer_t *peer,
pmix_list_t *nslist,
pmix_buffer_t *buff);
#define PMIX_GDS_MARK_MODEX_COMPLETE(r, p, l, b) \
do { \
pmix_gds_base_module_t *_g = pmix_globals.mypeer->nptr->compat.gds; \
pmix_output_verbose(1, pmix_gds_base_output, \
"[%s:%d] GDS MARK MODEX COMPLETE WITH %s", \
__FILE__, __LINE__, _g->name); \
(r) = _g->mark_modex_complete(p, l, b); \
} while (0)
typedef pmix_status_t (*pmix_gds_base_module_recv_modex_complete_fn_t)(pmix_buffer_t *buff);
#define PMIX_GDS_RECV_MODEX_COMPLETE(r, p, b) \
do { \
pmix_gds_base_module_t *_g = pmix_globals.mypeer->nptr->compat.gds; \
pmix_output_verbose(1, pmix_gds_base_output, \
"[%s:%d] GDS RECV MODEX COMPLETE WITH %s", \
__FILE__, __LINE__, _g->name); \
(r) = _g->recv_modex_complete(b); \
} while (0)
/**
* fetch value corresponding to provided key from within the defined
* scope. A NULL key returns all values committed by the given peer
* for that scope.
*
* @param proc namespace and rank whose info is being requested
*
* @param key key.
*
* @param scope scope of the data to be considered
*
* @param copy true if the caller _requires_ a copy of the data. This
* is used when the requestor is off-node. If
* set to false, then the GDS component can provide
* either a copy of the data, or shmem contact info
* to the location of the data
*
* @param info array of pmix_info_t the caller provided as
* qualifiers to guide the request
*
* @param ninfo number of elements in the info array
*
* @param kvs pointer to a list that will be populated with the
* returned pmix_kval_t data
*
* @return PMIX_SUCCESS on success.
*
* Note: all available job-level data for a given nspace can be fetched
* by passing a proc with rank=PMIX_RANK_WILDCARD and a NULL key. Similarly,
* passing a NULL key for a non-wildcard rank will return all data "put"
* by that rank. Scope is ignored for job-level data requests.
*
* When a specific rank if provided with a NULL key, then data for only
* that rank is returned. If the scope is PMIX_LOCAL, then the returned
* data shall include only data that was specifically "put" to local scope,
* plus any data that was put to PMIX_GLOBAL scope. Similarly, a scope of
* PMIX_REMOTE will return data that was "put" to remote scope, plus
* any data that was put to PMIX_GLOBAL scope. A scope of PMIX_GLOBAL
* will return LOCAL, REMOTE, and GLOBAL data.
*
* Data stored with PMIX_INTERNAL scope can be retrieved with that scope.
*/
typedef pmix_status_t (*pmix_gds_base_module_fetch_fn_t)(const pmix_proc_t *proc,
pmix_scope_t scope, bool copy,
const char *key, pmix_info_t info[],
size_t ninfo, pmix_list_t *kvs);
/* define a convenience macro for fetch key-val pairs based on peer,
* passing a pmix_cb_t containing all the required info */
#define PMIX_GDS_FETCH_KV(s, p, c) \
do { \
pmix_gds_base_module_t *_g = (p)->nptr->compat.gds; \
pmix_output_verbose(1, pmix_gds_base_output, "[%s:%d] GDS FETCH KV WITH %s", __FILE__, \
__LINE__, _g->name); \
(s) = _g->fetch((c)->proc, (c)->scope, (c)->copy, (c)->key, (c)->info, (c)->ninfo, \
&(c)->kvs); \
} while (0)
/**
* Add any envars to a peer's environment that the module needs
* to communicate. The API stub will rotate across all active modules, giving
* each a chance to contribute
*
* @return PMIX_SUCCESS on success.
*/
typedef pmix_status_t (*pmix_gds_base_module_setup_fork_fn_t)(const pmix_proc_t *proc, char ***env);
/**
* Define a new nspace in the GDS
*
* @param nspace namespace string
*
* @return PMIX_SUCCESS on success.
*/
typedef pmix_status_t (*pmix_gds_base_module_add_nspace_fn_t)(const char *nspace,
uint32_t nlocalprocs,
pmix_info_t info[], size_t ninfo);
/* define a convenience macro for add_nspace based on peer */
#define PMIX_GDS_ADD_NSPACE(s, n, ls, i, ni) \
do { \
pmix_gds_base_active_module_t *_g; \
pmix_status_t _s = PMIX_SUCCESS; \
(s) = PMIX_SUCCESS; \
pmix_output_verbose(1, pmix_gds_base_output, "[%s:%d] GDS ADD NSPACE %s", __FILE__, \
__LINE__, (n)); \
PMIX_LIST_FOREACH (_g, &pmix_gds_globals.actives, pmix_gds_base_active_module_t) { \
if (NULL != _g->module->add_nspace) { \
_s = _g->module->add_nspace(n, ls, i, ni); \
} \
if (PMIX_SUCCESS != _s) { \
(s) = PMIX_ERROR; \
} \
} \
} while (0)
/**
* Delete nspace and its associated data
*
* @param nspace namespace string
*
* @return PMIX_SUCCESS on success.
*/
typedef pmix_status_t (*pmix_gds_base_module_del_nspace_fn_t)(const char *nspace);
/* define a convenience macro for del_nspace based on peer */
#define PMIX_GDS_DEL_NSPACE(s, n) \
do { \
pmix_gds_base_active_module_t *_g; \
pmix_status_t _s = PMIX_SUCCESS; \
(s) = PMIX_SUCCESS; \
pmix_output_verbose(1, pmix_gds_base_output, "[%s:%d] GDS DEL NSPACE %s", __FILE__, \
__LINE__, (n)); \
PMIX_LIST_FOREACH (_g, &pmix_gds_globals.actives, pmix_gds_base_active_module_t) { \
if (NULL != _g->module->del_nspace) { \
_s = _g->module->del_nspace(n); \
} \
if (PMIX_SUCCESS != _s) { \
(s) = PMIX_ERROR; \
} \
} \
} while (0)
/* define a convenience macro for is_tsafe for fetch operation */
#define PMIX_GDS_FETCH_IS_TSAFE(s, p) \
do { \
pmix_gds_base_module_t *_g = (p)->nptr->compat.gds; \
pmix_output_verbose(1, pmix_gds_base_output, \
"[%s:%d] GDS FETCH IS THREAD SAFE WITH %s", \
__FILE__, __LINE__, _g->name); \
if (true == _g->is_tsafe) { \
(s) = PMIX_SUCCESS; \
} else { \
(s) = PMIX_ERR_NOT_SUPPORTED; \
} \
} while(0)
typedef pmix_status_t (*pmix_gds_base_module_fetch_array_fn_t)(struct pmix_peer_t *pr,
pmix_buffer_t *reply);
/* define a convenience macro for fetching array info for
* a given peer */
#define PMIX_GDS_FETCH_INFO_ARRAYS(s, p, b) \
do { \
pmix_gds_base_module_t *_g = pmix_globals.mypeer->nptr->compat.gds; \
pmix_output_verbose(1, pmix_gds_base_output, \
"[%s:%d] GDS FETCH ARRAYS WITH %s", \
__FILE__, __LINE__, _g->name); \
(s) = _g->fetch_arrays((struct pmix_peer_t*)(p), b); \
} while(0)
/* structure for gds modules */
typedef struct {
const char *name;
const bool is_tsafe;
pmix_gds_base_module_init_fn_t init;
pmix_gds_base_module_fini_fn_t finalize;
pmix_gds_base_assign_module_fn_t assign_module;
pmix_gds_base_module_cache_job_info_fn_t cache_job_info;
pmix_gds_base_module_register_job_info_fn_t register_job_info;
pmix_gds_base_module_store_job_info_fn_t store_job_info;
pmix_gds_base_module_store_fn_t store;
pmix_gds_base_module_store_modex_fn_t store_modex;
pmix_gds_base_module_fetch_fn_t fetch;
pmix_gds_base_module_setup_fork_fn_t setup_fork;
pmix_gds_base_module_add_nspace_fn_t add_nspace;
pmix_gds_base_module_del_nspace_fn_t del_nspace;
pmix_gds_base_module_assemb_kvs_req_fn_t assemb_kvs_req;
pmix_gds_base_module_accept_kvs_resp_fn_t accept_kvs_resp;
pmix_gds_base_module_fetch_array_fn_t fetch_arrays;
pmix_gds_base_module_mark_modex_complete_fn_t mark_modex_complete;
pmix_gds_base_module_recv_modex_complete_fn_t recv_modex_complete;
} pmix_gds_base_module_t;
/* NOTE: there is no public GDS interface structure - all access is
* done directly to/from an assigned module */
/* define the component structure */
typedef pmix_mca_base_component_t pmix_gds_base_component_t;
/*
* Macro for use in components that are of type gds
*/
#define PMIX_GDS_BASE_VERSION_1_0_0 PMIX_MCA_BASE_VERSION_1_0_0("gds", 1, 0, 0)
END_C_DECLS
#endif

View File

@@ -0,0 +1,314 @@
/* -*- Mode: C; c-basic-offset:4 ; indent-tabs-mode:nil -*- */
/*
* Copyright (c) 2004-2008 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2005 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2008-2012 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2015 Los Alamos National Security, LLC. All rights
* reserved.
* Copyright (c) 2016-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2021-2022 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
/**
* @file
*
* Top-level interface for all pmix MCA components.
*/
#ifndef PMIX_MCA_H
#define PMIX_MCA_H
#include "src/include/pmix_config.h"
/**
* Common type for all MCA modules.
*
* An instance of this type is always the first element in MCA
* modules, allowing the module to be associated with a
* particular version of a specific framework, and to publish its own
* name and version.
*/
struct pmix_mca_base_module_2_0_0_t {
int dummy_value;
};
/** Unversioned convenience typedef; use this name in
frameworks/components to stay forward source-compatible */
typedef struct pmix_mca_base_module_2_0_0_t pmix_mca_base_module_t;
/** Versioned convenience typedef */
typedef struct pmix_mca_base_module_2_0_0_t pmix_mca_base_module_2_0_0_t;
/**
* MCA component open function.
*
* @retval PMIX_SUCCESS This component can be used in the process.
*
* @retval PMIX_ERR_NOT_AVAILABLE Silently ignore this component for
* the duration of the process (it may even be unloaded from the
* process).
*
* @retval anything_else The MCA base will print an error message
* ignore this component for the duration of the process (it may even
* be unloaded from the process).
*
* All MCA components can have an "open" function that is invoked once
* per process, when the component is located and loaded.
*
* This function should avoid registering MCA parameters (use the
* component "register" function for that; i.e.,
* mca_base_register_component_params_2_0_0_fn_t for that). Legacy
* components still register MCA params in their component "open"
* function, but their authors should update them to use the component
* "register" function.
*
* This function can also be used to allocate any resources necessary
* for the component (e.g., heap memory).
*
* This function should return PMIX_SUCCESS if it wishes to remain
* loaded in the process. Any other return value will cause the MCA
* base to unload the component. Although most components do not use
* this mechanism to force themselves to be unloaded (because if they
* are immediately unloaded, ompi_info will not display them), the
* mechanism is available should the need arise.
*
* If the component a) has no MCA parameters to register, b) no
* resources to allocate, and c) can always be used in a process
* (albeit perhaps not selected), it may provide NULL for this
* function. In this cause, the MCA will act as if it called the open
* function and it returned PMIX_SUCCESS.
*/
typedef int (*pmix_mca_base_open_component_1_0_0_fn_t)(void);
/**
* MCA component close function.
*
* @retval PMIX_SUCCESS The component successfully shut down.
*
* @retval any_other_value Some error occurred, but is likely to be
* ignored.
*
* This function is invoked on a component after all of its modules
* have been finalized (according to the rules of its framework) and
* the component will never be used in the process again; the
* component may be unloaded from the process memory after the close
* function has been invoked.
*
* This function is typically used to release any resources still in
* use by the component.
*
* If the component has no resources to free, it may provide NULL for
* this function. In this case, the MCA will act as if it called the
* close function and it returned PMIX_SUCCESS.
*/
typedef int (*pmix_mca_base_close_component_1_0_0_fn_t)(void);
/**
* MCA component query function.
*
* @retval PMIX_SUCCESS The component successfully queried.
*
* @retval any_other_value Some error occurred, but is likely to be
* ignored.
*
* @param module The module to be used if this component is selected.
*
* @param priority The priority of this component.
*
* This function is used by the mca_base_select function to find the
* highest priority component to select. Frameworks are free to
* implement their own query function, but must also implement their
* own select function as a result.
*/
typedef int (*pmix_mca_base_query_component_2_0_0_fn_t)(pmix_mca_base_module_2_0_0_t **module,
int *priority);
/**
* MCA component parameter registration function.
*
* @retval PMIX_SUCCESS This component successfully registered its
* parameters and can be used in this process.
* @retval PMIX_ERR_BAD_PARAM Indicates that the register function
* failed because an MCA parameter got an invalid/incorrect value.
*
* @retval anything_else The MCA will ignore this component for the
* duration of the process.
*
* If a component has a non-NULL parameter registration function, it
* will be invoked to register all MCA parameters associated with the
* component. This function is invoked *before* the component "open"
* function is invoked.
*
* The registration function should not allocate any resources that
* need to be freed (aside from registering MCA parameters).
* Specifically, strings that are passed to the MCA parameter
* registration functions are all internally copied; there's no need
* for the caller to keep them after registering a parameter. Hence,
* it is possible that the registration function will be the *only*
* function invoked on a component; component authors should take care
* that no resources are leaked in this case.
*
* This function should return PMIX_SUCCESS if it wishes to remain
* loaded in the process. Any other return value will cause the MCA
* base to unload the component. Although most components do not use
* this mechanism to force themselves to be unloaded (because if they
* are immediately unloaded, ompi_info will not display them), the
* mechanism is available should the need arise.
*
* Note that if the function returns PMIX_ERR_BAD_PARAM, it is
* possible (likely?) that the component didn't register all of its
* parameters. When this happens, ompi_info (and friends) will stop
* execution and print out all existing registered parameters from the
* entire framework (since ompi_info doesn't track individual
* component register failures). This allows a user to know exactly
* what value is incorrect, and from where it was set (e.g., via an
* MCA params file).
*
* If the component a) has no MCA parameters to register, b) no
* resources to allocate, and c) can always be used in a process
* (albeit perhaps not selected), it may provide NULL for this
* function. In this cause, the MCA will act as if it called the
* registration function and it returned PMIX_SUCCESS.
*/
typedef int (*pmix_mca_base_register_component_params_2_0_0_fn_t)(void);
/**
* Maximum length of MCA project string names.
*/
#define PMIX_MCA_BASE_MAX_PROJECT_NAME_LEN 15
/**
* Maximum length of MCA framework string names.
*/
#define PMIX_MCA_BASE_MAX_TYPE_NAME_LEN 31
/**
* Maximum length of MCA component string names.
*/
#define PMIX_MCA_BASE_MAX_COMPONENT_NAME_LEN 63
/**
* Common type for all MCA components.
*
* An instance of this type is always the first element in MCA
* components, allowing the component to be associated with a
* particular version of a specific framework, and to publish its own
* name and version.
*/
struct pmix_mca_base_component_2_1_0_t {
int pmix_mca_major_version;
/**< Major number of the MCA. */
int pmix_mca_minor_version;
/**< Minor number of the MCA. */
int pmix_mca_release_version;
/**< Release number of the MCA. */
char pmix_mca_project_name[PMIX_MCA_BASE_MAX_PROJECT_NAME_LEN + 1];
/**< String name of the project that this component belongs to. */
int pmix_mca_project_major_version;
/**< Major version number of the project that this component
belongs to. */
int pmix_mca_project_minor_version;
/**< Minor version number of the project that this component
belongs to. */
int pmix_mca_project_release_version;
/**< Release version number of the project that this component
belongs to. */
char pmix_mca_type_name[PMIX_MCA_BASE_MAX_TYPE_NAME_LEN + 1];
/**< String name of the framework that this component belongs to. */
int pmix_mca_type_major_version;
/**< Major version number of the framework that this component
belongs to. */
int pmix_mca_type_minor_version;
/**< Minor version number of the framework that this component
belongs to. */
int pmix_mca_type_release_version;
/**< Release version number of the framework that this component
belongs to. */
char pmix_mca_component_name[PMIX_MCA_BASE_MAX_COMPONENT_NAME_LEN + 1];
/**< This comopnent's string name. */
int pmix_mca_component_major_version;
/**< This component's major version number. */
int pmix_mca_component_minor_version;
/**< This component's minor version number. */
int pmix_mca_component_release_version;
/**< This component's release version number. */
pmix_mca_base_open_component_1_0_0_fn_t pmix_mca_open_component;
/**< Method for opening this component. */
pmix_mca_base_close_component_1_0_0_fn_t pmix_mca_close_component;
/**< Method for closing this component. */
pmix_mca_base_query_component_2_0_0_fn_t pmix_mca_query_component;
/**< Method for querying this component. */
pmix_mca_base_register_component_params_2_0_0_fn_t pmix_mca_register_component_params;
/**< Method for registering the component's MCA parameters */
/** Extra space to allow for expansion in the future without
breaking older components. */
char reserved[32];
};
#define PMIX_BASE_COMPONENT_STATIC_INIT \
{ \
.pmix_mca_major_version = 0, \
.pmix_mca_minor_version = 0, \
.pmix_mca_release_version = 0, \
.pmix_mca_project_name = {0}, \
.pmix_mca_type_major_version = 0, \
.pmix_mca_type_minor_version = 0, \
.pmix_mca_type_release_version = 0, \
.pmix_mca_component_name = {0}, \
.pmix_mca_component_major_version = 0, \
.pmix_mca_component_minor_version = 0, \
.pmix_mca_component_release_version = 0, \
.pmix_mca_open_component = NULL, \
.pmix_mca_close_component = NULL, \
.pmix_mca_query_component = NULL, \
.pmix_mca_register_component_params = NULL, \
.reserved = {0} \
}
/** Unversioned convenience typedef; use this name in
frameworks/components to stay forward source-compatible */
typedef struct pmix_mca_base_component_2_1_0_t pmix_mca_base_component_t;
/** Versioned convenience typedef */
typedef struct pmix_mca_base_component_2_1_0_t pmix_mca_base_component_2_1_0_t;
/**
* Macro for framework author convenience.
*
* This macro is used by frameworks defining their component types,
* indicating that they subscribe to the MCA version 2.0.0. See
* component header files (e.g., coll.h) for examples of its usage.
*/
#define PMIX_MCA_BASE_VERSION_MAJOR 2
#define PMIX_MCA_BASE_VERSION_MINOR 1
#define PMIX_MCA_BASE_VERSION_RELEASE 0
#define PMIX_MCA_BASE_MAKE_VERSION(level, MAJOR, MINOR, RELEASE) \
.pmix_mca_##level##_major_version = MAJOR, .pmix_mca_##level##_minor_version = MINOR, \
.pmix_mca_##level##_release_version = RELEASE
#define PMIX_MCA_BASE_VERSION_2_1_0(PROJECT, project_major, project_minor, project_release, TYPE, \
type_major, type_minor, type_release) \
.pmix_mca_major_version = PMIX_MCA_BASE_VERSION_MAJOR, \
.pmix_mca_minor_version = PMIX_MCA_BASE_VERSION_MINOR, \
.pmix_mca_release_version = PMIX_MCA_BASE_VERSION_RELEASE, .pmix_mca_project_name = PROJECT, \
PMIX_MCA_BASE_MAKE_VERSION(project, project_major, project_minor, project_release), \
.pmix_mca_type_name = TYPE, \
PMIX_MCA_BASE_MAKE_VERSION(type, type_major, type_minor, type_release)
#define PMIX_MCA_BASE_VERSION_1_0_0(type, type_major, type_minor, type_release) \
PMIX_MCA_BASE_VERSION_2_1_0("pmix", PMIX_MAJOR_VERSION, PMIX_MINOR_VERSION, \
PMIX_RELEASE_VERSION, type, type_major, type_minor, type_release)
#endif /* PMIX_MCA_H */

View File

@@ -0,0 +1,85 @@
/*
* Copyright (c) 2004-2010 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
*
* Copyright (c) 2019 Intel, Inc. All rights reserved.
* Copyright (c) 2021-2022 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
#ifndef PMIX_COMPRESS_BASE_H
#define PMIX_COMPRESS_BASE_H
#include "pmix_config.h"
#include "src/mca/pcompress/pcompress.h"
#include "src/util/pmix_environ.h"
#include "src/mca/base/pmix_base.h"
/*
* Global functions for MCA overall COMPRESS
*/
#if defined(c_plusplus) || defined(__cplusplus)
extern "C" {
#endif
/* define a macro for quickly checking if a string exceeds the
* compression limit */
#define PMIX_STRING_SIZE_CHECK(s) \
(PMIX_STRING == (s)->type && NULL != (s)->data.string \
&& pmix_compress_base.compress_limit < strlen((s)->data.string))
#define PMIX_VALUE_COMPRESSED_STRING_UNPACK(s) \
do { \
char *tmp; \
/* if this is a compressed string, then uncompress it */ \
if (PMIX_COMPRESSED_STRING == (s)->type) { \
pmix_compress.decompress_string(&tmp, (uint8_t *) (s)->data.bo.bytes, \
(s)->data.bo.size); \
if (NULL == tmp) { \
PMIX_ERROR_LOG(PMIX_ERR_NOMEM); \
rc = PMIX_ERR_NOMEM; \
PMIX_VALUE_RELEASE(s); \
val = NULL; \
} else { \
PMIX_VALUE_DESTRUCT(s); \
(s)->data.string = tmp; \
(s)->type = PMIX_STRING; \
} \
} \
} while (0)
typedef struct {
size_t compress_limit;
bool selected;
bool silent;
} pmix_compress_base_t;
PMIX_EXPORT extern pmix_compress_base_t pmix_compress_base;
/**
* Select an available component.
*
* @retval OPAL_SUCCESS Upon Success
* @retval OPAL_NOT_FOUND If no component can be selected
* @retval OPAL_ERROR Upon other failure
*
*/
PMIX_EXPORT int pmix_compress_base_select(void);
/**
* Globals
*/
PMIX_EXPORT extern pmix_mca_base_framework_t pmix_pcompress_base_framework;
PMIX_EXPORT extern pmix_compress_base_module_t pmix_compress;
#if defined(c_plusplus) || defined(__cplusplus)
}
#endif
#endif /* PMIX_COMPRESS_BASE_H */

View File

@@ -0,0 +1,119 @@
/* -*- Mode: C; c-basic-offset:4 ; indent-tabs-mode:nil -*- */
/*
* Copyright (c) 2004-2010 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2015 Los Alamos National Security, LLC. All rights
* reserved.
*
* Copyright (c) 2019-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2021-2022 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
/**
* @file
*
* Compression Framework
*
* General Description:
*
* The PMIX Compress framework has been created to provide an abstract interface
* to the compression agent library on the host machine. This framework is useful
* when distributing files that can be compressed before sending to dimish the
* load on the network.
*
*/
#ifndef PMIX_MCA_COMPRESS_H
#define PMIX_MCA_COMPRESS_H
#include "pmix_config.h"
#include "src/class/pmix_object.h"
#include "src/mca/base/pmix_base.h"
#include "src/mca/mca.h"
#if defined(c_plusplus) || defined(__cplusplus)
extern "C" {
#endif
/**
* Module initialization function.
* Returns PMIX_SUCCESS
*/
typedef int (*pmix_compress_base_module_init_fn_t)(void);
/**
* Module finalization function.
* Returns PMIX_SUCCESS
*/
typedef int (*pmix_compress_base_module_finalize_fn_t)(void);
/**
* Compress a string
*
* Arguments:
*
*/
typedef bool (*pmix_compress_base_module_compress_string_fn_t)(char *instring, uint8_t **outbytes,
size_t *nbytes);
typedef bool (*pmix_compress_base_module_decompress_string_fn_t)(char **outstring, uint8_t *inbytes,
size_t len);
typedef size_t (*pmix_compress_base_module_get_decompressed_strlen_fn_t)(const pmix_byte_object_t *bo);
/**
* Compress a block
*
* Arguments:
*
*/
typedef bool (*pmix_compress_base_module_compress_fn_t)(const uint8_t *inbytes, size_t size,
uint8_t **outbytes, size_t *nbytes);
typedef bool (*pmix_compress_base_module_decompress_fn_t)(uint8_t **outbytes, size_t *outlen,
const uint8_t *inbytes, size_t len);
typedef size_t (*pmix_compress_base_module_get_decompressed_size_fn_t)(const pmix_byte_object_t *bo);
/**
* Structure for COMPRESS components.
*/
typedef pmix_mca_base_component_t pmix_compress_base_component_t;
/**
* Structure for COMPRESS modules
*/
struct pmix_compress_base_module_1_0_0_t {
/** Initialization Function */
pmix_compress_base_module_init_fn_t init;
/** Finalization Function */
pmix_compress_base_module_finalize_fn_t finalize;
/** Compress interface */
pmix_compress_base_module_compress_fn_t compress;
/** Decompress Interface */
pmix_compress_base_module_decompress_fn_t decompress;
pmix_compress_base_module_get_decompressed_size_fn_t get_decompressed_size;
/* COMPRESS STRING */
pmix_compress_base_module_compress_string_fn_t compress_string;
pmix_compress_base_module_decompress_string_fn_t decompress_string;
pmix_compress_base_module_get_decompressed_strlen_fn_t get_decompressed_strlen;
};
typedef struct pmix_compress_base_module_1_0_0_t pmix_compress_base_module_1_0_0_t;
typedef struct pmix_compress_base_module_1_0_0_t pmix_compress_base_module_t;
PMIX_EXPORT extern pmix_compress_base_module_t pmix_compress;
/**
* Macro for use in components that are of type COMPRESS
*/
#define PMIX_COMPRESS_BASE_VERSION_2_0_0 PMIX_MCA_BASE_VERSION_1_0_0("pcompress", 2, 0, 0)
#if defined(c_plusplus) || defined(__cplusplus)
}
#endif
#endif /* PMIX_COMPRESS_H */

View File

@@ -0,0 +1,99 @@
/*
* Copyright (c) 2004-2010 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2015 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2016-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2021-2022 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
#ifndef PMIX_PDL_BASE_H
#define PMIX_PDL_BASE_H
#include "src/include/pmix_config.h"
#include "src/mca/pdl/pdl.h"
#include "src/util/pmix_environ.h"
#include "src/mca/base/pmix_base.h"
BEGIN_C_DECLS
/**
* Globals
*/
PMIX_EXPORT extern pmix_mca_base_framework_t pmix_pdl_base_framework;
extern pmix_pdl_base_component_t *pmix_pdl_base_selected_component;
extern pmix_pdl_base_module_t *pmix_pdl;
/**
* Initialize the PDL MCA framework
*
* @retval PMIX_SUCCESS Upon success
* @retval PMIX_ERROR Upon failures
*
* This function is invoked during pmix_init();
*/
int pmix_pdl_base_open(pmix_mca_base_open_flag_t flags);
/**
* Select an available component.
*
* @retval PMIX_SUCCESS Upon Success
* @retval PMIX_NOT_FOUND If no component can be selected
* @retval PMIX_ERROR Upon other failure
*
*/
int pmix_pdl_base_select(void);
/**
* Finalize the PDL MCA framework
*
* @retval PMIX_SUCCESS Upon success
* @retval PMIX_ERROR Upon failures
*
* This function is invoked during pmix_finalize();
*/
int pmix_pdl_base_close(void);
/**
* Open a DSO
*
* (see pmix_pdl_base_module_open_ft_t in pmix/mca/pdl/pdl.h for
* documentation of this function)
*/
int pmix_pdl_open(const char *fname, bool use_ext, bool private_namespace,
pmix_pdl_handle_t **handle, char **err_msg);
/**
* Lookup a symbol in a DSO
*
* (see pmix_pdl_base_module_lookup_ft_t in pmix/mca/pdl/pdl.h for
* documentation of this function)
*/
int pmix_pdl_lookup(pmix_pdl_handle_t *handle, const char *symbol, void **ptr, char **err_msg);
/**
* Close a DSO
*
* (see pmix_pdl_base_module_close_ft_t in pmix/mca/pdl/pdl.h for
* documentation of this function)
*/
int pmix_pdl_close(pmix_pdl_handle_t *handle);
/**
* Iterate over files in a path
*
* (see pmix_pdl_base_module_foreachfile_ft_t in pmix/mca/pdl/pdl.h for
* documentation of this function)
*/
int pmix_pdl_foreachfile(const char *search_path,
int (*cb_func)(const char *filename, void *context), void *context);
END_C_DECLS
#endif /* PMIX_PDL_BASE_H */

View File

@@ -0,0 +1,181 @@
/* -*- Mode: C; c-basic-offset:4 ; indent-tabs-mode:nil -*- */
/*
* Copyright (c) 2015 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2015 Los Alamos National Security, LLC. All rights
* reserved.
* Copyright (c) 2020 Intel, Inc. All rights reserved.
* Copyright (c) 2021-2022 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
/**
* @file
*
* Dynamic library framework
*
* General Description:
*
* This framework provides portable access to dlopen- and dlsym-like
* functionality, very similar to Libtool's libltdl. Indeed, one of
* the components in this framework will use libltdl, if it is
* present/available. However, on some common types systems where
* libltdl headers and libraries are *not* available, we can support
* plugins via this simple framework.
*
* This is a compile-time framework: a single component will be
* selected by the priority that its configure.m4 provides. All other
* components will be ignored (i.e., not built/not part of the
* installation). Meaning: the static_components of the pdl framework
* will always contain 0 or 1 components.
*
* SIDENOTE: PMIX used to embed libltdl. However, as of early
* 2015, this became problematic, for a variety of complex and
* uninteresting reasons (see the following if you care about the
* details: https://github.com/open-mpi/ompi/issues/311,
* http://debbugs.gnu.org/cgi/bugreport.cgi?bug=19370,
* https://github.com/open-mpi/ompi/pull/366,
* https://github.com/open-mpi/ompi/pull/390). That being said, we,
* as a developer community, still wanted to be able to natively use
* DSOs by default. A small/simple framework for PDL functionality,
* along with a simple component that supports dlopen/dlsym on POSIX
* platforms and another component that natively uses libltdl seemed
* like a good solution.
*/
#ifndef PMIX_MCA_PDL_PDL_H
#define PMIX_MCA_PDL_PDL_H
#include "src/include/pmix_config.h"
#include "src/mca/base/pmix_base.h"
#include "src/mca/mca.h"
BEGIN_C_DECLS
/**
* Handle for an opened file
*/
struct pmix_pdl_handle_t;
typedef struct pmix_pdl_handle_t pmix_pdl_handle_t;
/**
* Dynamically open the file specified.
*
* Arguments:
* fname = Base filename to open. If NULL, open this process.
* use_ext = If true, try various filename suffixes that are
* relevant on this platform (e.g., .so, .dll, .dylib). If
* false, just use exactly whatever was passed as fname.
* private = If true, open the file in a private namespace.
* Otherwise, open the file in a global namespace.
* handle = Upon successful open, a handle to the opened file will
* be returned.
* err_msg= if non-NULL and !=PMIX_SUCCESS is returned, will point to a
* string error message
*
* Returns:
* PMIX_SUCCESS on success, or PMIX_ERROR
*
* Space for the handle must be allocated by the module (it can be
* freed during the call to pmix_pdl_base_module_dlclose_fn_t).
*
* The err_msg points to an internal string and should not be altered
* or freed by the caller. The contents of the err_msg string may
* change after successive calls to pmix_pdl API calls.
*/
typedef int (*pmix_pdl_base_module_open_fn_t)(const char *fname, bool use_ext,
bool private_namespace, pmix_pdl_handle_t **handle,
char **err_msg);
/**
* Lookup a symbol in an opened file.
*
* Arguments:
* handle = handle of a previously dynamically opened file
* symbol = name of the symbol to lookup
* ptr = if found, a pointer to the symbol. Otherwise, NULL.
* err_msg= if non-NULL and !=PMIX_SUCCESS is returned, will point to a
* string error message
* Returns:
* PMIX_SUCCESS on success, or PMIX_ERROR
*
*
* The err_msg points to an internal string and should not be altered
* or freed by the caller. The contents of the err_msg string may
* change after successive calls to pmix_pdl API calls.
*/
typedef int (*pmix_pdl_base_module_lookup_fn_t)(pmix_pdl_handle_t *handle, const char *symbol,
void **ptr, char **err_msg);
/**
* Dynamically close a previously dynamically-opened file.
*
* Arguments:
* handle = handle of a previously dynamically opened file.
* Returns:
* PMIX_SUCCESS on success, or PMIX_ERROR
*
* This function should close the file and free and resources
* associated with it (e.g., whatever is cached on the handle).
*/
typedef int (*pmix_pdl_base_module_close_fn_t)(pmix_pdl_handle_t *handle);
/**
* Search through a path of directories, invoking a callback on each
* unique regular (non-Libtool) file basename found (e.g., will only
* be invoked once for the files "foo.la" and "foo.so", with the
* parameter "foo").
*
* Arguments:
* path = PMIX_ENV_SEP-delimited list of directories
* cb_func= function to invoke on each filename found
* data = context for callback function
* Returns:
* PMIX_SUCESS on success, PMIX_ERR* otherwise
*/
typedef int (*pmix_pdl_base_module_foreachfile_fn_t)(
const char *search_path, int (*cb_func)(const char *filename, void *context), void *context);
/**
* Structure for PDL components.
*/
struct pmix_pdl_base_component_1_0_0_t {
/** MCA base component */
pmix_mca_base_component_t base_version;
/** Default priority */
int priority;
};
typedef struct pmix_pdl_base_component_1_0_0_t pmix_pdl_base_component_1_0_0_t;
typedef struct pmix_pdl_base_component_1_0_0_t pmix_pdl_base_component_t;
/**
* Structure for PDL modules
*/
struct pmix_pdl_base_module_1_0_0_t {
pmix_mca_base_module_2_0_0_t super;
/** Open / close */
pmix_pdl_base_module_open_fn_t open;
pmix_pdl_base_module_close_fn_t close;
/** Lookup a symbol */
pmix_pdl_base_module_lookup_fn_t lookup;
/** Iterate looking for files */
pmix_pdl_base_module_foreachfile_fn_t foreachfile;
};
typedef struct pmix_pdl_base_module_1_0_0_t pmix_pdl_base_module_1_0_0_t;
typedef struct pmix_pdl_base_module_1_0_0_t pmix_pdl_base_module_t;
/**
* Macro for use in components that are of type PDL
*/
#define PMIX_PDL_BASE_VERSION_1_0_0 PMIX_MCA_BASE_VERSION_1_0_0("pdl", 1, 0, 0)
END_C_DECLS
#endif /* PMIX_MCA_PDL_PDL_H */

View File

@@ -0,0 +1,31 @@
/*
* Copyright (c) 2010 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2016 Intel, Inc. All rights reserved.
* Copyright (c) 2022 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*
*/
#ifndef PMIX_PIF_BASE_H
#define PMIX_PIF_BASE_H
#include "src/include/pmix_config.h"
#include "src/mca/base/pmix_mca_base_framework.h"
#include "src/mca/pif/pif.h"
BEGIN_C_DECLS
/*
* Framework declaration
*/
PMIX_EXPORT extern pmix_mca_base_framework_t pmix_pif_base_framework;
END_C_DECLS
#endif /* PMIX_BASE_PIF_H */

View File

@@ -0,0 +1,93 @@
/* -*- Mode: C; c-basic-offset:4 ; indent-tabs-mode:nil -*- */
/*
* Copyright (c) 2010-2013 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2015 Los Alamos National Security, LLC. All rights
* reserved.
* Copyright (c) 2016-2019 Intel, Inc. All rights reserved.
* Copyright (c) 2021-2022 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
#ifndef PMIX_MCA_PIF_PIF_H
#define PMIX_MCA_PIF_PIF_H
#include "src/include/pmix_config.h"
#include <string.h>
#ifdef HAVE_UNISTD_H
# include <unistd.h>
#endif
#include <errno.h>
#ifdef HAVE_SYS_TYPES_H
# include <sys/types.h>
#endif
#ifdef HAVE_SYS_SOCKET_H
# include <sys/socket.h>
#endif
#ifdef HAVE_SYS_SOCKIO_H
# include <sys/sockio.h>
#endif
#ifdef HAVE_SYS_IOCTL_H
# include <sys/ioctl.h>
#endif
#ifdef HAVE_NETINET_IN_H
# include <netinet/in.h>
#endif
#ifdef HAVE_ARPA_INET_H
# include <arpa/inet.h>
#endif
#ifdef HAVE_NET_IF_H
# include <net/if.h>
#endif
#ifdef HAVE_NETDB_H
# include <netdb.h>
#endif
#ifdef HAVE_IFADDRS_H
# include <ifaddrs.h>
#endif
#include "src/mca/base/pmix_base.h"
#include "src/mca/mca.h"
#include "src/util/pmix_if.h"
BEGIN_C_DECLS
/*
* Define INADDR_NONE if we don't have it. Solaris is the only system
* where I have found that it does not exist, and the man page for
* inet_addr() says that it returns -1 upon failure. On Linux and
* other systems with INADDR_NONE, it's just a #define to -1 anyway.
* So just #define it to -1 here if it doesn't already exist.
*/
#if !defined(INADDR_NONE)
# define INADDR_NONE -1
#endif
#define DEFAULT_NUMBER_INTERFACES 10
#define MAX_PIFCONF_SIZE 10 * 1024 * 1024
/* "global" list of available interfaces */
extern pmix_list_t pmix_if_list;
/* global flags */
extern bool pmix_if_do_not_resolve;
extern bool pmix_if_retain_loopback;
/**
* Structure for if components.
*/
typedef pmix_mca_base_component_t pmix_pif_base_component_t;
/*
* Macro for use in components that are of type pif
*/
#define PMIX_PIF_BASE_VERSION_2_0_0 PMIX_MCA_BASE_VERSION_1_0_0("pif", 2, 0, 0)
END_C_DECLS
#endif /* PMIX_MCA_PIF_PIF_H */

View File

@@ -0,0 +1,43 @@
/*
* Copyright (c) 2006-2013 Los Alamos National Security, LLC. All rights
* reserved.
* Copyright (c) 2007-2010 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2010 Sandia National Laboratories. All rights reserved.
* Copyright (c) 2016-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2021 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*
*/
#ifndef PMIX_PINSTALLDIRS_BASE_H
#define PMIX_PINSTALLDIRS_BASE_H
#include "src/include/pmix_config.h"
#include "src/mca/base/pmix_mca_base_framework.h"
#include "src/mca/pinstalldirs/pinstalldirs.h"
/*
* Global functions for MCA overall pinstalldirs open and close
*/
BEGIN_C_DECLS
/**
* Framework structure declaration
*/
PMIX_EXPORT extern pmix_mca_base_framework_t pmix_pinstalldirs_base_framework;
/* Just like pmix_pinstall_dirs_expand() (see pinstalldirs.h), but will
also insert the value of the environment variable $PMIX_DESTDIR, if
it exists/is set. This function should *only* be used during the
setup routines of pinstalldirs. */
PMIX_EXPORT char *pmix_pinstall_dirs_expand_setup(const char *input);
PMIX_EXPORT int pmix_pinstall_dirs_base_init(pmix_info_t info[], size_t ninfo);
END_C_DECLS
#endif /* PMIX_BASE_PINSTALLDIRS_H */

View File

@@ -0,0 +1,57 @@
/* -*- Mode: C; c-basic-offset:4 ; indent-tabs-mode:nil -*- */
/*
* Copyright (c) 2006-2015 Los Alamos National Security, LLC. All rights
* reserved.
* Copyright (c) 2016-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2021-2022 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
#ifndef PMIX_MCA_PINSTALLDIRS_PINSTALLDIRS_H
#define PMIX_MCA_PINSTALLDIRS_PINSTALLDIRS_H
#include "src/include/pmix_config.h"
#include "pmix_common.h"
#include "src/mca/base/pmix_base.h"
#include "src/mca/mca.h"
#include "src/mca/pinstalldirs/pinstalldirs_types.h"
BEGIN_C_DECLS
/**
* Expand out path variables (such as ${prefix}) in the input string
* using the current pmix_pinstall_dirs structure */
PMIX_EXPORT char *pmix_pinstall_dirs_expand(const char *input);
/* optional initialization function */
typedef void (*pmix_install_dirs_init_fn_t)(pmix_info_t info[], size_t ninfo);
/**
* Structure for pinstalldirs components.
*/
struct pmix_pinstalldirs_base_component_2_0_0_t {
/** MCA base component */
pmix_mca_base_component_t component;
/** install directories provided by the given component */
pmix_pinstall_dirs_t install_dirs_data;
/* optional init function */
pmix_install_dirs_init_fn_t init;
};
/**
* Convenience typedef
*/
typedef struct pmix_pinstalldirs_base_component_2_0_0_t pmix_pinstalldirs_base_component_t;
/*
* Macro for use in components that are of type pinstalldirs
*/
#define PMIX_PINSTALLDIRS_BASE_VERSION_1_0_0 PMIX_MCA_BASE_VERSION_1_0_0("pinstalldirs", 1, 0, 0)
END_C_DECLS
#endif /* PMIX_MCA_PINSTALLDIRS_PINSTALLDIRS_H */

View File

@@ -0,0 +1,61 @@
/* -*- Mode: C; c-basic-offset:4 ; indent-tabs-mode:nil -*- */
/*
* Copyright (c) 2006-2015 Los Alamos National Security, LLC. All rights
* reserved.
* Copyright (c) 2016-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2021-2022 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
#ifndef PMIX_MCA_PINSTALLDIRS_PINSTALLDIRS_TYPES_H
#define PMIX_MCA_PINSTALLDIRS_PINSTALLDIRS_TYPES_H
#include "src/include/pmix_config.h"
#include "pmix_common.h"
BEGIN_C_DECLS
/*
* Most of this file is just for pmix_info. The only public interface
* once pmix_init has been called is the pmix_pinstall_dirs structure
* and the pmix_pinstall_dirs_expand() call */
struct pmix_pinstall_dirs_t {
char *prefix;
char *exec_prefix;
char *bindir;
char *sbindir;
char *libexecdir;
char *datarootdir;
char *datadir;
char *sysconfdir;
char *sharedstatedir;
char *localstatedir;
char *libdir;
char *includedir;
char *infodir;
char *mandir;
/* Rather than using pkg{data,lib,includedir}, use our own
pmix{data,lib,includedir}, which is always set to
{datadir,libdir,includedir}/pmix.
Note that these field names match macros set by configure that
are used in Makefile.am files. E.g., project help files are
installed into $(pmixdatadir). */
char *pmixdatadir;
char *pmixlibdir;
char *pmixincludedir;
};
typedef struct pmix_pinstall_dirs_t pmix_pinstall_dirs_t;
/* Install directories. Only available after pmix_init() */
PMIX_EXPORT extern pmix_pinstall_dirs_t pmix_pinstall_dirs;
END_C_DECLS
#endif /* PMIX_MCA_PINSTALLDIRS_PINSTALLDIRS_TYPES_H */

View File

@@ -0,0 +1,91 @@
/* -*- C -*-
*
* Copyright (c) 2004-2007 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2006 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2012 Los Alamos National Security, Inc. All rights reserved.
* Copyright (c) 2014-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2015-2020 Research Organization for Information Science
* and Technology (RIST). All rights reserved.
* Copyright (c) 2021-2022 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*
*/
#ifndef PMIX_PLOG_BASE_H_
#define PMIX_PLOG_BASE_H_
#include "src/include/pmix_config.h"
#ifdef HAVE_SYS_TIME_H
# include <sys/time.h> /* for struct timeval */
#endif
#ifdef HAVE_STRING_H
# include <string.h>
#endif
#include "src/class/pmix_list.h"
#include "src/class/pmix_pointer_array.h"
#include "src/mca/base/pmix_mca_base_framework.h"
#include "src/mca/mca.h"
#include "src/threads/pmix_threads.h"
#include "src/mca/plog/plog.h"
BEGIN_C_DECLS
/*
* MCA Framework
*/
PMIX_EXPORT extern pmix_mca_base_framework_t pmix_plog_base_framework;
/**
* PLOG select function
*
* Cycle across available components and construct the array
* of active modules
*/
PMIX_EXPORT pmix_status_t pmix_plog_base_select(void);
/**
* Track an active component / module
*/
struct pmix_plog_base_active_module_t {
pmix_list_item_t super;
bool reqd;
bool added;
int pri;
pmix_plog_module_t *module;
pmix_plog_base_component_t *component;
};
typedef struct pmix_plog_base_active_module_t pmix_plog_base_active_module_t;
PMIX_CLASS_DECLARATION(pmix_plog_base_active_module_t);
/* framework globals */
struct pmix_plog_globals_t {
pmix_lock_t lock;
pmix_pointer_array_t actives;
bool initialized;
bool selected;
char **channels;
};
typedef struct pmix_plog_globals_t pmix_plog_globals_t;
PMIX_EXPORT extern pmix_plog_globals_t pmix_plog_globals;
PMIX_EXPORT pmix_status_t pmix_plog_base_log(const pmix_proc_t *source, const pmix_info_t data[],
size_t ndata, const pmix_info_t directives[],
size_t ndirs, pmix_op_cbfunc_t cbfunc, void *cbdata);
END_C_DECLS
#endif

View File

@@ -0,0 +1,97 @@
/* -*- Mode: C; c-basic-offset:4 ; indent-tabs-mode:nil -*- */
/*
* Copyright (c) 2007-2008 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2015-2020 Intel, Inc. All rights reserved.
*
* Copyright (c) 2015 Research Organization for Information Science
* and Technology (RIST). All rights reserved.
* Copyright (c) 2021-2022 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
/**
* @file
*
* This interface is for use by PMIx servers to obtain network-related info
* such as security keys that need to be shared across applications, and to
* setup network support for applications prior to launch
*
* Available plugins may be defined at runtime via the typical MCA parameter
* syntax.
*/
#ifndef PMIX_PLOG_H
#define PMIX_PLOG_H
#include "src/include/pmix_config.h"
#include "pmix_common.h"
#include "src/class/pmix_list.h"
#include "src/include/pmix_globals.h"
#include "src/mca/base/pmix_mca_base_framework.h"
#include "src/mca/base/pmix_mca_base_var.h"
#include "src/mca/mca.h"
BEGIN_C_DECLS
/****** MODULE DEFINITION ******/
/**
* Initialize the module. Returns an error if the module cannot
* run, success if it can and wants to be used.
*/
typedef pmix_status_t (*pmix_plog_base_module_init_fn_t)(void);
/**
* Finalize the module
*/
typedef void (*pmix_plog_base_module_fini_fn_t)(void);
/**
* Log data to channel, if possible
*/
typedef pmix_status_t (*pmix_plog_base_module_log_fn_t)(const pmix_proc_t *source,
const pmix_info_t data[], size_t ndata,
const pmix_info_t directives[],
size_t ndirs, pmix_op_cbfunc_t cbfunc,
void *cbdata);
/**
* Base structure for a PLOG module
*/
typedef struct {
char *name;
char **channels;
/* init/finalize */
pmix_plog_base_module_init_fn_t init;
pmix_plog_base_module_fini_fn_t finalize;
pmix_plog_base_module_log_fn_t log;
} pmix_plog_module_t;
/**
* Base structure for a PLOG API
*/
typedef struct {
pmix_plog_base_module_log_fn_t log;
} pmix_plog_API_module_t;
/* declare the global APIs */
PMIX_EXPORT extern pmix_plog_API_module_t pmix_plog;
/*
* the standard component data structure
*/
typedef pmix_mca_base_component_t pmix_plog_base_component_t;
/*
* Macro for use in components that are of type plog
*/
#define PMIX_PLOG_BASE_VERSION_1_0_0 PMIX_MCA_BASE_VERSION_1_0_0("plog", 1, 0, 0)
END_C_DECLS
#endif

View File

@@ -0,0 +1,96 @@
/* -*- C -*-
*
* Copyright (c) 2004-2007 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2006 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2012 Los Alamos National Security, Inc. All rights reserved.
* Copyright (c) 2014-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2015-2020 Research Organization for Information Science
* and Technology (RIST). All rights reserved.
* Copyright (c) 2021-2023 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*
*/
#ifndef PMIX_PMDL_BASE_H_
#define PMIX_PMDL_BASE_H_
#include "src/include/pmix_config.h"
#ifdef HAVE_SYS_TIME_H
# include <sys/time.h> /* for struct timeval */
#endif
#ifdef HAVE_STRING_H
# include <string.h>
#endif
#include "src/class/pmix_list.h"
#include "src/class/pmix_pointer_array.h"
#include "src/mca/base/pmix_mca_base_framework.h"
#include "src/mca/mca.h"
#include "src/mca/pmdl/pmdl.h"
BEGIN_C_DECLS
/*
* MCA Framework
*/
PMIX_EXPORT extern pmix_mca_base_framework_t pmix_pmdl_base_framework;
/**
* PMDL select function
*
* Cycle across available components and construct the list
* of active modules
*/
PMIX_EXPORT pmix_status_t pmix_pmdl_base_select(void);
/**
* Track an active component / module
*/
struct pmix_pmdl_base_active_module_t {
pmix_list_item_t super;
int pri;
pmix_pmdl_module_t *module;
pmix_pmdl_base_component_t *component;
};
typedef struct pmix_pmdl_base_active_module_t pmix_pmdl_base_active_module_t;
PMIX_EXPORT PMIX_CLASS_DECLARATION(pmix_pmdl_base_active_module_t);
/* framework globals */
struct pmix_pmdl_globals_t {
pmix_lock_t lock;
pmix_list_t actives;
bool initialized;
bool selected;
};
typedef struct pmix_pmdl_globals_t pmix_pmdl_globals_t;
PMIX_EXPORT extern pmix_pmdl_globals_t pmix_pmdl_globals;
PMIX_EXPORT pmix_status_t pmix_pmdl_base_harvest_envars(char *nspace, const pmix_info_t info[],
size_t ninfo, pmix_list_t *ilist);
PMIX_EXPORT void pmix_pmdl_base_parse_file_envars(pmix_list_t *ilist);
PMIX_EXPORT bool pmix_pmdl_base_check_prte_param(char *param);
PMIX_EXPORT bool pmix_pmdl_base_check_pmix_param(char *param);
PMIX_EXPORT pmix_status_t pmix_pmdl_base_setup_nspace(pmix_namespace_t *nptr, pmix_info_t *info);
PMIX_EXPORT pmix_status_t pmix_pmdl_base_setup_nspace_kv(pmix_namespace_t *nptr, pmix_kval_t *kv);
PMIX_EXPORT pmix_status_t pmix_pmdl_base_register_nspace(pmix_namespace_t *nptr);
PMIX_EXPORT pmix_status_t pmix_pmdl_base_setup_client(pmix_namespace_t *nptr, pmix_rank_t rank,
uint32_t appnum);
PMIX_EXPORT pmix_status_t pmix_pmdl_base_setup_fork(const pmix_proc_t *peer, char ***env);
PMIX_EXPORT void pmix_pmdl_base_deregister_nspace(const char *nptr);
END_C_DECLS
#endif

View File

@@ -0,0 +1,152 @@
/* -*- Mode: C; c-basic-offset:4 ; indent-tabs-mode:nil -*- */
/*
* Copyright (c) 2007-2008 Cisco Systems, Inc. All rights reserved.
*
* Copyright (c) 2015-2018 Research Organization for Information Science
* and Technology (RIST). All rights reserved.
* Copyright (c) 2018-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2021-2023 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
/**
* @file
*
* This interface is for use by PMIx servers to obtain network-related info
* such as security keys that need to be shared across applications, and to
* setup network support for applications prior to launch
*
* Available plugins may be defined at runtime via the typical MCA parameter
* syntax.
*/
#ifndef PMIX_PMDL_H
#define PMIX_PMDL_H
#include "src/include/pmix_config.h"
#include "src/class/pmix_list.h"
#include "src/mca/base/pmix_mca_base_framework.h"
#include "src/mca/base/pmix_mca_base_var.h"
#include "src/mca/mca.h"
#include "src/server/pmix_server_ops.h"
BEGIN_C_DECLS
/****** MODULE DEFINITION ******/
/**
* Initialize the module. Returns an error if the module cannot
* run, success if it can and wants to be used.
*/
typedef pmix_status_t (*pmix_pmdl_base_module_init_fn_t)(void);
/**
* Finalize the module. Tear down any allocated storage, disconnect
* from any system support (e.g., LDAP server)
*/
typedef void (*pmix_pmdl_base_module_fini_fn_t)(void);
/* Harvest envars for this programming model so they can be forwarded
* to backend processes */
typedef pmix_status_t (*pmix_pmdl_base_module_harvest_envars_fn_t)(pmix_namespace_t *nptr,
const pmix_info_t info[],
size_t ninfo, pmix_list_t *ilist,
char ***priors);
/* Check a list of pmix_mca_base_var_file_value_t items that were
* read from a file to see if any belong to this programming
* model - if they do, then cache them for passing to any nspaces
* during harvest_envars */
typedef void (*pmix_pmdl_base_module_parse_file_envars_fn_t)(pmix_list_t *ilist);
/**
* Setup any programming model specific support for the given nspace
*/
typedef pmix_status_t (*pmix_pmdl_base_module_setup_ns_fn_t)(pmix_namespace_t *nptr,
pmix_info_t *info);
typedef pmix_status_t (*pmix_pmdl_base_module_setup_ns_kv_fn_t)(pmix_namespace_t *nptr,
pmix_kval_t *kv);
/* Allow programming models to add key-value pairs to the job-info - they
* can directly cache them in the GDS */
typedef pmix_status_t (*pmix_pmdl_base_module_reg_nspace_fn_t)(pmix_namespace_t *nptr);
/**
* Setup any programming model specific support for the given client */
typedef pmix_status_t (*pmix_pmdl_base_module_setup_client_fn_t)(pmix_namespace_t *nptr,
pmix_rank_t rank,
uint32_t apppnum);
/**
* Give the plugins an opportunity to add any envars to the
* environment of a local application process prior to fork/exec
*/
typedef pmix_status_t (*pmix_pmdl_base_module_setup_fork_fn_t)(const pmix_proc_t *peer, char ***env,
char ***priors);
/**
* Provide an opportunity for the fabric components to cleanup any
* resources they may have created to track the nspace
*/
typedef void (*pmix_pmdl_base_module_dregister_nspace_fn_t)(pmix_namespace_t *nptr);
/**
* Base structure for a PMDL module. Each component should malloc a
* copy of the module structure for each fabric plane they support.
*/
typedef struct {
char *name;
pmix_pmdl_base_module_init_fn_t init;
pmix_pmdl_base_module_fini_fn_t finalize;
pmix_pmdl_base_module_harvest_envars_fn_t harvest_envars;
pmix_pmdl_base_module_parse_file_envars_fn_t parse_file_envars;
pmix_pmdl_base_module_setup_ns_fn_t setup_nspace;
pmix_pmdl_base_module_setup_ns_kv_fn_t setup_nspace_kv;
pmix_pmdl_base_module_reg_nspace_fn_t register_nspace;
pmix_pmdl_base_module_setup_client_fn_t setup_client;
pmix_pmdl_base_module_setup_fork_fn_t setup_fork;
pmix_pmdl_base_module_dregister_nspace_fn_t deregister_nspace;
} pmix_pmdl_module_t;
/* define a public API */
typedef pmix_status_t (*pmix_pmdl_base_API_harvest_envars_fn_t)(char *nspace,
const pmix_info_t info[],
size_t ninfo, pmix_list_t *ilist);
typedef pmix_status_t (*pmix_pmdl_base_API_setup_fork_fn_t)(const pmix_proc_t *peer, char ***env);
typedef void (*pmix_pmdl_base_API_dregister_nspace_fn_t)(const char *nptr);
typedef struct {
char *name;
pmix_pmdl_base_module_init_fn_t init;
pmix_pmdl_base_module_fini_fn_t finalize;
pmix_pmdl_base_API_harvest_envars_fn_t harvest_envars;
pmix_pmdl_base_module_parse_file_envars_fn_t parse_file_envars;
pmix_pmdl_base_module_setup_ns_fn_t setup_nspace;
pmix_pmdl_base_module_setup_ns_kv_fn_t setup_nspace_kv;
pmix_pmdl_base_module_reg_nspace_fn_t register_nspace;
pmix_pmdl_base_module_setup_client_fn_t setup_client;
pmix_pmdl_base_API_setup_fork_fn_t setup_fork;
pmix_pmdl_base_API_dregister_nspace_fn_t deregister_nspace;
} pmix_pmdl_API_module_t;
/* declare the global APIs */
PMIX_EXPORT extern pmix_pmdl_API_module_t pmix_pmdl;
/*
* the standard component data structure
*/
typedef pmix_mca_base_component_t pmix_pmdl_base_component_t;
/*
* Macro for use in components that are of type pmdl
*/
#define PMIX_PMDL_BASE_VERSION_1_0_0 PMIX_MCA_BASE_VERSION_1_0_0("pmdl", 1, 0, 0)
END_C_DECLS
#endif

View File

@@ -0,0 +1,119 @@
/* -*- C -*-
*
* Copyright (c) 2004-2007 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2006 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2012 Los Alamos National Security, Inc. All rights reserved.
* Copyright (c) 2014-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2015-2020 Research Organization for Information Science
* and Technology (RIST). All rights reserved.
* Copyright (c) 2021 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*
*/
#ifndef PMIX_PNET_BASE_H_
#define PMIX_PNET_BASE_H_
#include "src/include/pmix_config.h"
#ifdef HAVE_SYS_TIME_H
# include <sys/time.h> /* for struct timeval */
#endif
#ifdef HAVE_STRING_H
# include <string.h>
#endif
#include "src/class/pmix_list.h"
#include "src/class/pmix_pointer_array.h"
#include "src/mca/base/pmix_mca_base_framework.h"
#include "src/mca/mca.h"
#include "src/mca/pnet/pnet.h"
BEGIN_C_DECLS
/*
* MCA Framework
*/
PMIX_EXPORT extern pmix_mca_base_framework_t pmix_pnet_base_framework;
/**
* PNET select function
*
* Cycle across available components and construct the list
* of active modules
*/
PMIX_EXPORT pmix_status_t pmix_pnet_base_select(void);
/**
* Track an active component / module
*/
struct pmix_pnet_base_active_module_t {
pmix_list_item_t super;
int pri;
pmix_pnet_module_t *module;
pmix_pnet_base_component_t *component;
};
typedef struct pmix_pnet_base_active_module_t pmix_pnet_base_active_module_t;
PMIX_EXPORT PMIX_CLASS_DECLARATION(pmix_pnet_base_active_module_t);
typedef struct {
pmix_list_item_t super;
char *name;
size_t index;
/* provide access to the component
* APIs that are managing this
* fabric plane */
pmix_pnet_module_t *module;
/* allow the component to add
* whatever structures it needs */
void *payload;
} pmix_pnet_fabric_t;
PMIX_EXPORT PMIX_CLASS_DECLARATION(pmix_pnet_fabric_t);
/* framework globals */
struct pmix_pnet_globals_t {
pmix_list_t actives;
pmix_list_t fabrics;
pmix_list_t nspaces;
bool selected;
};
typedef struct pmix_pnet_globals_t pmix_pnet_globals_t;
PMIX_EXPORT extern pmix_pnet_globals_t pmix_pnet_globals;
PMIX_EXPORT pmix_status_t pmix_pnet_base_allocate(char *nspace, pmix_info_t info[], size_t ninfo,
pmix_list_t *ilist);
PMIX_EXPORT pmix_status_t pmix_pnet_base_setup_local_network(char *nspace, pmix_info_t info[],
size_t ninfo);
PMIX_EXPORT pmix_status_t pmix_pnet_base_setup_fork(const pmix_proc_t *peer, char ***env);
PMIX_EXPORT void pmix_pnet_base_child_finalized(pmix_proc_t *peer);
PMIX_EXPORT void pmix_pnet_base_local_app_finalized(pmix_namespace_t *nptr);
PMIX_EXPORT void pmix_pnet_base_deregister_nspace(char *nspace);
PMIX_EXPORT pmix_status_t pmix_pnet_base_collect_inventory(pmix_info_t directives[], size_t ndirs,
pmix_list_t *inventory);
PMIX_EXPORT pmix_status_t pmix_pnet_base_deliver_inventory(pmix_info_t info[], size_t ninfo,
pmix_info_t directives[], size_t ndirs);
PMIX_EXPORT pmix_status_t pmix_pnet_base_harvest_envars(char **incvars, char **excvars,
pmix_list_t *ilist);
PMIX_EXPORT pmix_status_t pmix_pnet_base_register_fabric(pmix_fabric_t *fabric,
const pmix_info_t directives[],
size_t ndirs, pmix_op_cbfunc_t cbfunc,
void *cbdata);
PMIX_EXPORT pmix_status_t pmix_pnet_base_deregister_fabric(pmix_fabric_t *fabric);
PMIX_EXPORT pmix_status_t pmix_pnet_base_update_fabric(pmix_fabric_t *fabric);
END_C_DECLS
#endif

View File

@@ -0,0 +1,234 @@
/* -*- Mode: C; c-basic-offset:4 ; indent-tabs-mode:nil -*- */
/*
* Copyright (c) 2007-2008 Cisco Systems, Inc. All rights reserved.
*
* Copyright (c) 2015-2018 Research Organization for Information Science
* and Technology (RIST). All rights reserved.
* Copyright (c) 2018-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2021-2022 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
/**
* @file
*
* This interface is for use by PMIx servers to obtain network-related info
* such as security keys that need to be shared across applications, and to
* setup network support for applications prior to launch
*
* Available plugins may be defined at runtime via the typical MCA parameter
* syntax.
*/
#ifndef PMIX_PNET_H
#define PMIX_PNET_H
#include "src/include/pmix_config.h"
#include "include/pmix.h"
#include "src/class/pmix_list.h"
#include "src/include/pmix_globals.h"
#include "src/mca/base/pmix_mca_base_framework.h"
#include "src/mca/base/pmix_mca_base_var.h"
#include "src/mca/mca.h"
#include "src/server/pmix_server_ops.h"
BEGIN_C_DECLS
/****** MODULE DEFINITION ******/
/**
* Initialize the module. Returns an error if the module cannot
* run, success if it can and wants to be used.
*/
typedef pmix_status_t (*pmix_pnet_base_module_init_fn_t)(void);
/**
* Finalize the module. Tear down any allocated storage, disconnect
* from any system support (e.g., LDAP server)
*/
typedef void (*pmix_pnet_base_module_fini_fn_t)(void);
/**
* Allocate network resources. This can be called either as a result
* of a call to PMIx_Allocate_resources, or by the scheduler to
* provide an opportunity for the network to define values that
* are to be passed to an application. This can include security
* tokens required for application processes to communicate with
* each other, environmental variables picked up at the login node
* for forwarding to compute nodes, or allocation of static endpts
*/
typedef pmix_status_t (*pmix_pnet_base_module_allocate_fn_t)(pmix_namespace_t *nptr,
pmix_info_t info[], size_t ninfo,
pmix_list_t *ilist);
/**
* Give the local network library an opportunity to setup address information
* for the application by passing in the layout type and a regex describing
* the layout */
typedef pmix_status_t (*pmix_pnet_base_module_setup_local_net_fn_t)(pmix_nspace_env_cache_t *nptr,
pmix_info_t info[],
size_t ninfo);
/**
* Provide an opportunity for the local network library to cleanup when a
* local application process terminates
*/
typedef void (*pmix_pnet_base_module_child_finalized_fn_t)(pmix_proc_t *peer);
/**
* Provide an opportunity for the local network library to cleanup after
* all local clients for a given application have terminated
*/
typedef void (*pmix_pnet_base_module_local_app_finalized_fn_t)(pmix_namespace_t *nptr);
/**
* Provide an opportunity for the fabric components to cleanup any
* resource allocations (e.g., static ports) they may have assigned
*/
typedef void (*pmix_pnet_base_module_dregister_nspace_fn_t)(pmix_namespace_t *nptr);
/**
* Request that the module report local inventory for its network type.
*
* If the operation can be performed immediately, then the module should just
* add the inventory (as pmix_kval_t's) to the provided object's list and
* return PMIX_SUCCESS.
*
* If the module needs to perform some non-atomic operation
* (e.g., query a fabric manager), then it should shift to its own internal
* thread, return PMIX_OPERATION_IN_PROGRESS, and execute the provided
* callback function when the operation is completed.
*
* If there is no inventory to report, then just return PMIX_SUCCESS.
*
* If the module should be providing inventory but encounters an error,
* then immediately return an error code if the error is immediately detected,
* or execute the callback function with an error code if it is detected later.
*/
typedef pmix_status_t (*pmix_pnet_base_module_collect_inventory_fn_t)(
pmix_info_t directives[], size_t ndirs, pmix_list_t *inventory);
/**
* Deliver inventory for archiving by corresponding modules
*
* Modules are to search the provided inventory to identify
* entries provided by their remote peers, and then store that
* information in a manner that can be queried/retrieved by
* the host RM and/or scheduler. If the operation can be
* performed immediately (e.g., storing the information in
* the local hash table), then the module should just perform
* that operation and return the appropriate status.
*
* If the module needs to perform some non-atomic operation
* (e.g., storing the information in a non-local DHT), then
* it should shift to its own internal thread, return
* PMIX_OPERATION_IN_PROGRESS, and execute the provided
* callback function when the operation is completed.
*
* If there is no relevant inventory to archive, then the module
* should just return PMIX_SUCCESS;
*/
typedef pmix_status_t (*pmix_pnet_base_module_deliver_inventory_fn_t)(
pmix_info_t info[], size_t ninfo, pmix_info_t directives[], size_t ndirs);
/* Register to provide cost information
*
* Scan the provided directives to identify if the module
* should service this request - directives could include
* ordered specification of fabric type or a direct request
* for a specific component
*/
typedef pmix_status_t (*pmix_pnet_base_module_register_fabric_fn_t)(pmix_fabric_t *fabric,
const pmix_info_t directives[],
size_t ndirs,
pmix_op_cbfunc_t cbfunc,
void *cbdata);
/* Update the fabric information */
typedef pmix_status_t (*pmix_pnet_base_module_update_fabric_fn_t)(pmix_fabric_t *fabric);
/* Deregister the fabric, giving the associated module a chance to cleanup */
typedef pmix_status_t (*pmix_pnet_base_module_deregister_fabric_fn_t)(pmix_fabric_t *fabric);
/**
* Base structure for a PNET module. Each component should malloc a
* copy of the module structure for each fabric plane they support.
*/
typedef struct {
char *name;
/* provide a pointer to plane-specific metadata */
void *plane;
/* init/finalize */
pmix_pnet_base_module_init_fn_t init;
pmix_pnet_base_module_fini_fn_t finalize;
pmix_pnet_base_module_allocate_fn_t allocate;
pmix_pnet_base_module_setup_local_net_fn_t setup_local_network;
pmix_pnet_base_module_child_finalized_fn_t child_finalized;
pmix_pnet_base_module_local_app_finalized_fn_t local_app_finalized;
pmix_pnet_base_module_dregister_nspace_fn_t deregister_nspace;
pmix_pnet_base_module_collect_inventory_fn_t collect_inventory;
pmix_pnet_base_module_deliver_inventory_fn_t deliver_inventory;
pmix_pnet_base_module_register_fabric_fn_t register_fabric;
pmix_pnet_base_module_update_fabric_fn_t update_fabric;
pmix_pnet_base_module_deregister_fabric_fn_t deregister_fabric;
} pmix_pnet_module_t;
/* define a few API versions of the functions - main difference is the
* string nspace parameter instead of a pointer to pmix_namespace_t. This
* is done as an optimization to avoid having every component look for
* that pointer */
typedef pmix_status_t (*pmix_pnet_base_API_allocate_fn_t)(char *nspace, pmix_info_t info[],
size_t ninfo, pmix_list_t *ilist);
typedef pmix_status_t (*pmix_pnet_base_API_setup_local_net_fn_t)(char *nspace, pmix_info_t info[],
size_t ninfo);
/**
* Give the network framework an opportunity to add any envars to the
* environment of a local application process prior to fork/exec
*/
typedef pmix_status_t (*pmix_pnet_base_API_setup_fork_fn_t)(const pmix_proc_t *peer, char ***env);
typedef void (*pmix_pnet_base_API_deregister_nspace_fn_t)(char *nspace);
/**
* Base structure for a PNET API
*/
typedef struct {
char *name;
/* init/finalize */
pmix_pnet_base_module_init_fn_t init;
pmix_pnet_base_module_fini_fn_t finalize;
pmix_pnet_base_API_allocate_fn_t allocate;
pmix_pnet_base_API_setup_local_net_fn_t setup_local_network;
pmix_pnet_base_API_setup_fork_fn_t setup_fork;
pmix_pnet_base_module_child_finalized_fn_t child_finalized;
pmix_pnet_base_module_local_app_finalized_fn_t local_app_finalized;
pmix_pnet_base_API_deregister_nspace_fn_t deregister_nspace;
pmix_pnet_base_module_collect_inventory_fn_t collect_inventory;
pmix_pnet_base_module_deliver_inventory_fn_t deliver_inventory;
pmix_pnet_base_module_register_fabric_fn_t register_fabric;
pmix_pnet_base_module_update_fabric_fn_t update_fabric;
pmix_pnet_base_module_deregister_fabric_fn_t deregister_fabric;
} pmix_pnet_API_module_t;
/* declare the global APIs */
PMIX_EXPORT extern pmix_pnet_API_module_t pmix_pnet;
/*
* the standard component data structure
*/
typedef pmix_mca_base_component_t pmix_pnet_base_component_t;
/*
* Macro for use in components that are of type pnet
*/
#define PMIX_PNET_BASE_VERSION_1_0_0 PMIX_MCA_BASE_VERSION_1_0_0("pnet", 1, 0, 0)
END_C_DECLS
#endif

View File

@@ -0,0 +1,93 @@
/* -*- C -*-
*
* Copyright (c) 2004-2007 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2006 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2012 Los Alamos National Security, Inc. All rights reserved.
* Copyright (c) 2014-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2015-2020 Research Organization for Information Science
* and Technology (RIST). All rights reserved.
* Copyright (c) 2021-2022 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*
*/
#ifndef PMIX_PREG_BASE_H_
#define PMIX_PREG_BASE_H_
#include "src/include/pmix_config.h"
#ifdef HAVE_SYS_TIME_H
# include <sys/time.h> /* for struct timeval */
#endif
#ifdef HAVE_STRING_H
# include <string.h>
#endif
#include "src/class/pmix_pointer_array.h"
#include "src/mca/base/pmix_mca_base_framework.h"
#include "src/mca/mca.h"
#include "src/mca/preg/preg.h"
BEGIN_C_DECLS
/*
* MCA Framework
*/
PMIX_EXPORT extern pmix_mca_base_framework_t pmix_preg_base_framework;
/**
* PREG select function
*
* Cycle across available components and construct the list
* of active modules
*/
PMIX_EXPORT pmix_status_t pmix_preg_base_select(void);
/**
* Track an active component / module
*/
struct pmix_preg_base_active_module_t {
pmix_list_item_t super;
int pri;
pmix_preg_module_t *module;
pmix_mca_base_component_t *component;
};
typedef struct pmix_preg_base_active_module_t pmix_preg_base_active_module_t;
PMIX_CLASS_DECLARATION(pmix_preg_base_active_module_t);
/* framework globals */
struct pmix_preg_globals_t {
pmix_list_t actives;
bool initialized;
bool selected;
};
typedef struct pmix_preg_globals_t pmix_preg_globals_t;
PMIX_EXPORT extern pmix_preg_globals_t pmix_preg_globals;
PMIX_EXPORT pmix_status_t pmix_preg_base_generate_node_regex(const char *input, char **regex);
PMIX_EXPORT pmix_status_t pmix_preg_base_generate_ppn(const char *input, char **ppn);
PMIX_EXPORT pmix_status_t pmix_preg_base_parse_nodes(const char *regexp, char ***names);
PMIX_EXPORT pmix_status_t pmix_preg_base_parse_procs(const char *regexp, char ***procs);
PMIX_EXPORT pmix_status_t pmix_preg_base_copy(char **dest, size_t *len, const char *input);
PMIX_EXPORT pmix_status_t pmix_preg_base_pack(pmix_buffer_t *buffer, const char *input);
PMIX_EXPORT pmix_status_t pmix_preg_base_unpack(pmix_buffer_t *buffer, char **regex);
PMIX_EXPORT pmix_status_t pmix_preg_base_release(char *regexp);
END_C_DECLS
#endif

View File

@@ -0,0 +1,114 @@
/* -*- Mode: C; c-basic-offset:4 ; indent-tabs-mode:nil -*- */
/*
* Copyright (c) 2007-2008 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2015-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2015 Research Organization for Information Science
* and Technology (RIST). All rights reserved.
* Copyright (c) 2021-2022 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
/**
* @file
*
* This interface is for regex support. This is a multi-select framework.
*
* Available plugins may be defined at runtime via the typical MCA parameter
* syntax.
*/
#ifndef PMIX_PREG_H
#define PMIX_PREG_H
#include "src/include/pmix_config.h"
#include "src/mca/base/pmix_mca_base_framework.h"
#include "src/mca/base/pmix_mca_base_var.h"
#include "src/mca/bfrops/bfrops_types.h"
#include "src/mca/mca.h"
#include "src/mca/preg/preg_types.h"
BEGIN_C_DECLS
/****** MODULE DEFINITION ******/
#define PMIX_MAX_NODE_PREFIX 50
/* given a semicolon-separated list of input values, generate
* a regex that can be passed down to a client for parsing.
* The caller is responsible for free'ing the resulting
* string
*
* If values have leading zero's, then that is preserved.
* Example:
*
* Input: odin009;odin010;odin011;odin012;odin017;odin018;thor176
*
* Output:
* "foo:odin[009-012,017-018],thor176"
*
* Note that the "foo" at the beginning of the regex indicates
* that the "foo" regex component is to be used to parse the
* provided regex.
*/
typedef pmix_status_t (*pmix_preg_base_module_generate_node_regex_fn_t)(const char *input,
char **regex);
/* The input is expected to consist of a comma-separated list
* of ranges. Thus, an input of:
* "1-4;2-5;8,10,11,12;6,7,9"
* would generate a regex of
* "[pmix:2x(3);8,10-12;6-7,9]"
*
* Note that the "pmix" at the beginning of each regex indicates
* that the PMIx native parser is to be used by the client for
* parsing the provided regex. Other parsers may be supported - see
* the pmix_client.h header for a list.
*/
typedef pmix_status_t (*pmix_preg_base_module_generate_ppn_fn_t)(const char *input, char **ppn);
typedef pmix_status_t (*pmix_preg_base_module_parse_nodes_fn_t)(const char *regexp, char ***names);
typedef pmix_status_t (*pmix_preg_base_module_parse_procs_fn_t)(const char *regexp, char ***procs);
typedef pmix_status_t (*pmix_preg_base_module_copy_fn_t)(char **dest, size_t *len,
const char *input);
typedef pmix_status_t (*pmix_preg_base_module_pack_fn_t)(pmix_buffer_t *buffer, const char *regex);
typedef pmix_status_t (*pmix_preg_base_module_unpack_fn_t)(pmix_buffer_t *buffer, char **regex);
typedef pmix_status_t (*pmix_preg_base_module_release_fn_t)(char *regexp);
/**
* Base structure for a PREG module
*/
typedef struct {
char *name;
pmix_preg_base_module_generate_node_regex_fn_t generate_node_regex;
pmix_preg_base_module_generate_ppn_fn_t generate_ppn;
pmix_preg_base_module_parse_nodes_fn_t parse_nodes;
pmix_preg_base_module_parse_procs_fn_t parse_procs;
pmix_preg_base_module_copy_fn_t copy;
pmix_preg_base_module_pack_fn_t pack;
pmix_preg_base_module_unpack_fn_t unpack;
pmix_preg_base_module_release_fn_t release;
} pmix_preg_module_t;
/* we just use the standard component definition */
PMIX_EXPORT extern pmix_preg_module_t pmix_preg;
/*
* Macro for use in components that are of type preg
*/
#define PMIX_PREG_BASE_VERSION_1_0_0 PMIX_MCA_BASE_VERSION_1_0_0("preg", 1, 0, 0)
END_C_DECLS
#endif

View File

@@ -0,0 +1,61 @@
/* -*- C -*-
*
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2006 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2007-2011 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2012-2013 Los Alamos National Security, Inc. All rights reserved.
* Copyright (c) 2014-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2019 IBM Corporation. All rights reserved.
* Copyright (c) 2021 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
/**
* @file
*
* Buffer management types.
*/
#ifndef PMIX_MCA_PREG_TYPES_H_
#define PMIX_MCA_PREG_TYPES_H_
#include "src/include/pmix_config.h"
#include "src/class/pmix_list.h"
#include "src/class/pmix_object.h"
BEGIN_C_DECLS
/* these classes are required by the regex code */
typedef struct {
pmix_list_item_t super;
int start;
int cnt;
} pmix_regex_range_t;
PMIX_EXPORT PMIX_CLASS_DECLARATION(pmix_regex_range_t);
typedef struct {
/* list object */
pmix_list_item_t super;
char *prefix;
char *suffix;
int num_digits;
pmix_list_t ranges;
bool skip;
} pmix_regex_value_t;
PMIX_EXPORT PMIX_CLASS_DECLARATION(pmix_regex_value_t);
END_C_DECLS
#endif /* PMIX_PREG_TYPES_H */

View File

@@ -0,0 +1,84 @@
/* -*- C -*-
*
* Copyright (c) 2004-2007 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2006 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2012 Los Alamos National Security, Inc. All rights reserved.
* Copyright (c) 2014-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2015-2020 Research Organization for Information Science
* and Technology (RIST). All rights reserved.
* Copyright (c) 2021 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*
*/
#ifndef PMIX_PSEC_BASE_H_
#define PMIX_PSEC_BASE_H_
#include "src/include/pmix_config.h"
#ifdef HAVE_SYS_TIME_H
# include <sys/time.h> /* for struct timeval */
#endif
#ifdef HAVE_STRING_H
# include <string.h>
#endif
#include "src/class/pmix_pointer_array.h"
#include "src/mca/base/pmix_mca_base_framework.h"
#include "src/mca/mca.h"
#include "src/mca/psec/psec.h"
BEGIN_C_DECLS
/*
* MCA Framework
*/
PMIX_EXPORT extern pmix_mca_base_framework_t pmix_psec_base_framework;
/**
* PSEC select function
*
* Cycle across available components and construct the list
* of active modules
*/
PMIX_EXPORT pmix_status_t pmix_psec_base_select(void);
/**
* Track an active component / module
*/
struct pmix_psec_base_active_module_t {
pmix_list_item_t super;
int pri;
pmix_psec_module_t *module;
pmix_psec_base_component_t *component;
};
typedef struct pmix_psec_base_active_module_t pmix_psec_base_active_module_t;
PMIX_CLASS_DECLARATION(pmix_psec_base_active_module_t);
/* framework globals */
struct pmix_psec_globals_t {
pmix_list_t actives;
bool initialized;
bool selected;
};
typedef struct pmix_psec_globals_t pmix_psec_globals_t;
PMIX_EXPORT extern pmix_psec_globals_t pmix_psec_globals;
PMIX_EXPORT char *pmix_psec_base_get_available_modules(void);
PMIX_EXPORT pmix_psec_module_t *pmix_psec_base_assign_module(const char *options);
END_C_DECLS
#endif

View File

@@ -0,0 +1,209 @@
/* -*- Mode: C; c-basic-offset:4 ; indent-tabs-mode:nil -*- */
/*
* Copyright (c) 2007-2008 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2015-2020 Intel, Inc. All rights reserved.
*
* Copyright (c) 2015 Research Organization for Information Science
* and Technology (RIST). All rights reserved.
* Copyright (c) 2019 Mellanox Technologies, Inc. All rights reserved.
* Copyright (c) 2021-2022 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
/**
* @file
*
* This interface is for psecurity support. PMIx doesn't need much in
* this regard, but we do need a mechanism for authenticating connections.
*
* Only *one* plugin will be active in a client, but multiple plugins may
* be active in a server. Thus, this is a multi-select framework.
*
* Available plugins may be defined at runtime via the typical MCA parameter
* syntax.
*/
#ifndef PMIX_PSEC_H
#define PMIX_PSEC_H
#include "src/include/pmix_config.h"
#include "src/mca/base/pmix_mca_base_framework.h"
#include "src/mca/base/pmix_mca_base_var.h"
#include "src/mca/mca.h"
#include "src/mca/ptl/ptl_types.h"
BEGIN_C_DECLS
/* forward declaration */
struct pmix_peer_t;
/****** MODULE DEFINITION ******/
/**
* Initialize the module. Returns an error if the module cannot
* run, success if it can and wants to be used.
*/
typedef pmix_status_t (*pmix_psec_base_module_init_fn_t)(void);
/**
* Finalize the module. Tear down any allocated storage, disconnect
* from any system support (e.g., LDAP server)
*/
typedef void (*pmix_psec_base_module_fini_fn_t)(void);
/**** CLIENT-SIDE FUNCTIONS ****/
/**
* Create and return a credential for this client - this
* could be a string or a byte array, which is why we must
* also return the length. The directives contain info on
* desired credential type, or other directives used by
* the credential agent. The returned info array typically
* contains the name of the agent issuing the credential,
* plus any other info the agent chooses to return.
*/
typedef pmix_status_t (*pmix_psec_base_module_create_cred_fn_t)(struct pmix_peer_t *peer,
const pmix_info_t directives[],
size_t ndirs, pmix_info_t **info,
size_t *ninfo,
pmix_byte_object_t *cred);
/**
* Perform the client-side handshake. Note that it is not required
* (and indeed, would be rare) for a protocol to use both the
* credential and handshake interfaces. It is acceptable, therefore,
* for one of them to be NULL */
typedef pmix_status_t (*pmix_psec_base_module_client_hndshk_fn_t)(int sd);
/**** SERVER-SIDE FUNCTIONS ****/
/**
* Validate a client's credential - the credential could be a string
* or an array of bytes, which is why we include the length. The directives
* contain information provided by the requestor to aid in the validation
* process - e.g., the uid/gid of the process seeking validation, or
* the name of the agent being asked to perform the validation. The
* returned info array typically contains the name of the agent that
* actually performed the validation, plus any other info the agent
* chooses to return (e.g., the uid/gid contained in the credential)
*/
typedef pmix_status_t (*pmix_psec_base_module_validate_cred_fn_t)(struct pmix_peer_t *peer,
const pmix_info_t directives[],
size_t ndirs, pmix_info_t **info,
size_t *ninfo,
const pmix_byte_object_t *cred);
/**
* Perform the server-side handshake. Note that it is not required
* (and indeed, would be rare) for a protocol to use both the
* credential and handshake interfaces. It is acceptable, therefore,
* for one of them to be NULL */
typedef pmix_status_t (*pmix_psec_base_module_server_hndshk_fn_t)(int sd);
/**
* Base structure for a PSEC module
*/
typedef struct {
char *name;
/* init/finalize */
pmix_psec_base_module_init_fn_t init;
pmix_psec_base_module_fini_fn_t finalize;
/** Client-side */
pmix_psec_base_module_create_cred_fn_t create_cred;
pmix_psec_base_module_client_hndshk_fn_t client_handshake;
/** Server-side */
pmix_psec_base_module_validate_cred_fn_t validate_cred;
pmix_psec_base_module_server_hndshk_fn_t server_handshake;
} pmix_psec_module_t;
/* define an API module */
/* get a list of available options - caller must free results
* when done */
PMIX_EXPORT char *pmix_psec_base_get_available_modules(void);
/* Select a psec module for a given peer */
PMIX_EXPORT pmix_psec_module_t *pmix_psec_base_assign_module(const char *options);
/* MACROS FOR EXECUTING PSEC FUNCTIONS */
#define PMIX_PSEC_CREATE_CRED(r, p, d, nd, in, nin, c) \
(r) = (p)->nptr->compat.psec->create_cred((struct pmix_peer_t *) (p), (d), (nd), (in), (nin), c)
#define PMIX_PSEC_CLIENT_HANDSHAKE(r, p, sd) (r) = (p)->nptr->compat.psec->client_handshake(sd)
#define PMIX_PSEC_VALIDATE_CRED(r, p, d, nd, in, nin, c) \
(r) = (p)->nptr->compat.psec->validate_cred((struct pmix_peer_t *) (p), (d), (nd), (in), \
(nin), c)
#define PMIX_PSEC_VALIDATE_CONNECTION(r, p, d, nd, in, nin, c) \
do { \
int _r; \
/* if a credential is available, then check it */ \
if (NULL != (p)->nptr->compat.psec->validate_cred) { \
_r = (p)->nptr->compat.psec->validate_cred((struct pmix_peer_t *) (p), (d), (nd), \
(in), (nin), c); \
if (PMIX_SUCCESS != _r) { \
pmix_output_verbose(2, pmix_globals.debug_output, \
"validation of credential failed: %s", PMIx_Error_string(_r)); \
} else { \
pmix_output_verbose(2, pmix_globals.debug_output, "credential validated"); \
} \
(r) = _r; \
} else if (NULL != (p)->nptr->compat.psec->server_handshake) { \
/* request the handshake if the security mode calls for it */ \
pmix_output_verbose(2, pmix_globals.debug_output, "requesting handshake"); \
_r = PMIX_ERR_READY_FOR_HANDSHAKE; \
(r) = _r; \
} else { \
/* this is not allowed */ \
(r) = PMIX_ERR_NOT_SUPPORTED; \
} \
} while (0)
#define PMIX_PSEC_SERVER_HANDSHAKE_IFNEED(r, p, d, nd, in, nin, c) \
if (PMIX_ERR_READY_FOR_HANDSHAKE == r) { \
int _r; \
/* execute the handshake if the security mode calls for it */ \
pmix_output_verbose(2, pmix_globals.debug_output, "executing handshake"); \
if (PMIX_SUCCESS != (_r = p->nptr->compat.psec->server_handshake((p)->sd))) { \
PMIX_ERROR_LOG(_r); \
} \
/* Update the reply status */ \
(r) = _r; \
}
/**** COMPONENT STRUCTURE DEFINITION ****/
/* define a component-level API for initializing the component */
typedef pmix_status_t (*pmix_psec_base_component_init_fn_t)(void);
/* define a component-level API for finalizing the component */
typedef void (*pmix_psec_base_component_finalize_fn_t)(void);
/* define a component-level API for getting a module */
typedef pmix_psec_module_t *(*pmix_psec_base_component_assign_module_fn_t)(void);
/*
* the standard component data structure
*/
struct pmix_psec_base_component_t {
pmix_mca_base_component_t base;
int priority;
pmix_psec_base_component_init_fn_t init;
pmix_psec_base_component_finalize_fn_t finalize;
pmix_psec_base_component_assign_module_fn_t assign_module;
};
typedef struct pmix_psec_base_component_t pmix_psec_base_component_t;
/*
* Macro for use in components that are of type psec
*/
#define PMIX_PSEC_BASE_VERSION_1_0_0 PMIX_MCA_BASE_VERSION_1_0_0("psec", 1, 0, 0)
END_C_DECLS
#endif

View File

@@ -0,0 +1,61 @@
/*
* Copyright (c) 2009 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2013 Los Alamos National Security, LLC. All rights reserved.
* Copyright (c) 2017-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2020 Research Organization for Information Science
* and Technology (RIST). All rights reserved.
* Copyright (c) 2021 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
/** @file:
*/
#ifndef PMIX_PSENSOR_BASE_H_
#define PMIX_PSENSOR_BASE_H_
#include "src/include/pmix_config.h"
#include "src/class/pmix_list.h"
#include "src/mca/base/pmix_mca_base_framework.h"
#include "src/mca/mca.h"
#include "src/mca/psensor/psensor.h"
BEGIN_C_DECLS
/*
* MCA Framework
*/
PMIX_EXPORT extern pmix_mca_base_framework_t pmix_psensor_base_framework;
PMIX_EXPORT int pmix_psensor_base_select(void);
/* define a struct to hold framework-global values */
typedef struct {
pmix_list_t actives;
pmix_event_base_t *evbase;
bool selected;
} pmix_psensor_base_t;
typedef struct {
pmix_list_item_t super;
pmix_psensor_base_component_t *component;
pmix_psensor_base_module_t *module;
int priority;
} pmix_psensor_active_module_t;
PMIX_CLASS_DECLARATION(pmix_psensor_active_module_t);
PMIX_EXPORT extern pmix_psensor_base_t pmix_psensor_base;
PMIX_EXPORT pmix_status_t pmix_psensor_base_start(pmix_peer_t *requestor, pmix_status_t error,
const pmix_info_t *monitor,
const pmix_info_t directives[], size_t ndirs);
PMIX_EXPORT pmix_status_t pmix_psensor_base_stop(pmix_peer_t *requestor, char *id);
END_C_DECLS
#endif

View File

@@ -0,0 +1,82 @@
/*
* Copyright (c) 2009 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2012 Los Alamos National Security, Inc. All rights reserved.
* Copyright (c) 2014-2020 Intel, Inc. All rights reserved.
*
* Copyright (c) 2021-2022 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*
* @file:
*
*/
#ifndef PMIX_PSENSOR_H_
#define PMIX_PSENSOR_H_
#include "src/include/pmix_config.h"
#include "src/class/pmix_list.h"
#include "src/include/pmix_globals.h"
#include "src/mca/mca.h"
BEGIN_C_DECLS
/*
* Component functions - all MUST be provided!
*/
/* start a sensor operation:
*
* requestor - the process requesting this operation
*
* monitor - a PMIx attribute specifying what is to be monitored
*
* directives - an array of pmix_info_t specifying relevant limits on values, and action
* to be taken when limits exceeded. Can include
* user-provided "id" string */
typedef pmix_status_t (*pmix_psensor_base_module_start_fn_t)(pmix_peer_t *requestor,
pmix_status_t error,
const pmix_info_t *monitor,
const pmix_info_t directives[],
size_t ndirs);
/* stop a sensor operation:
*
* requestor - the process requesting this operation
*
* id - the "id" string provided by the user at the time the
* affected monitoring operation was started. A NULL indicates
* that all operations started by this requestor are to
* be terminated */
typedef pmix_status_t (*pmix_psensor_base_module_stop_fn_t)(pmix_peer_t *requestor, char *id);
/* API module */
/*
* Ver 1.0
*/
typedef struct pmix_psensor_base_module_1_0_0_t {
pmix_psensor_base_module_start_fn_t start;
pmix_psensor_base_module_stop_fn_t stop;
} pmix_psensor_base_module_t;
/*
* the standard component data structure
*/
typedef pmix_mca_base_component_t pmix_psensor_base_component_t;
/*
* Macro for use in components that are of type sensor v1.0.0
*/
#define PMIX_PSENSOR_BASE_VERSION_1_0_0 PMIX_MCA_BASE_VERSION_1_0_0("psensor", 1, 0, 0)
/* Global structure for accessing sensor functions
*/
PMIX_EXPORT extern pmix_psensor_base_module_t pmix_psensor; /* holds API function pointers */
END_C_DECLS
#endif /* MCA_SENSOR_H */

View File

@@ -0,0 +1,83 @@
/* -*- C -*-
*
* Copyright (c) 2019 IBM Corporation. All rights reserved.
* Copyright (c) 2019 Mellanox Technologies, Inc.
* All rights reserved.
* Copyright (c) 2020 Research Organization for Information Science
* and Technology (RIST). All rights reserved.
* Copyright (c) 2020 Intel, Inc. All rights reserved.
* Copyright (c) 2021 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*
*/
#ifndef PMIX_PSQUASH_BASE_H_
#define PMIX_PSQUASH_BASE_H_
#include "src/include/pmix_config.h"
#ifdef HAVE_STRING_H
# include <string.h>
#endif
#include "src/class/pmix_pointer_array.h"
#include "src/mca/base/pmix_mca_base_framework.h"
#include "src/mca/mca.h"
#include "src/mca/psquash/psquash.h"
BEGIN_C_DECLS
/**
* Sizeof by PMIx type integer values.
*
* r - return status code
* t - type (pmix_data_type_t) of integer value
* s - size of type in bytes
* (see a comment to `pmix_bfrops_pack_flex` for additional details)
*/
#define PMIX_SQUASH_TYPE_SIZEOF(r, t, s) \
do { \
(r) = PMIX_SUCCESS; \
switch (t) { \
case PMIX_INT16: \
case PMIX_UINT16: \
(s) = SIZEOF_SHORT; \
break; \
case PMIX_INT: \
case PMIX_INT32: \
case PMIX_UINT: \
case PMIX_UINT32: \
(s) = SIZEOF_INT; \
break; \
case PMIX_INT64: \
case PMIX_UINT64: \
(s) = SIZEOF_LONG; \
break; \
case PMIX_SIZE: \
(s) = SIZEOF_SIZE_T; \
break; \
default: \
(r) = PMIX_ERR_BAD_PARAM; \
} \
} while (0)
struct pmix_psquash_globals_t {
bool initialized;
bool selected;
};
typedef struct pmix_psquash_globals_t pmix_psquash_globals_t;
PMIX_EXPORT extern pmix_mca_base_framework_t pmix_psquash_base_framework;
PMIX_EXPORT pmix_status_t pmix_psquash_base_select(void);
PMIX_EXPORT extern pmix_psquash_globals_t pmix_psquash_globals;
END_C_DECLS
#endif

View File

@@ -0,0 +1,118 @@
/* -*- Mode: C; c-basic-offset:4 ; indent-tabs-mode:nil -*- */
/*
* Copyright (c) 2019 IBM Corporation. All rights reserved.
* Copyright (c) 2019 Mellanox Technologies, Inc.
* All rights reserved.
* Copyright (c) 2020 Intel, Inc. All rights reserved.
* Copyright (c) 2021-2022 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
/**
* @file
*
* This interface is for the encoding/decoding of basic types and the
* compression/decompression of larger blobs of data (i.e., modex).
*
* Available plugins may be defined at runtime via the typical MCA parameter
* syntax.
*/
#ifndef PMIX_PSQUASH_H
#define PMIX_PSQUASH_H
#include "src/include/pmix_config.h"
#include "src/mca/base/pmix_mca_base_framework.h"
#include "src/mca/base/pmix_mca_base_var.h"
#include "src/mca/mca.h"
BEGIN_C_DECLS
/****** MODULE DEFINITION ******/
/**
* Initialize the module
*/
typedef pmix_status_t (*pmix_psquash_base_module_init_fn_t)(void);
/**
* Finalize the module
*/
typedef void (*pmix_psquash_base_module_finalize_fn_t)(void);
/**
* Maximum size of the type.
*
* type - Type (PMIX_SIZE, PMIX_INT to PMIX_UINT64)
* size - size of the type
*/
typedef pmix_status_t (*pmix_psquash_get_max_size_fn_t)(pmix_data_type_t type, size_t *size);
/**
* Encode a basic integer type into a contiguous destination buffer.
*
* type - Type of the 'src' pointer (PMIX_SIZE, PMIX_INT to PMIX_UINT64)
* src - pointer to a single basic integer type
* dest - pointer to buffer to store data
* dst_len - pointer to the packed size of dest, in bytes
*/
typedef pmix_status_t (*pmix_psquash_encode_int_fn_t)(pmix_data_type_t type, void *src, void *dest,
size_t *dst_len);
/**
* Decode a basic a contiguous destination buffer into a basic integer type.
*
* type - Type of the 'dest' pointer (PMIX_SIZE, PMIX_INT to PMIX_UINT64)
* src - pointer to buffer where data was stored
* src_len - length, in bytes, of the src buffer
* dest - pointer to a single basic integer type
* dst_len - pointer to the unpacked size of dest, in bytes
*/
typedef pmix_status_t (*pmix_psquash_decode_int_fn_t)(pmix_data_type_t type, void *src,
size_t src_len, void *dest, size_t *dst_len);
/**
* Base structure for a PSQUASH module
*/
typedef struct {
const char *name;
/* flag indicating if the type is encoded within the value, otherwise, it is necessary to
* further pack the type with the value. */
bool int_type_is_encoded;
/** init/finalize */
pmix_psquash_base_module_init_fn_t init;
pmix_psquash_base_module_finalize_fn_t finalize;
pmix_psquash_get_max_size_fn_t get_max_size;
/** Integer compression */
pmix_psquash_encode_int_fn_t encode_int;
pmix_psquash_decode_int_fn_t decode_int;
} pmix_psquash_base_module_t;
/**
* Base structure for a PSQUASH component
*/
struct pmix_psquash_base_component_t {
pmix_mca_base_component_t base;
int priority;
};
typedef struct pmix_psquash_base_component_t pmix_psquash_base_component_t;
PMIX_EXPORT extern pmix_psquash_base_module_t pmix_psquash;
/*
* Macro for use in components that are of type psquash
*/
#define PMIX_PSQUASH_BASE_VERSION_1_0_0 PMIX_MCA_BASE_VERSION_1_0_0("psquash", 1, 0, 0)
END_C_DECLS
#endif

View File

@@ -0,0 +1,60 @@
/*
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2006 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2007-2020 Cisco Systems, Inc. All rights reserved
* Copyright (c) 2019 Intel, Inc. All rights reserved.
* Copyright (c) 2021 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*
*/
#ifndef PMIX_PSTAT_BASE_H
#define PMIX_PSTAT_BASE_H
#include "pmix_config.h"
#include "src/mca/base/pmix_mca_base_framework.h"
#include "src/mca/pstat/pstat.h"
/*
* Global functions for MCA overall pstat open and close
*/
BEGIN_C_DECLS
/**
* Framework structure declaration for this framework
*/
PMIX_EXPORT extern pmix_mca_base_framework_t pmix_pstat_base_framework;
/**
* Select an available component.
*
* @return PMIX_SUCCESS Upon success.
* @return PMIX_NOT_FOUND If no component can be selected.
* @return PMIX_ERROR Upon other failure.
*
* At the end of this process, we'll either have a single
* component that is selected and initialized, or no component was
* selected. If no component was selected, subsequent invocation
* of the pstat functions will return an error indicating no data
* could be obtained
*/
PMIX_EXPORT int pmix_pstat_base_select(void);
PMIX_EXPORT extern pmix_pstat_base_component_t *pmix_pstat_base_component;
END_C_DECLS
#endif /* PMIX_BASE_PSTAT_H */

View File

@@ -0,0 +1,82 @@
/* -*- Mode: C; c-basic-offset:4 ; indent-tabs-mode:nil -*- */
/*
* Copyright (c) 2004-2007 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2008 The Trustees of Indiana University.
* All rights reserved.
* Copyright (c) 2015 Los Alamos National Security, LLC. All rights
* reserved.
*
* Copyright (c) 2019 Intel, Inc. All rights reserved.
* Copyright (c) 2020 Cisco Systems, Inc. All rights reserved
* Copyright (c) 2021-2022 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
/**
* @file
*
* pstat (process statistics) framework component interface.
*
* Intent
*
* To support the ompi-top utility.
*
*/
#ifndef PMIX_MCA_PSTAT_H
#define PMIX_MCA_PSTAT_H
#include "pmix_config.h"
#include "pmix_common.h"
#include "src/mca/base/pmix_base.h"
#include "src/mca/mca.h"
BEGIN_C_DECLS
/**
* Module initialization function. Should return PMIX_SUCCESS.
*/
typedef int (*pmix_pstat_base_module_init_fn_t)(void);
typedef int (*pmix_pstat_base_module_query_fn_t)(pid_t pid, pmix_proc_stats_t *stats,
pmix_node_stats_t *nstats);
typedef int (*pmix_pstat_base_module_fini_fn_t)(void);
/**
* Structure for pstat components.
*/
typedef pmix_mca_base_component_t pmix_pstat_base_component_t;
/**
* Structure for pstat modules
*/
struct pmix_pstat_base_module_1_0_0_t {
pmix_pstat_base_module_init_fn_t init;
pmix_pstat_base_module_query_fn_t query;
pmix_pstat_base_module_fini_fn_t finalize;
};
/**
* Convenience typedef
*/
typedef struct pmix_pstat_base_module_1_0_0_t pmix_pstat_base_module_1_0_0_t;
typedef struct pmix_pstat_base_module_1_0_0_t pmix_pstat_base_module_t;
/**
* Macro for use in components that are of type pstat
*/
#define PMIX_PSTAT_BASE_VERSION_1_0_0 PMIX_MCA_BASE_VERSION_1_0_0("pstat", 1, 0, 0)
/* Global structure for accessing pstat functions */
PMIX_EXPORT extern pmix_pstat_base_module_t pmix_pstat;
END_C_DECLS
#endif /* PMIX_MCA_PSTAT_H */

View File

@@ -0,0 +1,184 @@
/* -*- C -*-
*
* Copyright (c) 2004-2007 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2006 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2012 Los Alamos National Security, Inc. All rights reserved.
* Copyright (c) 2014-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2015-2020 Research Organization for Information Science
* and Technology (RIST). All rights reserved.
* Copyright (c) 2021-2024 Nanook Consulting All rights reserved.
* Copyright (c) 2023 Triad National Security, LLC. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*
*/
#ifndef PMIX_PTL_BASE_H_
#define PMIX_PTL_BASE_H_
#include "src/include/pmix_config.h"
#ifdef HAVE_SYS_TIME_H
# include <sys/time.h> /* for struct timeval */
#endif
#ifdef HAVE_STRING_H
# include <string.h>
#endif
#include "src/class/pmix_pointer_array.h"
#include "src/mca/base/pmix_mca_base_framework.h"
#include "src/mca/mca.h"
#include "src/include/pmix_globals.h"
#include "src/include/pmix_stdatomic.h"
#include "src/mca/ptl/base/ptl_base_handshake.h"
#include "src/mca/ptl/ptl.h"
BEGIN_C_DECLS
/*
* MCA Framework
*/
PMIX_EXPORT extern pmix_mca_base_framework_t pmix_ptl_base_framework;
/**
* PTL select function
*
* Cycle across available components and construct the list
* of active modules
*/
PMIX_EXPORT pmix_status_t pmix_ptl_base_select(void);
/* framework globals */
struct pmix_ptl_base_t {
bool initialized;
bool selected;
pmix_list_t posted_recvs; // list of pmix_ptl_posted_recv_t
pmix_list_t unexpected_msgs;
pmix_listener_t listener;
struct sockaddr_storage *connection;
uint32_t current_tag;
size_t max_msg_size;
char *session_tmpdir;
char *system_tmpdir;
char *report_uri;
char *uri;
char *urifile;
char *sysctrlr_filename;
char *scheduler_filename;
char *system_filename;
char *session_filename;
char *nspace_filename;
char *pid_filename;
char *rendezvous_filename;
bool created_rendezvous_file;
bool created_session_tmpdir;
bool created_system_tmpdir;
bool created_sysctrlr_filename;
bool created_scheduler_filename;
bool created_system_filename;
bool created_session_filename;
bool created_nspace_filename;
bool created_pid_filename;
bool created_urifile;
bool remote_connections;
bool system_tool;
bool session_tool;
bool tool_support;
char *if_include;
char *if_exclude;
int ipv4_port;
bool disable_ipv4_family;
int ipv6_port;
bool disable_ipv6_family;
int max_retries;
int wait_to_connect;
int handshake_wait_time;
int handshake_max_retries;
};
typedef struct pmix_ptl_base_t pmix_ptl_base_t;
PMIX_EXPORT extern pmix_ptl_base_t pmix_ptl_base;
typedef struct {
pmix_list_item_t super;
int sd;
char *nspace;
pmix_rank_t rank;
char *uri;
char *version;
} pmix_connection_t;
PMIX_CLASS_DECLARATION(pmix_connection_t);
/* API stubs */
PMIX_EXPORT pmix_status_t pmix_ptl_base_set_notification_cbfunc(pmix_ptl_cbfunc_t cbfunc);
PMIX_EXPORT pmix_status_t pmix_ptl_base_connect_to_peer(struct pmix_peer_t *peer,
pmix_info_t info[], size_t ninfo,
char **suri);
PMIX_EXPORT pmix_status_t pmix_ptl_base_parse_uri_file(char *filename,
bool optional,
pmix_list_t *connections);
PMIX_EXPORT pmix_status_t pmix_ptl_base_setup_connection(char *uri,
struct sockaddr_storage *connection,
size_t *len);
PMIX_EXPORT void pmix_ptl_base_post_recv(int fd, short args, void *cbdata);
PMIX_EXPORT void pmix_ptl_base_cancel_recv(int sd, short args, void *cbdata);
PMIX_EXPORT pmix_status_t pmix_ptl_base_start_listening(pmix_info_t info[], size_t ninfo);
PMIX_EXPORT void pmix_ptl_base_stop_listening(void);
PMIX_EXPORT pmix_status_t pmix_base_write_rndz_file(char *filename, char *uri, bool *created);
/* base support functions */
PMIX_EXPORT pmix_status_t pmix_ptl_base_check_server_uris(pmix_peer_t *peer, char **evar);
PMIX_EXPORT pmix_status_t pmix_ptl_base_check_directives(pmix_info_t *info, size_t ninfo);
PMIX_EXPORT pmix_status_t pmix_ptl_base_setup_fork(const pmix_proc_t *proc, char ***env);
PMIX_EXPORT void pmix_ptl_base_send_handler(int sd, short flags, void *cbdata);
PMIX_EXPORT void pmix_ptl_base_recv_handler(int sd, short flags, void *cbdata);
PMIX_EXPORT void pmix_ptl_base_process_msg(int fd, short flags, void *cbdata);
PMIX_EXPORT pmix_status_t pmix_ptl_base_set_nonblocking(int sd);
PMIX_EXPORT pmix_status_t pmix_ptl_base_set_blocking(int sd);
PMIX_EXPORT pmix_status_t pmix_ptl_base_send_blocking(int sd, char *ptr, size_t size);
PMIX_EXPORT pmix_status_t pmix_ptl_base_recv_blocking(int sd, char *data, size_t size);
PMIX_EXPORT pmix_status_t pmix_ptl_base_connect(struct sockaddr_storage *addr, pmix_socklen_t len,
int *fd);
PMIX_EXPORT void pmix_ptl_base_connection_handler(int sd, short args, void *cbdata);
PMIX_EXPORT pmix_status_t pmix_ptl_base_setup_listener(pmix_info_t info[], size_t ninfo);
PMIX_EXPORT pmix_status_t pmix_ptl_base_send_connect_ack(int sd);
PMIX_EXPORT pmix_status_t pmix_ptl_base_recv_connect_ack(int sd);
PMIX_EXPORT void pmix_ptl_base_lost_connection(pmix_peer_t *peer, pmix_status_t err);
PMIX_EXPORT bool pmix_ptl_base_peer_is_earlier(pmix_peer_t *peer, uint8_t major, uint8_t minor,
uint8_t release);
PMIX_EXPORT void pmix_ptl_base_query_servers(int sd, short args, void *cbdata);
PMIX_EXPORT pmix_status_t pmix_ptl_base_parse_uri(const char *evar, char **nspace,
pmix_rank_t *rank, char **suri);
PMIX_EXPORT pmix_status_t pmix_ptl_base_df_search(char *dirname, char *prefix, pmix_info_t info[],
size_t ninfo, bool optional, pmix_list_t *connections);
PMIX_EXPORT pmix_rnd_flag_t pmix_ptl_base_set_flag(size_t *sz);
PMIX_EXPORT pmix_status_t pmix_ptl_base_make_connection(pmix_peer_t *peer, char *suri,
pmix_info_t *iptr, size_t niptr);
PMIX_EXPORT void pmix_ptl_base_complete_connection(pmix_peer_t *peer, char *nspace,
pmix_rank_t rank);
PMIX_EXPORT pmix_status_t pmix_ptl_base_set_timeout(pmix_peer_t *peer, struct timeval *save,
pmix_socklen_t *sz, bool *sockopt);
PMIX_EXPORT void pmix_ptl_base_setup_socket(pmix_peer_t *peer);
PMIX_EXPORT pmix_status_t pmix_ptl_base_client_handshake(pmix_peer_t *peer, pmix_status_t reply);
PMIX_EXPORT pmix_status_t pmix_ptl_base_tool_handshake(pmix_peer_t *peer, pmix_status_t rp);
PMIX_EXPORT char **pmix_ptl_base_split_and_resolve(const char *orig_str,
const char *name);
PMIX_EXPORT pmix_status_t pmix_ptl_base_set_peer(pmix_peer_t *peer, char *evar);
PMIX_EXPORT char *pmix_ptl_base_get_cmd_line(void);
END_C_DECLS
#endif

View File

@@ -0,0 +1,215 @@
/* -*- C -*-
*
* Copyright (c) 2020 Intel, Inc. All rights reserved.
* Copyright (c) 2021 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*
*/
#ifndef PMIX_PTL_BASE_HANDSHAKE_H_
#define PMIX_PTL_BASE_HANDSHAKE_H_
#include "src/include/pmix_config.h"
#ifdef HAVE_STRING_H
# include <string.h>
#endif
/* The following macros are for use in the PTL connection
* handler. For simplicity, they include variables that are
* defined in the functions where they are used - thus, these
* macros are NOT portable for use elsewhere
*
* A symmetric pair of macros are provided specifically to
* make it easier to read and compare the two ends of the
* handshake */
BEGIN_C_DECLS
/* define flag values that indicate the type of process attempting
* to connect to a server:
* 0 => simple client process
* 1 => legacy tool - may or may not have an identifier
* 2 => legacy launcher - may or may not have an identifier
* ------------------------------------------
* 3 => self-started tool process that needs an identifier
* 4 => self-started tool process that was given an identifier by caller
* 5 => tool that was started by a PMIx server - identifier specified by server
* 6 => self-started launcher that needs an identifier
* 7 => self-started launcher that was given an identifier by caller
* 8 => launcher that was started by a PMIx server - identifier specified by server
* 9 => singleton client - treated like a tool that has an identifier
* ------------------------------------------
* 10 => scheduler
*/
typedef uint8_t pmix_rnd_flag_t;
#define PMIX_SIMPLE_CLIENT 0
#define PMIX_LEGACY_TOOL 1
#define PMIX_LEGACY_LAUNCHER 2
#define PMIX_TOOL_NEEDS_ID 3
#define PMIX_TOOL_GIVEN_ID 4
#define PMIX_TOOL_CLIENT 5
#define PMIX_LAUNCHER_NEEDS_ID 6
#define PMIX_LAUNCHER_GIVEN_ID 7
#define PMIX_LAUNCHER_CLIENT 8
#define PMIX_SINGLETON_CLIENT 9
#define PMIX_SCHEDULER_WITH_ID 10
/* The following macros are used in the ptl_base_connection_hdlr.c
* file to parse the handshake message and extract its fields */
#define PMIX_PTL_GET_STRING(n) \
do { \
size_t _l; \
PMIX_STRNLEN(_l, mg, cnt); \
if (_l < cnt) { \
(n) = strdup(mg); \
mg += strlen((n)) + 1; \
cnt -= strlen((n)) + 1; \
} else { \
PMIX_ERROR_LOG(PMIX_ERR_BAD_PARAM); \
goto error; \
} \
} while (0)
/* numerical value must be converted back to host
* order, so we use an intermediate storage place
* for that purpose */
#define PMIX_PTL_GET_U32_NOERROR(r, n) \
do { \
uint32_t _u; \
if (sizeof(uint32_t) <= cnt) { \
memcpy(&_u, mg, sizeof(uint32_t)); \
(n) = ntohl(_u); \
mg += sizeof(uint32_t); \
cnt -= sizeof(uint32_t); \
(r) = PMIX_SUCCESS; \
} else { \
(r) = PMIX_ERR_BAD_PARAM; \
} \
} while (0)
#define PMIX_PTL_GET_U32(n) \
do { \
uint32_t _u; \
if (sizeof(uint32_t) <= cnt) { \
memcpy(&_u, mg, sizeof(uint32_t)); \
(n) = ntohl(_u); \
mg += sizeof(uint32_t); \
cnt -= sizeof(uint32_t); \
} else { \
PMIX_ERROR_LOG(PMIX_ERR_BAD_PARAM); \
goto error; \
} \
} while (0)
#define PMIX_PTL_GET_BLOB(b, l) \
do { \
if (0 < (l)) { \
(b) = (char *) malloc((l)); \
if (NULL == (b)) { \
PMIX_ERROR_LOG(PMIX_ERR_NOMEM); \
goto error; \
} \
memcpy((b), mg, (l)); \
mg += (l); \
cnt -= (l); \
} \
} while (0)
#define PMIX_PTL_GET_U8(n) \
do { \
if (sizeof(uint8_t) <= cnt) { \
memcpy(&(n), mg, sizeof(uint8_t)); \
mg += sizeof(uint8_t); \
cnt -= sizeof(uint8_t); \
} else { \
PMIX_ERROR_LOG(PMIX_ERR_BAD_PARAM); \
goto error; \
} \
} while (0)
#define PMIX_PTL_GET_PROCID(p) \
do { \
char *n; \
uint32_t _r; \
pmix_status_t _rc; \
PMIX_PTL_GET_STRING(n); \
PMIX_PTL_GET_U32_NOERROR(_rc, _r); \
if (PMIX_SUCCESS != _rc) { \
PMIX_ERROR_LOG(_rc); \
free(n); \
goto error; \
} \
PMIX_LOAD_PROCID(&(p), n, _r); \
free(n); \
} while (0)
/* The following macros are for use in the ptl_base_fns.c
* when constructing the handshake message. */
#define PMIX_PTL_PUT_STRING(n) \
do { \
memcpy(msg + csize, (n), strlen((n))); \
csize += strlen((n)) + 1; \
} while (0)
/* numerical value must be converted to network byte
* order, so we use an intermediate storage place
* for that purpose */
#define PMIX_PTL_PUT_U32(n) \
do { \
uint32_t _u; \
_u = htonl((uint32_t)(n)); \
memcpy(msg + csize, &_u, sizeof(uint32_t)); \
csize += sizeof(uint32_t); \
} while (0)
#define PMIX_PTL_PUT_BLOB(b, l) \
do { \
if (0 < (l)) { \
memcpy(msg + csize, (b), (l)); \
csize += (l); \
} \
} while (0)
#define PMIX_PTL_PUT_U8(n) \
do { \
memcpy(msg + csize, &(n), sizeof(uint8_t)); \
csize += sizeof(uint8_t); \
} while (0)
#define PMIX_PTL_PUT_PROCID(p) \
do { \
PMIX_PTL_PUT_STRING((p).nspace); \
PMIX_PTL_PUT_U32((p).rank); \
} while (0)
/* the following macros are for use in the ptl_base_fns.c
* when sending/recving values during the handshake */
#define PMIX_PTL_RECV_NSPACE(s, n) \
do { \
pmix_status_t r; \
r = pmix_ptl_base_recv_blocking((s), (char *) (n), PMIX_MAX_NSLEN + 1); \
(n)[PMIX_MAX_NSLEN] = '\0'; /* ensure NULL termination */ \
if (PMIX_SUCCESS != r) { \
return r; \
} \
} while (0)
#define PMIX_PTL_RECV_U32(s, n) \
do { \
pmix_status_t r; \
uint32_t _u; \
r = pmix_ptl_base_recv_blocking((s), (char *) &_u, sizeof(uint32_t)); \
if (PMIX_SUCCESS != r) { \
return r; \
} \
(n) = htonl(_u); \
} while (0)
END_C_DECLS
#endif

View File

@@ -0,0 +1,222 @@
/* -*- Mode: C; c-basic-offset:4 ; -*- */
/*
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2005 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2012 Los Alamos National Security, Inc. All rights reserved.
* Copyright (c) 2013-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2015 Research Organization for Information Science
* and Technology (RIST). All rights reserved.
* Copyright (c) 2016 Mellanox Technologies, Inc.
* All rights reserved.
* Copyright (c) 2021-2024 Nanook Consulting All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
/**
* @file
*
* Data packing subsystem.
*/
#ifndef PMIX_PTL_H_
#define PMIX_PTL_H_
#include "src/include/pmix_config.h"
#include "src/include/pmix_types.h"
#include "src/mca/base/pmix_mca_base_framework.h"
#include "src/mca/base/pmix_mca_base_var.h"
#include "src/mca/bfrops/bfrops_types.h"
#include "src/mca/mca.h"
#include "ptl_types.h"
BEGIN_C_DECLS
/* forward declaration */
struct pmix_peer_t;
/* The overall objective of this framework is to provide transport
* options by which a server can communicate with a client:
*
* (a) across different versions of the library - e.g., when the
* connection handshake changes.
*
* (b) using different transports as necessitated by different
* environments.
*
* This is a single-select framework - i.e., only one component
* is selected and "active" at a time. The intent is
* to have one component for each use-case, with the
* expectation that the community will do its best not to revise
* communications in manners that expand components to support (a).
* Thus, new variations should be rare, and only a few components
* will exist.
*/
/**** MODULE INTERFACE DEFINITION ****/
/* initialize the active plugin */
typedef pmix_status_t (*pmix_ptl_init_fn_t)(void);
/* finalize the active plugin */
typedef void (*pmix_ptl_finalize_fn_t)(void);
/* (ONE-WAY) register a persistent recv */
typedef pmix_status_t (*pmix_ptl_recv_fn_t)(struct pmix_peer_t *peer, pmix_ptl_cbfunc_t cbfunc,
pmix_ptl_tag_t tag);
/* Cancel a persistent recv */
typedef pmix_status_t (*pmix_ptl_cancel_fn_t)(struct pmix_peer_t *peer, pmix_ptl_tag_t tag);
/* connect to a peer - this is a blocking function
* to establish a connection to a peer*/
typedef pmix_status_t (*pmix_ptl_connect_to_peer_fn_t)(struct pmix_peer_t *peer,
pmix_info_t info[],
size_t ninfo,
char **suri);
/* query available servers on the local node */
typedef void (*pmix_ptl_query_servers_fn_t)(char *dirname, pmix_list_t *servers);
/* define an API for establishing a
* communication rendezvous point for local procs. The active component
* is given an opportunity to register a listener with the
* PTL base */
typedef pmix_status_t (*pmix_ptl_setup_listener_fn_t)(pmix_info_t info[], size_t ninfo);
/* define an API for obtaining any envars that are to
* be passed to client procs upon fork */
typedef pmix_status_t (*pmix_ptl_setup_fork_fn_t)(const pmix_proc_t *proc, char ***env);
/**
* Base structure for a PTL module
*/
struct pmix_ptl_module_t {
char *name;
pmix_ptl_init_fn_t init;
pmix_ptl_finalize_fn_t finalize;
pmix_ptl_recv_fn_t recv;
pmix_ptl_cancel_fn_t cancel;
pmix_ptl_connect_to_peer_fn_t connect_to_peer;
pmix_ptl_query_servers_fn_t query_servers;
pmix_ptl_setup_listener_fn_t setup_listener;
pmix_ptl_setup_fork_fn_t setup_fork;
};
typedef struct pmix_ptl_module_t pmix_ptl_module_t;
/***** MACROS FOR EXECUTING PTL FUNCTIONS *****/
/* (TWO-WAY) send a message to the peer, and get a response delivered
* to the specified callback function. The buffer will be free'd
* at the completion of the send, and the cbfunc will be called
* when the corresponding reply is received */
#define PMIX_PTL_SEND_RECV(r, p, b, c, d) \
do { \
pmix_ptl_sr_t *ms; \
pmix_peer_t *pr = (pmix_peer_t *) (p); \
if ((p)->finalized) { \
(r) = PMIX_ERR_UNREACH; \
} else { \
ms = PMIX_NEW(pmix_ptl_sr_t); \
PMIX_RETAIN(pr); \
ms->peer = pr; \
ms->bfr = (b); \
ms->cbfunc = (c); \
ms->cbdata = (d); \
PMIX_THREADSHIFT(ms, pmix_ptl_base_send_recv); \
(r) = PMIX_SUCCESS; \
} \
} while (0)
/* (ONE-WAY) send a message to the peer. The buffer will be free'd
* at the completion of the send */
#define PMIX_PTL_SEND_ONEWAY(r, p, b, t) \
do { \
pmix_ptl_queue_t *q; \
pmix_peer_t *pr = (pmix_peer_t *) (p); \
if ((p)->finalized) { \
(r) = PMIX_ERR_UNREACH; \
} else { \
q = PMIX_NEW(pmix_ptl_queue_t); \
PMIX_RETAIN(pr); \
q->peer = pr; \
q->buf = (b); \
q->tag = (t); \
PMIX_THREADSHIFT(q, pmix_ptl_base_send); \
(r) = PMIX_SUCCESS; \
} \
} while (0)
#define PMIX_PTL_RECV(r, c, t) \
do { \
pmix_ptl_posted_recv_t *req; \
req = PMIX_NEW(pmix_ptl_posted_recv_t); \
if (NULL == req) { \
(r) = PMIX_ERR_NOMEM; \
} else { \
req->tag = (t); \
req->cbfunc = (c); \
pmix_event_assign(&(req->ev), pmix_globals.evbase, -1, EV_WRITE, \
pmix_ptl_base_post_recv, req); \
pmix_event_active(&(req->ev), EV_WRITE, 1); \
(r) = PMIX_SUCCESS; \
} \
} while (0)
#define PMIX_PTL_CANCEL(r, t) \
do { \
pmix_ptl_posted_recv_t *req; \
req = PMIX_NEW(pmix_ptl_posted_recv_t); \
if (NULL == req) { \
(r) = PMIX_ERR_NOMEM; \
} else { \
req->tag = (t); \
pmix_event_assign(&(req->ev), pmix_globals.evbase, -1, EV_WRITE, \
pmix_ptl_base_cancel_recv, req); \
pmix_event_active(&(req->ev), EV_WRITE, 1); \
(r) = PMIX_SUCCESS; \
} \
} while (0)
/* expose functions used by the macros */
PMIX_EXPORT extern void pmix_ptl_base_send(int sd, short args, void *cbdata);
PMIX_EXPORT extern void pmix_ptl_base_send_recv(int sd, short args, void *cbdata);
PMIX_EXPORT extern void pmix_ptl_base_register_recv(int sd, short args, void *cbdata);
PMIX_EXPORT extern void pmix_ptl_base_cancel_recv(int sd, short args, void *cbdata);
/**** COMPONENT STRUCTURE DEFINITION ****/
/*
* the standard component data structure
*/
struct pmix_ptl_base_component_t {
pmix_mca_base_component_t base;
int priority;
char *uri;
};
typedef struct pmix_ptl_base_component_t pmix_ptl_base_component_t;
/* export the PTL module struct */
PMIX_EXPORT extern pmix_ptl_module_t pmix_ptl;
/*
* Macro for use in components that are of type ptl
*/
#define PMIX_PTL_BASE_VERSION_2_0_0 PMIX_MCA_BASE_VERSION_1_0_0("ptl", 2, 0, 0)
END_C_DECLS
#endif /* PMIX_PTL_H */

View File

@@ -0,0 +1,435 @@
/* -*- C -*-
*
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2006 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2007-2011 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2012-2013 Los Alamos National Security, Inc. All rights reserved.
* Copyright (c) 2014-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2021-2023 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
/**
* @file
*
* Buffer management types.
*/
#ifndef PMIX_PTL_TYPES_H_
#define PMIX_PTL_TYPES_H_
#include "src/include/pmix_config.h"
#include "src/include/pmix_types.h"
#ifdef HAVE_UNISTD_H
# include <unistd.h>
#endif
#ifdef HAVE_SYS_SOCKET_H
# include <sys/socket.h>
#endif
#ifdef HAVE_SYS_UN_H
# include <sys/un.h>
#endif
#ifdef HAVE_SYS_UIO_H
# include <sys/uio.h>
#endif
#ifdef HAVE_NET_UIO_H
# include <net/uio.h>
#endif
#ifdef HAVE_SYS_TYPES_H
# include <sys/types.h>
#endif
#include <event.h>
#include "src/class/pmix_list.h"
#include "src/include/pmix_stdatomic.h"
#include "src/mca/bfrops/bfrops_types.h"
#include "src/mca/ptl/base/ptl_base_handshake.h"
#include "src/util/pmix_output.h"
BEGIN_C_DECLS
// forward declaration
struct pmix_peer_t;
struct pmix_ptl_module_t;
/* define a process type */
typedef struct {
uint32_t type;
uint8_t major;
uint8_t minor;
uint8_t release;
uint8_t flag; // see pmix_ptl_base_set_flag for definition of values
} pmix_proc_type_t;
#define PMIX_MAJOR_WILDCARD 255
#define PMIX_MINOR_WILDCARD 255
#define PMIX_RELEASE_WILDCARD 255
/* use 255 as WILDCARD for the release triplet values */
#define PMIX_PROC_TYPE_STATIC_INIT \
{ \
.type = PMIX_PROC_UNDEF, \
.major = PMIX_MAJOR_WILDCARD, \
.minor = PMIX_MINOR_WILDCARD, \
.release = PMIX_RELEASE_WILDCARD, \
.flag = 0 \
}
/* Define process types - we use a bit-mask as procs can
* span multiple types */
#define PMIX_PROC_UNDEF 0x00000000
#define PMIX_PROC_CLIENT 0x00000001 // simple client process
#define PMIX_PROC_SERVER 0x00000002 // simple server process
#define PMIX_PROC_TOOL 0x00000004 // simple tool
#define PMIX_PROC_SINGLETON_ACT 0x00000008 // self-started client process
#define PMIX_PROC_SINGLETON (PMIX_PROC_CLIENT | PMIX_PROC_SINGLETON_ACT)
#define PMIX_PROC_LAUNCHER_ACT 0x10000000 // process acting as launcher
#define PMIX_PROC_LAUNCHER (PMIX_PROC_TOOL | PMIX_PROC_SERVER | PMIX_PROC_LAUNCHER_ACT)
#define PMIX_PROC_CLIENT_LAUNCHER (PMIX_PROC_LAUNCHER | PMIX_PROC_CLIENT)
#define PMIX_PROC_CLIENT_TOOL_ACT 0x20000000
#define PMIX_PROC_CLIENT_TOOL (PMIX_PROC_TOOL | PMIX_PROC_CLIENT | PMIX_PROC_CLIENT_TOOL_ACT)
#define PMIX_PROC_GATEWAY_ACT 0x40000000
#define PMIX_PROC_GATEWAY (PMIX_PROC_SERVER | PMIX_PROC_GATEWAY_ACT)
#define PMIX_PROC_SCHEDULER_ACT 0x80000000
#define PMIX_PROC_SCHEDULER (PMIX_PROC_SERVER | PMIX_PROC_SCHEDULER_ACT)
#define PMIX_PROC_SYS_CTRLR_ACT 0x01000000
#define PMIX_PROC_SYS_CTRLR (PMIX_PROC_SERVER | PMIX_PROC_SYS_CTRLR_ACT)
#define PMIX_SET_PEER_TYPE(a, b) (a)->proc_type.type |= (b)
#define PMIX_SET_PROC_TYPE(a, b) (a)->type |= (b)
/* define some convenience macros for testing proc type */
#define PMIX_PEER_IS_CLIENT(p) (PMIX_PROC_CLIENT & (p)->proc_type.type)
#define PMIX_PEER_IS_SINGLETON(p) (PMIX_PROC_SINGLETON_ACT & (p)->proc_type.type)
#define PMIX_PEER_IS_SERVER(p) (PMIX_PROC_SERVER & (p)->proc_type.type)
#define PMIX_PEER_IS_TOOL(p) (PMIX_PROC_TOOL & (p)->proc_type.type)
#define PMIX_PEER_IS_LAUNCHER(p) (PMIX_PROC_LAUNCHER_ACT & (p)->proc_type.type)
#define PMIX_PEER_IS_CLIENT_LAUNCHER(p) \
((PMIX_PROC_LAUNCHER_ACT & (p)->proc_type.type) && (PMIX_PROC_CLIENT & (p)->proc_type.type))
#define PMIX_PEER_IS_CLIENT_TOOL(p) \
((PMIX_PROC_CLIENT_TOOL_ACT & (p)->proc_type.type) && (PMIX_PROC_CLIENT & (p)->proc_type.type))
#define PMIX_PEER_IS_GATEWAY(p) (PMIX_PROC_GATEWAY_ACT & (p)->proc_type.type)
#define PMIX_PEER_IS_SCHEDULER(p) (PMIX_PROC_SCHEDULER_ACT & (p)->proc_type.type)
#define PMIX_PEER_IS_SYS_CTRLR(p) (PMIX_PROC_SYS_CTRLR_ACT & (p)->proc_type.type)
#define PMIX_PROC_IS_CLIENT(p) (PMIX_PROC_CLIENT & (p)->type)
#define PMIX_PROC_IS_SERVER(p) (PMIX_PROC_SERVER & (p)->type)
#define PMIX_PROC_IS_TOOL(p) (PMIX_PROC_TOOL & (p)->type)
#define PMIX_PROC_IS_LAUNCHER(p) (PMIX_PROC_LAUNCHER_ACT & (p)->type)
#define PMIX_PROC_IS_CLIENT_LAUNCHER(p) \
((PMIX_PROC_LAUNCHER_ACT & (p)->type) && (PMIX_PROC_CLIENT & (p)->type))
#define PMIX_PROC_IS_CLIENT_TOOL(p) \
((PMIX_PROC_CLIENT_TOOL_ACT & (p)->type) && (PMIX_PROC_CLIENT & (p)->type))
#define PMIX_PROC_IS_GATEWAY(p) (PMIX_PROC_GATEWAY_ACT & (p)->type)
#define PMIX_PROC_IS_SCHEDULER(p) (PMIX_PROC_SCHEDULER_ACT & (p)->type)
#define PMIX_PROC_IS_SYS_CTRLR(p) (PMIX_PROC_SYS_CTRLR_ACT & (p)->type)
/* provide macros for setting the major, minor, and release values
* just so people don't have to deal with the details of the struct */
#define PMIX_SET_PEER_VERSION(p, e, a, b) \
do { \
char *e2; \
unsigned long mj, mn, rl; \
if (NULL != e) { \
if ('v' == e[0]) { \
mj = strtoul(&e[1], &e2, 10); \
} else { \
mj = strtoul(e, &e2, 10); \
} \
++e2; \
mn = strtoul(e2, &e2, 10); \
++e2; \
rl = strtoul(e2, NULL, 10); \
PMIX_SET_PEER_MAJOR((p), mj); \
PMIX_SET_PEER_MINOR((p), mn); \
PMIX_SET_PEER_RELEASE((p), rl); \
} else { \
PMIX_SET_PEER_MAJOR((p), (a)); \
PMIX_SET_PEER_MINOR((p), (b)); \
} \
} while (0)
#define PMIX_SET_PEER_MAJOR(p, a) (p)->proc_type.major = (a)
#define PMIX_SET_PEER_MINOR(p, a) (p)->proc_type.minor = (a)
#define PMIX_SET_PEER_RELEASE(p, a) (p)->proc_type.release = (a)
#define PMIX_SET_PROC_MAJOR(p, a) (p)->major = (a)
#define PMIX_SET_PROC_MINOR(p, a) (p)->minor = (a)
#define PMIX_SET_PROC_RELEASE(p, a) (p)->release = (a)
/* define some convenience macros for testing version */
#define PMIX_PEER_MAJOR_VERSION(p) (p)->proc_type.major
#define PMIX_PEER_MINOR_VERSION(p) (p)->proc_type.minor
#define PMIX_PEER_REL_VERSION(p) (p)->proc_type.release
#define PMIX_PROC_MAJOR_VERSION(p) (p)->major
#define PMIX_PROC_MINOR_VERSION(p) (p)->minor
#define PMIX_PROC_REL_VERSION(p) (p)->release
#define PMIX_PEER_IS_V1(p) ((p)->proc_type.major == 1)
#define PMIX_PEER_IS_V20(p) ((p)->proc_type.major == 2 && (p)->proc_type.minor == 0)
#define PMIX_PEER_IS_V21(p) ((p)->proc_type.major == 2 && (p)->proc_type.minor == 1)
#define PMIX_PEER_IS_V3(p) ((p)->proc_type.major == 3)
#define PMIX_PEER_IS_V40(p) ((p)->proc_type.major == 4 && (p)->proc_type.minor == 0)
#define PMIX_PEER_IS_V41(p) ((p)->proc_type.major == 4 && (p)->proc_type.minor == 1)
#define PMIX_PEER_TRIPLET(p, a, b, c) \
((PMIX_PEER_MAJOR_VERSION(p) == PMIX_MAJOR_WILDCARD || (a) == PMIX_MAJOR_WILDCARD \
|| PMIX_PEER_MAJOR_VERSION(p) == (a)) \
&& (PMIX_PEER_MINOR_VERSION(p) == PMIX_MINOR_WILDCARD || (b) == PMIX_MINOR_WILDCARD \
|| PMIX_PEER_MINOR_VERSION(p) == (b)) \
&& (PMIX_PEER_REL_VERSION(p) == PMIX_RELEASE_WILDCARD || (c) == PMIX_RELEASE_WILDCARD \
|| PMIX_PEER_REL_VERSION(p) == (c)))
#define PMIX_PROC_TRIPLET(p, a, b, c) \
((PMIX_PROC_MAJOR_VERSION(p) == PMIX_MAJOR_WILDCARD || PMIX_PROC_MAJOR_VERSION(p) == (a)) \
&& (PMIX_PROC_MINOR_VERSION(p) == PMIX_MINOR_WILDCARD || PMIX_PROC_MINOR_VERSION(p) == (b)) \
&& (PMIX_PROC_REL_VERSION(p) == PMIX_RELEASE_WILDCARD || PMIX_PROC_REL_VERSION(p) == (c)))
#define PMIX_PEER_IS_EARLIER(p, a, b, c) pmix_ptl_base_peer_is_earlier(p, a, b, c)
/**** MESSAGING STRUCTURES ****/
typedef uint32_t pmix_ptl_tag_t;
/* define a range of "reserved" tags - these
* are tags that are used for persistent recvs
* within the system */
#define PMIX_PTL_TAG_NOTIFY 0
#define PMIX_PTL_TAG_HEARTBEAT 1
#define PMIX_PTL_TAG_IOF 2
/* define the start of dynamic tags that are
* assigned for send/recv operations */
#define PMIX_PTL_TAG_DYNAMIC 100
/* header for messages */
typedef struct {
int32_t pindex;
pmix_ptl_tag_t tag;
uint32_t nbytes;
#if SIZEOF_SIZE_T == 8
uint32_t padding;
#endif
} pmix_ptl_hdr_t;
/* define the messaging cbfunc */
typedef void (*pmix_ptl_cbfunc_t)(struct pmix_peer_t *peer, pmix_ptl_hdr_t *hdr, pmix_buffer_t *buf,
void *cbdata);
/* define a callback function for notifying that server connection
* has completed */
typedef void (*pmix_ptl_connect_cbfunc_t)(pmix_status_t status, void *cbdata);
/* define a callback function for processing pending connections */
typedef void (*pmix_ptl_pending_cbfunc_t)(int sd, short args, void *cbdata);
/* structure for sending a message */
typedef struct {
pmix_list_item_t super;
pmix_event_t ev;
pmix_ptl_hdr_t hdr;
pmix_buffer_t *data;
bool hdr_sent;
char *sdptr;
size_t sdbytes;
} pmix_ptl_send_t;
PMIX_CLASS_DECLARATION(pmix_ptl_send_t);
/* structure for recving a message */
typedef struct {
pmix_list_item_t super;
pmix_event_t ev;
struct pmix_peer_t *peer;
int sd;
pmix_ptl_hdr_t hdr;
char *data;
bool hdr_recvd;
char *rdptr;
size_t rdbytes;
} pmix_ptl_recv_t;
PMIX_CLASS_DECLARATION(pmix_ptl_recv_t);
/* structure for tracking posted recvs */
typedef struct {
pmix_list_item_t super;
pmix_event_t ev;
uint32_t tag;
pmix_ptl_cbfunc_t cbfunc;
void *cbdata;
} pmix_ptl_posted_recv_t;
PMIX_CLASS_DECLARATION(pmix_ptl_posted_recv_t);
/* struct for posting send/recv request */
typedef struct {
pmix_object_t super;
volatile bool active;
pmix_event_t ev;
struct pmix_peer_t *peer;
pmix_status_t status;
pmix_buffer_t *bfr;
pmix_ptl_cbfunc_t cbfunc;
void *cbdata;
} pmix_ptl_sr_t;
PMIX_CLASS_DECLARATION(pmix_ptl_sr_t);
typedef struct {
pmix_object_t super;
volatile bool active;
pmix_event_t ev;
struct pmix_peer_t *peer;
pmix_buffer_t *buf;
pmix_ptl_tag_t tag;
} pmix_ptl_queue_t;
PMIX_CLASS_DECLARATION(pmix_ptl_queue_t);
/* define listener protocol types */
typedef uint16_t pmix_listener_protocol_t;
#define PMIX_PROTOCOL_UNDEF 0
#define PMIX_PROTOCOL_V1 1 // legacy usock
#define PMIX_PROTOCOL_V2 2 // tcp
/* connection support */
typedef struct {
pmix_object_t super;
pmix_event_t ev;
pmix_listener_protocol_t protocol;
int sd;
bool need_id;
pmix_rnd_flag_t flag;
pmix_proc_t proc;
pmix_info_t *info;
size_t ninfo;
pmix_status_t status;
struct sockaddr_storage addr;
struct pmix_peer_t *peer;
char *version;
char *bfrops;
char *psec;
char *gds;
pmix_bfrop_buffer_type_t buffer_type;
char *cred;
size_t len;
uid_t uid;
gid_t gid;
pmix_proc_type_t proc_type;
} pmix_pending_connection_t;
PMIX_CLASS_DECLARATION(pmix_pending_connection_t);
/* listener objects */
typedef struct pmix_listener_t {
pmix_list_item_t super;
pmix_event_t ev;
pmix_atomic_bool_t active;
pmix_listener_protocol_t protocol;
int socket;
char *varname;
char *uri;
uint32_t owner;
bool owner_given;
uint32_t group;
bool group_given;
uint32_t mode;
pmix_ptl_pending_cbfunc_t cbfunc;
} pmix_listener_t;
PMIX_CLASS_DECLARATION(pmix_listener_t);
#define PMIX_LISTENER_STATIC_INIT \
{ \
.super = PMIX_LIST_ITEM_STATIC_INIT, \
.active = false, \
.protocol = PMIX_PROTOCOL_UNDEF, \
.socket = 0, \
.varname = NULL, \
.uri = NULL, \
.owner = 0, \
.owner_given = false, \
.group = 0, \
.mode = 0, \
.cbfunc = NULL \
}
/* provide a backdoor to the framework output for debugging */
PMIX_EXPORT extern int pmix_ptl_base_output;
#define PMIX_ACTIVATE_POST_MSG(ms) \
do { \
pmix_event_assign(&((ms)->ev), pmix_globals.evbase, -1, EV_WRITE, \
pmix_ptl_base_process_msg, (ms)); \
PMIX_POST_OBJECT(ms); \
pmix_event_active(&((ms)->ev), EV_WRITE, 1); \
} while (0)
#define PMIX_SND_CADDY(c, h, s) \
do { \
(c) = PMIX_NEW(pmix_server_caddy_t); \
(void) memcpy(&(c)->hdr, &(h), sizeof(pmix_ptl_hdr_t)); \
PMIX_RETAIN((s)); \
(c)->snd = (s); \
} while (0)
/* queue a message to be sent to one of our procs - must
* provide the following params:
* p - pmix_peer_t of target recipient
* t - tag to be sent to
* b - buffer to be sent
*/
#define PMIX_SERVER_QUEUE_REPLY(r, p, t, b) \
do { \
pmix_ptl_send_t *snd; \
uint32_t nbytes; \
pmix_output_verbose(5, pmix_ptl_base_output, \
"[%s:%d] queue callback called: reply to %s:%d on tag %d size %d", \
__FILE__, __LINE__, (p)->info->pname.nspace, (p)->info->pname.rank, \
(t), (int) (b)->bytes_used); \
if ((p)->finalized) { \
(r) = PMIX_ERR_UNREACH; \
} else { \
snd = PMIX_NEW(pmix_ptl_send_t); \
snd->hdr.pindex = htonl(pmix_globals.pindex); \
snd->hdr.tag = htonl(t); \
nbytes = (b)->bytes_used; \
snd->hdr.nbytes = htonl(nbytes); \
snd->data = (b); \
/* always start with the header */ \
snd->sdptr = (char *) &snd->hdr; \
snd->sdbytes = sizeof(pmix_ptl_hdr_t); \
/* if there is no message on-deck, put this one there */ \
if (NULL == (p)->send_msg) { \
(p)->send_msg = snd; \
} else { \
/* add it to the queue */ \
pmix_list_append(&(p)->send_queue, &snd->super); \
} \
/* ensure the send event is active */ \
if (!(p)->send_ev_active && 0 <= (p)->sd) { \
(p)->send_ev_active = true; \
PMIX_POST_OBJECT(snd); \
pmix_event_add(&(p)->send_event, 0); \
} \
(r) = PMIX_SUCCESS; \
} \
} while (0)
#define CLOSE_THE_SOCKET(s) \
do { \
if (0 <= (s)) { \
shutdown((s), 2); \
close((s)); \
(s) = -1; \
} \
} while (0)
END_C_DECLS
#endif /* PMIX_PTL_TYPES_H */

View File

@@ -0,0 +1,45 @@
/*
* Copyright (c) 2004-2007 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2007 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2008 Sun Microsystems, Inc. All rights reserved.
* Copyright (c) 2010-2012 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2014-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2021-2023 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
/** @file **/
#ifndef PMIX_INIT_UTIL_H
#define PMIX_INIT_UTIL_H
#include "src/include/pmix_config.h"
#include "pmix_common.h"
BEGIN_C_DECLS
PMIX_EXPORT extern const char* pmix_tool_basename;
PMIX_EXPORT extern const char* pmix_tool_version;
PMIX_EXPORT extern const char* pmix_tool_org;
PMIX_EXPORT extern const char* pmix_tool_msg;
PMIX_EXPORT int pmix_init_util(pmix_info_t info[], size_t ninfo, char *helpdir);
PMIX_EXPORT int pmix_finalize_util(void);
PMIX_EXPORT void pmix_expose_param(char *param);
END_C_DECLS
#endif /* PMIX_INIT_UTIL_H */

View File

@@ -0,0 +1,87 @@
/*
* Copyright (c) 2014-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2015 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2021-2022 Nanook Consulting All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
#ifndef PMIX_PROGRESS_THREADS_H
#define PMIX_PROGRESS_THREADS_H
#include "pmix_config.h"
#include <pthread.h>
#include <event.h>
#include "src/include/pmix_types.h"
/**
* Initialize a progress thread name; if a progress thread is not
* already associated with that name, start a progress thread.
*
* If you have general events that need to run in *a* progress thread
* (but not necessarily a your own, dedicated progress thread), pass
* NULL the "name" argument to the pmix_progress_thead_init() function
* to glom on to the general PMIX-wide progress thread.
*
* If a name is passed that was already used in a prior call to
* pmix_progress_thread_init(), the event base associated with that
* already-running progress thread will be returned (i.e., no new
* progress thread will be started).
*/
PMIX_EXPORT pmix_event_base_t *pmix_progress_thread_init(const char *name);
PMIX_EXPORT pmix_status_t pmix_progress_thread_start(const char *name);
/**
* Stop a progress thread name (reference counted).
*
* Once this function is invoked as many times as
* pmix_progress_thread_init() was invoked on this name (or NULL), the
* progress function is shut down.
* it is destroyed.
*
* Will return PMIX_ERR_NOT_FOUND if the progress thread name does not
* exist; PMIX_SUCCESS otherwise.
*/
PMIX_EXPORT pmix_status_t pmix_progress_thread_stop(const char *name);
/**
* Finalize a progress thread name (reference counted).
*
* Once this function is invoked after pmix_progress_thread_stop() has been called
* as many times as pmix_progress_thread_init() was invoked on this name (or NULL),
* the event base associated with it is destroyed.
*
* Will return PMIX_ERR_NOT_FOUND if the progress thread name does not
* exist; PMIX_SUCCESS otherwise.
*/
PMIX_EXPORT pmix_status_t pmix_progress_thread_finalize(const char *name);
/**
* Temporarily pause the progress thread associated with this name.
*
* This function does not destroy the event base associated with this
* progress thread name, but it does stop processing all events on
* that event base until pmix_progress_thread_resume() is invoked on
* that name.
*
* Will return PMIX_ERR_NOT_FOUND if the progress thread name does not
* exist; PMIX_SUCCESS otherwise.
*/
PMIX_EXPORT pmix_status_t pmix_progress_thread_pause(const char *name);
/**
* Restart a previously-paused progress thread associated with this
* name.
*
* Will return PMIX_ERR_NOT_FOUND if the progress thread name does not
* exist; PMIX_SUCCESS otherwise.
*/
PMIX_EXPORT pmix_status_t pmix_progress_thread_resume(const char *name);
#endif

View File

@@ -0,0 +1,82 @@
/*
* Copyright (c) 2004-2007 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2007 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2008 Sun Microsystems, Inc. All rights reserved.
* Copyright (c) 2010-2022 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2014-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2021-2022 Nanook Consulting All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
/** @file **/
#ifndef PMIX_RTE_H
#define PMIX_RTE_H
#include "src/include/pmix_config.h"
#include "pmix_common.h"
#include "src/class/pmix_object.h"
#include <stdio.h>
#include <sys/types.h>
#include <unistd.h>
#include <event.h>
#include "src/include/pmix_globals.h"
#include "src/mca/ptl/ptl_types.h"
BEGIN_C_DECLS
#if PMIX_ENABLE_TIMING
PMIX_EXPORT extern char *pmix_timing_sync_file;
PMIX_EXPORT extern char *pmix_timing_output;
PMIX_EXPORT extern bool pmix_timing_overhead;
#endif
PMIX_EXPORT extern char *pmix_net_private_ipv4;
PMIX_EXPORT extern int pmix_event_caching_window;
PMIX_EXPORT extern bool pmix_suppress_missing_data_warning;
PMIX_EXPORT extern char *pmix_progress_thread_cpus;
PMIX_EXPORT extern bool pmix_bind_progress_thread_reqd;
PMIX_EXPORT extern int pmix_maxfd;
/** version string of pmix */
extern const char pmix_version_string[];
/**
* Initialize the PMIX layer, including the MCA system.
*
* @retval PMIX_SUCCESS Upon success.
* @retval PMIX_ERROR Upon failure.
*
*/
PMIX_EXPORT pmix_status_t pmix_rte_init(uint32_t type, pmix_info_t info[], size_t ninfo,
pmix_ptl_cbfunc_t cbfunc);
/**
* Finalize the PMIX layer, including the MCA system.
*
*/
PMIX_EXPORT void pmix_rte_finalize(void);
/**
* Internal function. Do not call.
*/
PMIX_EXPORT pmix_status_t pmix_register_params(void);
PMIX_EXPORT pmix_status_t pmix_deregister_params(void);
END_C_DECLS
#endif /* PMIX_RTE_H */

View File

@@ -0,0 +1,395 @@
/* -*- Mode: C; c-basic-offset:4 ; indent-tabs-mode:nil -*- */
/*
* Copyright (c) 2015-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2015 Artem Y. Polyakov <artpol84@gmail.com>.
* All rights reserved.
* Copyright (c) 2015 Mellanox Technologies, Inc.
* All rights reserved.
* Copyright (c) 2016-2020 IBM Corporation. All rights reserved.
* Copyright (c) 2016-2018 Research Organization for Information Science
* and Technology (RIST). All rights reserved.
* Copyright (c) 2021-2024 Nanook Consulting All rights reserved.
* $COPYRIGHT$
*/
#ifndef PMIX_SERVER_OPS_H
#define PMIX_SERVER_OPS_H
#include <unistd.h>
#ifdef HAVE_SYS_TYPES_H
# include <sys/types.h>
#endif
#include "src/include/pmix_config.h"
#include "pmix_common.h"
#include "pmix_server.h"
#include "src/class/pmix_hotel.h"
#include "src/include/pmix_globals.h"
#include "src/include/pmix_types.h"
#include "src/threads/pmix_threads.h"
#include "src/util/pmix_hash.h"
#define PMIX_IOF_HOTEL_SIZE 256
#define PMIX_IOF_MAX_STAY 300000000
typedef struct {
pmix_object_t super;
pmix_event_t ev;
pmix_server_trkr_t *trk;
} pmix_trkr_caddy_t;
PMIX_CLASS_DECLARATION(pmix_trkr_caddy_t);
typedef struct {
pmix_object_t super;
pmix_event_t ev;
pmix_lock_t lock;
pmix_peer_t *peer;
char *nspace;
pmix_status_t status;
pmix_status_t *codes;
size_t ncodes;
pmix_proc_t proc;
pmix_proc_t *procs;
size_t nprocs;
uid_t uid;
gid_t gid;
void *server_object;
int nlocalprocs;
pmix_info_t *info;
size_t ninfo;
bool copied;
char **keys;
pmix_app_t *apps;
size_t napps;
pmix_iof_channel_t channels;
pmix_iof_flags_t flags;
pmix_byte_object_t *bo;
size_t nbo;
/* timestamp receipt of the notification so we
* can evict the oldest one if we get overwhelmed */
time_t ts;
/* what room of the hotel they are in */
int room;
pmix_op_cbfunc_t opcbfunc;
pmix_dmodex_response_fn_t cbfunc;
pmix_setup_application_cbfunc_t setupcbfunc;
pmix_lookup_cbfunc_t lkcbfunc;
pmix_spawn_cbfunc_t spcbfunc;
void *cbdata;
} pmix_setup_caddy_t;
PMIX_CLASS_DECLARATION(pmix_setup_caddy_t);
/* define a callback function returning inventory */
typedef void (*pmix_inventory_cbfunc_t)(pmix_status_t status, pmix_list_t *inventory, void *cbdata);
/* define an object for rolling up the inventory*/
typedef struct {
pmix_object_t super;
pmix_lock_t lock;
pmix_event_t ev;
pmix_status_t status;
int requests;
int replies;
pmix_list_t payload; // list of pmix_kval_t containing the replies
pmix_info_t *info;
size_t ninfo;
pmix_inventory_cbfunc_t cbfunc;
pmix_info_cbfunc_t infocbfunc;
pmix_op_cbfunc_t opcbfunc;
void *cbdata;
} pmix_inventory_rollup_t;
PMIX_CLASS_DECLARATION(pmix_inventory_rollup_t);
typedef struct {
pmix_list_item_t super;
pmix_setup_caddy_t *cd;
} pmix_dmdx_remote_t;
PMIX_CLASS_DECLARATION(pmix_dmdx_remote_t);
typedef struct {
pmix_list_item_t super;
pmix_proc_t proc; // id of proc whose data is being requested
pmix_list_t loc_reqs; // list of pmix_dmdx_request_t elem is keeping track of
// all local ranks that are interested in this namespace-rank
pmix_info_t *info; // array of info structs for this request
size_t ninfo; // number of info structs
} pmix_dmdx_local_t;
PMIX_CLASS_DECLARATION(pmix_dmdx_local_t);
typedef struct {
pmix_list_item_t super;
pmix_event_t ev;
bool event_active;
pmix_dmdx_local_t *lcd;
char *key;
pmix_modex_cbfunc_t cbfunc; // cbfunc to be executed when data is available
void *cbdata;
} pmix_dmdx_request_t;
PMIX_CLASS_DECLARATION(pmix_dmdx_request_t);
/* event/error registration book keeping */
typedef struct {
pmix_list_item_t super;
pmix_peer_t *peer;
bool enviro_events;
pmix_proc_t *affected;
size_t naffected;
} pmix_peer_events_info_t;
PMIX_CLASS_DECLARATION(pmix_peer_events_info_t);
typedef struct {
pmix_list_item_t super;
pmix_list_t peers; // list of pmix_peer_events_info_t
int code;
} pmix_regevents_info_t;
PMIX_CLASS_DECLARATION(pmix_regevents_info_t);
typedef struct {
pmix_list_item_t super;
pmix_group_t *grp;
pmix_rank_t rank;
size_t idx;
} pmix_group_caddy_t;
PMIX_CLASS_DECLARATION(pmix_group_caddy_t);
typedef struct {
pmix_list_item_t super;
pmix_proc_t source;
pmix_iof_channel_t channel;
pmix_byte_object_t *bo;
pmix_info_t *info;
size_t ninfo;
} pmix_iof_cache_t;
PMIX_CLASS_DECLARATION(pmix_iof_cache_t);
typedef struct {
pmix_list_item_t super;
char *name;
pmix_proc_t *members;
size_t nmembers;
} pmix_pset_t;
PMIX_CLASS_DECLARATION(pmix_pset_t);
typedef struct {
pmix_list_t nspaces; // list of pmix_nspace_t for the nspaces we know about
pmix_pointer_array_t clients; // array of pmix_peer_t local clients
pmix_list_t collectives; // list of active pmix_server_trkr_t
pmix_list_t remote_pnd; // list of pmix_dmdx_remote_t awaiting arrival of data fror servicing
// remote req's
pmix_list_t local_reqs; // list of pmix_dmdx_local_t awaiting arrival of data from local neighbours
pmix_list_t gdata; // cache of data given to me for passing to all clients
char **genvars; // argv array of envars given to me for passing to all clients
pmix_list_t events; // list of pmix_regevents_info_t registered events
char **failedgrps; // group IDs that failed to construct
pmix_list_t iof; // IO to be forwarded to clients
pmix_list_t iof_residuals; // leftover bytes waiting for newline
pmix_list_t psets; // list of known psets and memberships
size_t max_iof_cache; // max number of IOF messages to cache
bool tool_connections_allowed;
char *tmpdir; // temporary directory for this server
char *system_tmpdir; // system tmpdir
bool fence_localonly_opt; // local-only fence optimization
// verbosity for server get operations
int get_output;
int get_verbose;
// verbosity for server connect operations
int connect_output;
int connect_verbose;
// verbosity for server fence operations
int fence_output;
int fence_verbose;
// verbosity for server pub operations
int pub_output;
int pub_verbose;
// verbosity for server spawn operations
int spawn_output;
int spawn_verbose;
// verbosity for server event operations
int event_output;
int event_verbose;
// verbosity for server iof operations
int iof_output;
int iof_verbose;
// verbosity for basic server functions
int base_output;
int base_verbose;
// verbosity for server group operations
int group_output;
int group_verbose;
} pmix_server_globals_t;
#define PMIX_GDS_CADDY(c, p, t) \
do { \
(c) = PMIX_NEW(pmix_server_caddy_t); \
(c)->hdr.tag = (t); \
PMIX_RETAIN((p)); \
(c)->peer = (p); \
} while (0)
#define PMIX_SETUP_COLLECTIVE(c, t) \
do { \
(c) = PMIX_NEW(pmix_trkr_caddy_t); \
(c)->trk = (t); \
} while (0)
#define PMIX_EXECUTE_COLLECTIVE(c, t, f) \
do { \
PMIX_SETUP_COLLECTIVE(c, t); \
pmix_event_assign(&((c)->ev), pmix_globals.evbase, -1, EV_WRITE, (f), (c)); \
pmix_event_active(&((c)->ev), EV_WRITE, 1); \
} while (0)
PMIX_EXPORT bool pmix_server_trk_update(pmix_server_trkr_t *trk);
PMIX_EXPORT void pmix_pending_nspace_requests(pmix_namespace_t *nptr);
PMIX_EXPORT pmix_status_t pmix_pending_resolve(pmix_namespace_t *nptr, pmix_rank_t rank,
pmix_status_t status, pmix_scope_t scope,
pmix_dmdx_local_t *lcd);
PMIX_EXPORT pmix_status_t pmix_server_abort(pmix_peer_t *peer, pmix_buffer_t *buf,
pmix_op_cbfunc_t cbfunc, void *cbdata);
PMIX_EXPORT pmix_status_t pmix_server_commit(pmix_peer_t *peer, pmix_buffer_t *buf);
PMIX_EXPORT pmix_status_t pmix_server_fence(pmix_server_caddy_t *cd, pmix_buffer_t *buf,
pmix_modex_cbfunc_t modexcbfunc,
pmix_op_cbfunc_t opcbfunc);
PMIX_EXPORT pmix_status_t pmix_server_get(pmix_buffer_t *buf, pmix_modex_cbfunc_t cbfunc,
void *cbdata);
PMIX_EXPORT pmix_status_t pmix_server_publish(pmix_peer_t *peer, pmix_buffer_t *buf,
pmix_op_cbfunc_t cbfunc, void *cbdata);
PMIX_EXPORT pmix_status_t pmix_server_lookup(pmix_peer_t *peer, pmix_buffer_t *buf,
pmix_lookup_cbfunc_t cbfunc, void *cbdata);
PMIX_EXPORT pmix_status_t pmix_server_unpublish(pmix_peer_t *peer, pmix_buffer_t *buf,
pmix_op_cbfunc_t cbfunc, void *cbdata);
PMIX_EXPORT pmix_status_t pmix_server_spawn(pmix_peer_t *peer, pmix_buffer_t *buf,
pmix_spawn_cbfunc_t cbfunc, void *cbdata);
PMIX_EXPORT void pmix_server_spawn_parser(pmix_peer_t *peer,
pmix_iof_channel_t *channels,
pmix_iof_flags_t *flags,
pmix_info_t *info,
size_t ninfo);
PMIX_EXPORT pmix_status_t pmix_server_process_iof(pmix_setup_caddy_t *cd,
char nspace[]);
PMIX_EXPORT void pmix_server_spcbfunc(pmix_status_t status, char nspace[], void *cbdata);
PMIX_EXPORT pmix_status_t pmix_server_connect(pmix_server_caddy_t *cd, pmix_buffer_t *buf,
pmix_op_cbfunc_t cbfunc);
PMIX_EXPORT pmix_status_t pmix_server_disconnect(pmix_server_caddy_t *cd, pmix_buffer_t *buf,
pmix_op_cbfunc_t cbfunc);
PMIX_EXPORT pmix_status_t pmix_server_notify_error(pmix_status_t status, pmix_proc_t procs[],
size_t nprocs, pmix_proc_t error_procs[],
size_t error_nprocs, pmix_info_t info[],
size_t ninfo, pmix_op_cbfunc_t cbfunc,
void *cbdata);
PMIX_EXPORT pmix_status_t pmix_server_register_events(pmix_peer_t *peer, pmix_buffer_t *buf,
pmix_op_cbfunc_t cbfunc, void *cbdata);
PMIX_EXPORT void pmix_server_deregister_events(pmix_peer_t *peer, pmix_buffer_t *buf);
PMIX_EXPORT pmix_status_t pmix_server_query(pmix_peer_t *peer, pmix_buffer_t *buf,
pmix_info_cbfunc_t cbfunc, void *cbdata);
PMIX_EXPORT pmix_status_t pmix_server_log(pmix_peer_t *peer, pmix_buffer_t *buf,
pmix_op_cbfunc_t cbfunc, void *cbdata);
PMIX_EXPORT pmix_status_t pmix_server_alloc(pmix_peer_t *peer, pmix_buffer_t *buf,
pmix_info_cbfunc_t cbfunc, void *cbdata);
PMIX_EXPORT pmix_status_t pmix_server_job_ctrl(pmix_peer_t *peer, pmix_buffer_t *buf,
pmix_info_cbfunc_t cbfunc, void *cbdata);
PMIX_EXPORT pmix_status_t pmix_server_monitor(pmix_peer_t *peer, pmix_buffer_t *buf,
pmix_info_cbfunc_t cbfunc, void *cbdata);
PMIX_EXPORT pmix_status_t pmix_server_get_credential(pmix_peer_t *peer, pmix_buffer_t *buf,
pmix_credential_cbfunc_t cbfunc, void *cbdata);
PMIX_EXPORT pmix_status_t pmix_server_validate_credential(pmix_peer_t *peer, pmix_buffer_t *buf,
pmix_validation_cbfunc_t cbfunc,
void *cbdata);
PMIX_EXPORT pmix_status_t pmix_server_iofreg(pmix_peer_t *peer, pmix_buffer_t *buf,
pmix_op_cbfunc_t cbfunc, void *cbdata);
PMIX_EXPORT pmix_status_t pmix_server_iofstdin(pmix_peer_t *peer, pmix_buffer_t *buf,
pmix_op_cbfunc_t cbfunc, void *cbdata);
PMIX_EXPORT pmix_status_t pmix_server_iofdereg(pmix_peer_t *peer, pmix_buffer_t *buf,
pmix_op_cbfunc_t cbfunc, void *cbdata);
PMIX_EXPORT pmix_status_t pmix_server_grpconstruct(pmix_server_caddy_t *cd, pmix_buffer_t *buf);
PMIX_EXPORT pmix_status_t pmix_server_grpdestruct(pmix_server_caddy_t *cd, pmix_buffer_t *buf);
PMIX_EXPORT pmix_status_t pmix_server_event_recvd_from_client(pmix_peer_t *peer, pmix_buffer_t *buf,
pmix_op_cbfunc_t cbfunc,
void *cbdata);
PMIX_EXPORT void pmix_server_execute_collective(int sd, short args, void *cbdata);
PMIX_EXPORT pmix_status_t pmix_server_initialize(void);
PMIX_EXPORT void pmix_server_message_handler(struct pmix_peer_t *pr, pmix_ptl_hdr_t *hdr,
pmix_buffer_t *buf, void *cbdata);
PMIX_EXPORT void pmix_server_purge_events(pmix_peer_t *peer, pmix_proc_t *proc);
PMIX_EXPORT pmix_status_t pmix_server_fabric_register(pmix_server_caddy_t *cd, pmix_buffer_t *buf,
pmix_info_cbfunc_t cbfunc);
PMIX_EXPORT pmix_status_t pmix_server_fabric_update(pmix_server_caddy_t *cd, pmix_buffer_t *buf,
pmix_info_cbfunc_t cbfunc);
PMIX_EXPORT pmix_status_t pmix_server_fabric_get_vertex_info(pmix_server_caddy_t *cd,
pmix_buffer_t *buf,
pmix_info_cbfunc_t cbfunc);
PMIX_EXPORT pmix_status_t pmix_server_fabric_get_device_index(pmix_server_caddy_t *cd,
pmix_buffer_t *buf,
pmix_info_cbfunc_t cbfunc);
PMIX_EXPORT pmix_status_t pmix_server_device_dists(pmix_server_caddy_t *cd,
pmix_buffer_t *buf,
pmix_device_dist_cbfunc_t cbfunc);
PMIX_EXPORT pmix_status_t pmix_server_refresh_cache(pmix_server_caddy_t *cd,
pmix_buffer_t *buf,
pmix_op_cbfunc_t cbfunc);
PMIX_EXPORT void pmix_server_query_cbfunc(pmix_status_t status,
pmix_info_t *info, size_t ninfo, void *cbdata,
pmix_release_cbfunc_t release_fn, void *release_cbdata);
PMIX_EXPORT extern pmix_server_module_t pmix_host_server;
PMIX_EXPORT extern pmix_server_globals_t pmix_server_globals;
static inline pmix_peer_t* pmix_get_peer_object(const pmix_proc_t *proc)
{
pmix_peer_t *peer;
int n;
for (n=0; n < pmix_server_globals.clients.size; n++) {
peer = (pmix_peer_t *) pmix_pointer_array_get_item(&pmix_server_globals.clients, n);
if (NULL == peer) {
continue;
}
if (PMIX_CHECK_NSPACE(proc->nspace, peer->info->pname.nspace) &&
proc->rank == peer->info->pname.rank) {
return peer;
}
}
return NULL;
}
#endif // PMIX_SERVER_OPS_H

View File

@@ -0,0 +1,97 @@
/* -*- Mode: C; c-basic-offset:4 ; indent-tabs-mode:nil -*- */
/*
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2016 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2007 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2007-2016 Los Alamos National Security, LLC. All rights
* reserved.
* Copyright (c) 2007 Voltaire. All rights reserved.
* Copyright (c) 2010 Oracle and/or its affiliates. All rights reserved.
*
* Copyright (c) 2017 Intel, Inc. All rights reserved.
* Copyright (c) 2021-2022 Nanook Consulting All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
#ifndef PMIX_MUTEX_H
#define PMIX_MUTEX_H 1
#include "src/include/pmix_config.h"
BEGIN_C_DECLS
/**
* @file:
*
* Mutual exclusion functions.
*
* Functions for locking of critical sections.
*/
/**
* Opaque mutex object
*/
typedef struct pmix_mutex_t pmix_mutex_t;
typedef struct pmix_mutex_t pmix_recursive_mutex_t;
/**
* Try to acquire a mutex.
*
* @param mutex Address of the mutex.
* @return 0 if the mutex was acquired, 1 otherwise.
*/
static inline int pmix_mutex_trylock(pmix_mutex_t *mutex);
/**
* Acquire a mutex.
*
* @param mutex Address of the mutex.
*/
static inline void pmix_mutex_lock(pmix_mutex_t *mutex);
/**
* Release a mutex.
*
* @param mutex Address of the mutex.
*/
static inline void pmix_mutex_unlock(pmix_mutex_t *mutex);
/**
* Try to acquire a mutex using atomic operations.
*
* @param mutex Address of the mutex.
* @return 0 if the mutex was acquired, 1 otherwise.
*/
static inline int pmix_mutex_atomic_trylock(pmix_mutex_t *mutex);
/**
* Acquire a mutex using atomic operations.
*
* @param mutex Address of the mutex.
*/
static inline void pmix_mutex_atomic_lock(pmix_mutex_t *mutex);
/**
* Release a mutex using atomic operations.
*
* @param mutex Address of the mutex.
*/
static inline void pmix_mutex_atomic_unlock(pmix_mutex_t *mutex);
END_C_DECLS
#include "pmix_mutex_unix.h"
#endif /* PMIX_MUTEX_H */

View File

@@ -0,0 +1,175 @@
/* -*- Mode: C; c-basic-offset:4 ; indent-tabs-mode:nil -*- */
/*
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2006 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2007-2015 Los Alamos National Security, LLC. All rights
* reserved.
* Copyright (c) 2015-2016 Research Organization for Information Science
* and Technology (RIST). All rights reserved.
* Copyright (c) 2017-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2021-2022 Nanook Consulting All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
#ifndef PMIX_MUTEX_UNIX_H
#define PMIX_MUTEX_UNIX_H 1
/**
* @file:
*
* Mutual exclusion functions: Unix implementation.
*
* Functions for locking of critical sections.
*
* On unix, use pthreads or our own atomic operations as
* available.
*/
#include "src/include/pmix_config.h"
#include <errno.h>
#include <pthread.h>
#include <stdio.h>
#include "src/class/pmix_object.h"
BEGIN_C_DECLS
struct pmix_mutex_t {
pmix_object_t super;
pthread_mutex_t m_lock_pthread;
#if PMIX_ENABLE_DEBUG
int m_lock_debug;
const char *m_lock_file;
int m_lock_line;
#endif
};
PMIX_EXPORT PMIX_CLASS_DECLARATION(pmix_mutex_t);
PMIX_EXPORT PMIX_CLASS_DECLARATION(pmix_recursive_mutex_t);
#if defined(PTHREAD_RECURSIVE_MUTEX_INITIALIZER_NP)
# define PMIX_PTHREAD_RECURSIVE_MUTEX_INITIALIZER PTHREAD_RECURSIVE_MUTEX_INITIALIZER_NP
#elif defined(PTHREAD_RECURSIVE_MUTEX_INITIALIZER)
# define PMIX_PTHREAD_RECURSIVE_MUTEX_INITIALIZER PTHREAD_RECURSIVE_MUTEX_INITIALIZER
#endif
#if PMIX_ENABLE_DEBUG
# define PMIX_MUTEX_STATIC_INIT \
{ \
.super = PMIX_OBJ_STATIC_INIT(pmix_mutex_t), \
.m_lock_pthread = PTHREAD_MUTEX_INITIALIZER, .m_lock_debug = 0, .m_lock_file = NULL, \
.m_lock_line = 0, \
}
#else
# define PMIX_MUTEX_STATIC_INIT \
{ \
.super = PMIX_OBJ_STATIC_INIT(pmix_mutex_t), \
.m_lock_pthread = PTHREAD_MUTEX_INITIALIZER, \
}
#endif
#if defined(PMIX_PTHREAD_RECURSIVE_MUTEX_INITIALIZER)
# if PMIX_ENABLE_DEBUG
# define PMIX_RECURSIVE_MUTEX_STATIC_INIT \
{ \
.super = PMIX_OBJ_STATIC_INIT(pmix_mutex_t), \
.m_lock_pthread = PMIX_PTHREAD_RECURSIVE_MUTEX_INITIALIZER, .m_lock_debug = 0, \
.m_lock_file = NULL, .m_lock_line = 0, \
}
# else
# define PMIX_RECURSIVE_MUTEX_STATIC_INIT \
{ \
.super = PMIX_OBJ_STATIC_INIT(pmix_mutex_t), \
.m_lock_pthread = PMIX_PTHREAD_RECURSIVE_MUTEX_INITIALIZER, \
}
# endif
#endif
/************************************************************************
*
* mutex operations (non-atomic versions)
*
************************************************************************/
static inline int pmix_mutex_trylock(pmix_mutex_t *m)
{
#if PMIX_ENABLE_DEBUG
int ret = pthread_mutex_trylock(&m->m_lock_pthread);
if (ret == EDEADLK) {
errno = ret;
perror("pmix_mutex_trylock()");
abort();
}
return ret;
#else
return pthread_mutex_trylock(&m->m_lock_pthread);
#endif
}
static inline void pmix_mutex_lock(pmix_mutex_t *m)
{
#if PMIX_ENABLE_DEBUG
int ret = pthread_mutex_lock(&m->m_lock_pthread);
if (ret == EDEADLK) {
errno = ret;
perror("pmix_mutex_lock()");
abort();
}
#else
pthread_mutex_lock(&m->m_lock_pthread);
#endif
}
static inline void pmix_mutex_unlock(pmix_mutex_t *m)
{
#if PMIX_ENABLE_DEBUG
int ret = pthread_mutex_unlock(&m->m_lock_pthread);
if (ret == EPERM) {
errno = ret;
perror("pmix_mutex_unlock");
abort();
}
#else
pthread_mutex_unlock(&m->m_lock_pthread);
#endif
}
/************************************************************************
* Standard locking
************************************************************************/
static inline int pmix_mutex_atomic_trylock(pmix_mutex_t *m)
{
return pmix_mutex_trylock(m);
}
static inline void pmix_mutex_atomic_lock(pmix_mutex_t *m)
{
pmix_mutex_lock(m);
}
static inline void pmix_mutex_atomic_unlock(pmix_mutex_t *m)
{
pmix_mutex_unlock(m);
}
END_C_DECLS
#endif /* PMIX_MUTEX_UNIX_H */

View File

@@ -0,0 +1,204 @@
/*
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2006 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2010 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2010 Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 2015-2017 Research Organization for Information Science
* and Technology (RIST). All rights reserved.
* Copyright (c) 2017-2019 Intel, Inc. All rights reserved.
* Copyright (c) 2021-2022 Nanook Consulting All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
#ifndef PMIX_THREAD_H
#define PMIX_THREAD_H 1
#include "src/include/pmix_config.h"
#include <pthread.h>
#include <signal.h>
#include "src/class/pmix_object.h"
#include "src/include/pmix_atomic.h"
#if PMIX_ENABLE_DEBUG
# include "src/util/pmix_output.h"
#endif
#include "pmix_mutex.h"
BEGIN_C_DECLS
typedef void *(*pmix_thread_fn_t)(pmix_object_t *);
#define PMIX_THREAD_CANCELLED ((void *) 1);
struct pmix_thread_t {
pmix_object_t super;
pmix_thread_fn_t t_run;
void *t_arg;
pthread_t t_handle;
};
typedef struct pmix_thread_t pmix_thread_t;
#if PMIX_ENABLE_DEBUG
PMIX_EXPORT extern bool pmix_debug_threads;
#endif
PMIX_EXPORT PMIX_CLASS_DECLARATION(pmix_thread_t);
#define pmix_condition_wait(a, b) pthread_cond_wait(a, &(b)->m_lock_pthread)
typedef pthread_cond_t pmix_condition_t;
#define pmix_condition_broadcast(a) pthread_cond_broadcast(a)
#define pmix_condition_signal(a) pthread_cond_signal(a)
#define PMIX_CONDITION_STATIC_INIT PTHREAD_COND_INITIALIZER
typedef struct {
pmix_status_t status;
pmix_mutex_t mutex;
pmix_condition_t cond;
volatile bool active;
} pmix_lock_t;
#define PMIX_LOCK_STATIC_INIT \
{ \
.status = PMIX_SUCCESS, \
.mutex = PMIX_MUTEX_STATIC_INIT, \
.cond = PMIX_CONDITION_STATIC_INIT, \
.active = false \
}
#define PMIX_CONSTRUCT_LOCK(l) \
do { \
PMIX_CONSTRUCT(&(l)->mutex, pmix_mutex_t); \
pthread_cond_init(&(l)->cond, NULL); \
/* coverity[missing_lock : FALSE] */ \
(l)->active = true; \
} while (0)
#define PMIX_DESTRUCT_LOCK(l) \
do { \
PMIX_DESTRUCT(&(l)->mutex); \
pthread_cond_destroy(&(l)->cond); \
} while (0)
#if PMIX_ENABLE_DEBUG
# define PMIX_ACQUIRE_THREAD(lck) \
do { \
pmix_mutex_lock(&(lck)->mutex); \
if (pmix_debug_threads) { \
pmix_output(0, "Waiting for thread %s:%d", __FILE__, __LINE__); \
} \
while ((lck)->active) { \
pmix_condition_wait(&(lck)->cond, &(lck)->mutex); \
} \
if (pmix_debug_threads) { \
pmix_output(0, "Thread obtained %s:%d", __FILE__, __LINE__); \
} \
PMIX_ACQUIRE_OBJECT(lck); \
(lck)->active = true; \
} while (0)
#else
# define PMIX_ACQUIRE_THREAD(lck) \
do { \
pmix_mutex_lock(&(lck)->mutex); \
while ((lck)->active) { \
pmix_condition_wait(&(lck)->cond, &(lck)->mutex); \
} \
PMIX_ACQUIRE_OBJECT(lck); \
(lck)->active = true; \
} while (0)
#endif
#if PMIX_ENABLE_DEBUG
# define PMIX_WAIT_THREAD(lck) \
do { \
pmix_mutex_lock(&(lck)->mutex); \
if (pmix_debug_threads) { \
pmix_output(0, "Waiting for thread %s:%d", __FILE__, __LINE__); \
} \
while ((lck)->active) { \
pmix_condition_wait(&(lck)->cond, &(lck)->mutex); \
} \
if (pmix_debug_threads) { \
pmix_output(0, "Thread obtained %s:%d", __FILE__, __LINE__); \
} \
PMIX_ACQUIRE_OBJECT(lck); \
pmix_mutex_unlock(&(lck)->mutex); \
} while (0)
#else
# define PMIX_WAIT_THREAD(lck) \
do { \
pmix_mutex_lock(&(lck)->mutex); \
while ((lck)->active) { \
pmix_condition_wait(&(lck)->cond, &(lck)->mutex); \
} \
PMIX_ACQUIRE_OBJECT(lck); \
pmix_mutex_unlock(&(lck)->mutex); \
} while (0)
#endif
#if PMIX_ENABLE_DEBUG
# define PMIX_RELEASE_THREAD(lck) \
do { \
if (pmix_debug_threads) { \
pmix_output(0, "Releasing thread %s:%d", __FILE__, __LINE__); \
} \
(lck)->active = false; \
PMIX_POST_OBJECT(lck); \
pmix_condition_broadcast(&(lck)->cond); \
pmix_mutex_unlock(&(lck)->mutex); \
} while (0)
#else
# define PMIX_RELEASE_THREAD(lck) \
do { \
(lck)->active = false; \
PMIX_POST_OBJECT(lck); \
pmix_condition_broadcast(&(lck)->cond); \
pmix_mutex_unlock(&(lck)->mutex); \
} while (0)
#endif
#define PMIX_WAKEUP_THREAD(lck) \
do { \
pmix_mutex_lock(&(lck)->mutex); \
(lck)->active = false; \
PMIX_POST_OBJECT(lck); \
pmix_condition_broadcast(&(lck)->cond); \
pmix_mutex_unlock(&(lck)->mutex); \
} while (0)
/* provide a macro for forward-proofing the shifting
* of objects between threads - at some point, we
* may revamp our threading model */
/* post an object to another thread - for now, we
* only have a memory barrier */
#define PMIX_POST_OBJECT(o) pmix_atomic_wmb()
/* acquire an object from another thread - for now,
* we only have a memory barrier */
#define PMIX_ACQUIRE_OBJECT(o) pmix_atomic_rmb()
PMIX_EXPORT int pmix_thread_start(pmix_thread_t *);
PMIX_EXPORT int pmix_thread_join(pmix_thread_t *, void **thread_return);
PMIX_EXPORT bool pmix_thread_self_compare(pmix_thread_t *);
PMIX_EXPORT pmix_thread_t *pmix_thread_get_self(void);
PMIX_EXPORT void pmix_thread_kill(pmix_thread_t *, int sig);
PMIX_EXPORT void pmix_thread_set_main(void);
END_C_DECLS
#endif /* PMIX_THREAD_H */

View File

@@ -0,0 +1,103 @@
/*
* Copyright (c) 2007-2013 Los Alamos National Security, LLC. All rights
* reserved.
* Copyright (c) 2008 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2015-2017 Research Organization for Information Science
* and Technology (RIST). All rights reserved.
* Copyright (c) 2017-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2021-2022 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
#ifndef PMIX_THREADS_TSD_H
#define PMIX_THREADS_TSD_H
#include "src/include/pmix_config.h"
#include <pthread.h>
#include "pmix_common.h"
BEGIN_C_DECLS
/**
* @file
*
* Thread Specific Datastore Interface
*
* Functions for providing thread-specific datastore capabilities.
*/
/**
* Prototype for callback when tsd data is being destroyed
*/
typedef void (*pmix_tsd_destructor_t)(void *value);
typedef pthread_key_t pmix_tsd_key_t;
static inline int pmix_tsd_key_delete(pmix_tsd_key_t key)
{
return pthread_key_delete(key);
}
static inline int pmix_tsd_setspecific(pmix_tsd_key_t key, void *value)
{
return pthread_setspecific(key, value);
}
static inline int pmix_tsd_getspecific(pmix_tsd_key_t key, void **valuep)
{
*valuep = pthread_getspecific(key);
return PMIX_SUCCESS;
}
/**
* Create thread-specific data key
*
* Create a thread-specific data key visible to all threads in the
* current process. The returned key is valid in all threads,
* although the values bound to the key by pmix_tsd_setspecific() are
* allocated on a per-thread basis and persist for the life of the
* calling thread.
*
* Upon key creation, the value NULL is associated with the new key in
* all active threads. When a new thread is created, the value NULL
* is associated with all defined keys in the new thread.
*
* The destructor parameter may be NULL. At thread exit, if
* destructor is non-NULL AND the thread has a non-NULL value
* associated with the key, the function is called with the current
* value as its argument.
*
* @param key[out] The key for accessing thread-specific data
* @param destructor[in] Cleanup function to call when a thread exits
*
* @retval PMIX_SUCCESS Success
* @retval EAGAIN The system lacked the necessary resource to
* create another thread specific data key
* @retval ENOMEM Insufficient memory exists to create the key
*/
PMIX_EXPORT int pmix_tsd_key_create(pmix_tsd_key_t *key,
pmix_tsd_destructor_t destructor);
/**
* Destruct all thread-specific data keys
*
* Destruct all thread-specific data keys and invoke the destructor
*
* This should only be invoked in the main thread.
* This is made necessary since destructors are not invoked on the
* keys of the main thread, since there is no such thing as
* pthread_join(main_thread)
*
* @retval PMIX_SUCCESS Success
*/
PMIX_EXPORT int pmix_tsd_keys_destruct(void);
END_C_DECLS
#endif /* PMIX_MTHREADS_TSD_H */

View File

@@ -0,0 +1,19 @@
/* -*- Mode: C; c-basic-offset:4 ; indent-tabs-mode:nil -*- */
/*
* Copyright (c) 2020 Intel, Inc. All rights reserved.
*
* Copyright (c) 2021-2022 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*/
#ifndef PMIX_TOOL_OPS_H
#define PMIX_TOOL_OPS_H
#include "src/include/pmix_config.h"
#include "src/include/pmix_globals.h"
#include "src/include/pmix_types.h"
PMIX_EXPORT pmix_status_t pmix_tool_relay_op(pmix_cmd_t cmd, pmix_peer_t *peer, pmix_buffer_t *bfr,
uint32_t tag);
#endif // PMIX_TOOL_OPS_H

View File

@@ -0,0 +1,37 @@
/*
* Copyright (c) 2014 Mellanox Technologies, Inc.
* All rights reserved.
* Copyright (c) 2014 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2014-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2021-2022 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
#ifndef PMIX_ALFG_H
#define PMIX_ALFG_H
#include "src/include/pmix_config.h"
#include "pmix_common.h"
#include "src/include/pmix_stdint.h"
struct pmix_rng_buff_t {
uint32_t alfg[127];
int tap1;
int tap2;
};
typedef struct pmix_rng_buff_t pmix_rng_buff_t;
/* NOTE: UNLIKE OTHER PMIX FUNCTIONS, THIS FUNCTION RETURNS A 1 IF
* SUCCESSFUL INSTEAD OF PMIX_SUCCESS */
PMIX_EXPORT int pmix_srand(pmix_rng_buff_t *buff, uint32_t seed);
PMIX_EXPORT uint32_t pmix_rand(pmix_rng_buff_t *buff);
PMIX_EXPORT int pmix_random(void);
#endif /* PMIX_ALFG_H */

View File

@@ -0,0 +1,190 @@
/*
* Copyright (c) 2004-2007 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2005 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2008 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2007 Los Alamos National Security, LLC.
* All rights reserved.
* Copyright (c) 2007 Voltaire. All rights reserved.
* Copyright (c) 2012 Los Alamos National Security, LLC. All rights reserved.
* Copyright (c) 2015-2020 Intel, Inc. All rights reserved.
*
* Copyright (c) 2015-2019 Research Organization for Information Science
* and Technology (RIST). All rights reserved.
* Copyright (c) 2021-2022 Nanook Consulting All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
/**
* @file
*
* Generic routines for "argv"-like handling. Helpful for creating
* arrays of strings, especially when creating command lines.
*/
#ifndef PMIX_ARGV_H
#define PMIX_ARGV_H
#include "src/include/pmix_config.h"
#ifdef HAVE_SYS_TYPES_H
# include <sys/types.h>
#endif
#include "pmix_common.h"
BEGIN_C_DECLS
/**
* Append a string (by value) to an new or existing NULL-terminated
* argv array.
*
* @param argc Pointer to the length of the argv array. Must not be
* NULL.
* @param argv Pointer to an argv array.
* @param str Pointer to the string to append.
*
* @retval PMIX_SUCCESS On success
* @retval PMIX_ERROR On failure
*
* This function adds a string to an argv array of strings by value;
* it is permissible to pass a string on the stack as the str
* argument to this function.
*
* To add the first entry to an argv array, call this function with
* (*argv == NULL). This function will allocate an array of length
* 2; the first entry will point to a copy of the string passed in
* arg, the second entry will be set to NULL.
*
* If (*argv != NULL), it will be realloc'ed to be 1 (char*) larger,
* and the next-to-last entry will point to a copy of the string
* passed in arg. The last entry will be set to NULL.
*
* Just to reinforce what was stated above: the string is copied by
* value into the argv array; there is no need to keep the original
* string (i.e., the arg parameter) after invoking this function.
*/
PMIX_EXPORT pmix_status_t pmix_argv_append(int *argc, char ***argv, const char *arg)
__pmix_attribute_nonnull__(1) __pmix_attribute_nonnull__(3);
/**
* Append to an argv-style array, but only if the provided argument
* doesn't already exist somewhere in the array. Ignore the size of the array.
* Defines the index of the found/added item in the array.
*
* @param idx Index the found/added item in the array.
* @param argv Pointer to an argv array.
* @param str Pointer to the string to append.
*
* @retval PMIX_SUCCESS On success
* @retval PMIX_ERROR On failure
*
* This function is identical to the PMIx_Argv_append_unique_nosize() function
* but it has an extra argument defining the index of the item in the array.
*/
PMIX_EXPORT pmix_status_t pmix_argv_append_unique_idx(int *idx, char ***argv, const char *arg);
PMIX_EXPORT char *pmix_argv_join_range(char **argv, size_t start, size_t end, int delimiter)
__pmix_attribute_malloc__ __pmix_attribute_warn_unused_result__;
/**
* Return the number of bytes consumed by an argv array.
*
* @param argv The input argv array.
*
* Count the number of bytes consumed by a NULL-terminated argv
* array. This includes the number of bytes used by each of the
* strings as well as the pointers used in the argv array.
*/
PMIX_EXPORT size_t pmix_argv_len(char **argv);
/**
* Delete one or more tokens from the middle of an argv.
*
* @param argv The argv to delete from
* @param start The index of the first token to delete
* @param num_to_delete How many tokens to delete
*
* @retval PMIX_SUCCESS Always
*
* Delete some tokens from within an existing argv. The start
* parameter specifies the first token to delete, and will delete
* (num_to_delete-1) tokens following it. argv will be realloc()ed
* to *argc - num_deleted size.
*
* If start is beyond the end of the argv array, this function is
* a no-op.
*
* If num_to_delete runs beyond the end of the argv array, this
* function will delete all tokens starting with start to the end
* of the array.
*
* All deleted items in the argv array will have their contents
* free()ed (it is assumed that the argv "owns" the memory that
* the pointer points to).
*/
PMIX_EXPORT pmix_status_t pmix_argv_delete(int *argc, char ***argv, int start, int num_to_delete);
/**
* Insert one argv array into the middle of another
*
* @param target The argv to insert tokens into
* @param start Index where the first token will be placed in target
* @param source The argv to copy tokens from
*
* @retval PMIX_SUCCESS upon success
* @retval PMIX_BAD_PARAM if any parameters are non-sensical
*
* This function takes one arg and inserts it in the middle of
* another. The first token in source will be inserted at index
* start in the target argv; all other tokens will follow it.
* Similar to pmix_argv_append(), the target may be realloc()'ed
* to accommodate the new storage requirements.
*
* The source array is left unaffected -- its contents are copied
* by value over to the target array (i.e., the strings that
* source points to are strdup'ed into the new locations in
* target).
*/
PMIX_EXPORT pmix_status_t pmix_argv_insert(char ***target, int start, char **source);
/**
* Insert one argv element in front of a specific position in an array
*
* @param target The argv to insert tokens into
* @param location Index where the token will be placed in target
* @param source The token to be inserted
*
* @retval PMIX_SUCCESS upon success
* @retval PMIX_BAD_PARAM if any parameters are non-sensical
*
* This function takes one arg and inserts it in the middle of
* another. The token will be inserted at the specified index
* in the target argv; all other tokens will be shifted down.
* Similar to pmix_argv_append(), the target may be realloc()'ed
* to accommodate the new storage requirements.
*
* The source token is left unaffected -- its contents are copied
* by value over to the target array (i.e., the string that
* source points to is strdup'ed into the new location in
* target).
*/
PMIX_EXPORT pmix_status_t pmix_argv_insert_element(char ***target, int location, char *source);
PMIX_EXPORT
char **pmix_argv_copy_strip(char **argv) __pmix_attribute_malloc__ __pmix_attribute_warn_unused_result__;
END_C_DECLS
#endif /* PMIX_ARGV_H */

View File

@@ -0,0 +1,117 @@
/*
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2005 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2015-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2021-2022 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
/**
* @file
*
* Returns an OS-independant basename() of a given filename.
*/
#ifndef PMIX_BASENAME_H
#define PMIX_BASENAME_H
#include "src/include/pmix_config.h"
#include "pmix_common.h"
BEGIN_C_DECLS
/**
* Return the basename of a filename.
*
* @param filename The filename to examine
*
* @returns A string containing the basename, or NULL if there is an error
*
* The contents of the \em filename parameter are unchanged. This
* function returns a new string containing the basename of the
* filename (which must be eventually freed by the caller), or
* NULL if there is an error. Trailing "/" characters in the
* filename do not count, unless it is in the only part of the
* filename (e.g., "/" or "C:\").
*
* This function will do the Right Things on POSIX and
* Windows-based operating systems. For example:
*
* foo.txt returns "foo.txt"
*
* /foo/bar/baz returns "baz"
*
* /yow.c returns "yow.c"
*
* / returns "/"
*
* C:\foo\bar\baz returns "baz"
*
* D:foo.txt returns "foo.txt"
*
* E:\yow.c returns "yow.c"
*
* F: returns "F:"
*
* G:\ returns "G:"
*
* The caller is responsible for freeing the returned string.
*/
PMIX_EXPORT char *
pmix_basename(const char *filename) __pmix_attribute_malloc__ __pmix_attribute_warn_unused_result__;
/**
* Return the dirname of a filename.
*
* @param filename The filename to examine
*
* @returns A string containing the dirname, or NULL if there is an error
*
* The contents of the \em filename parameter are unchanged. This
* function returns a new string containing the dirname of the
* filename (which must be eventually freed by the caller), or
* NULL if there is an error. Trailing "/" characters in the
* filename do not count, unless it is in the only part of the
* filename (e.g., "/" or "C:\").
*
* This function will do the Right Things on POSIX and
* Windows-based operating systems. For example:
*
* foo.txt returns "foo.txt"
*
* /foo/bar/baz returns "/foo/bar"
*
* /yow.c returns "/"
*
* / returns ""
*
* C:\foo\bar\baz returns "C:\foo\bar"
*
* D:foo.txt returns "D:"
*
* E:\yow.c returns "E:"
*
* F: returns ""
*
* G:\ returns ""
*
* The caller is responsible for freeing the returned string.
*/
PMIX_EXPORT char *
pmix_dirname(const char *filename) __pmix_attribute_malloc__ __pmix_attribute_warn_unused_result__;
END_C_DECLS
#endif /* PMIX_BASENAME_H */

View File

@@ -0,0 +1,338 @@
/* -*- Mode: C; c-basic-offset:4 ; indent-tabs-mode:nil -*- */
/*
* Copyright (c) 2004-2007 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2005 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2012-2020 Cisco Systems, Inc. All rights reserved
* Copyright (c) 2015-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2016-2017 Los Alamos National Security, LLC. All rights
* reserved.
* Copyright (c) 2017 IBM Corporation. All rights reserved.
* Copyright (c) 2021-2023 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
#ifndef PMIX_CMD_LINE_H
#define PMIX_CMD_LINE_H
#include "src/include/pmix_config.h"
#ifdef HAVE_UNISTD_H
# include <unistd.h>
#endif
#include <ctype.h>
#include <stdio.h>
#include <string.h>
#include <getopt.h>
#include "src/class/pmix_list.h"
#include "src/class/pmix_object.h"
#include "src/util/pmix_argv.h"
BEGIN_C_DECLS
typedef struct {
pmix_list_item_t super;
char *key;
char **values;
} pmix_cli_item_t;
PMIX_CLASS_DECLARATION(pmix_cli_item_t);
typedef struct {
pmix_object_t super;
pmix_list_t instances; // comprised of pmix_cli_item_t's
char **tail; // remainder of argv
} pmix_cli_result_t;
PMIX_CLASS_DECLARATION(pmix_cli_result_t);
#define PMIX_CLI_RESULT_STATIC_INIT \
{ \
.super = PMIX_OBJ_STATIC_INIT(pmix_object_t), \
.instances = PMIX_LIST_STATIC_INIT, \
.tail = NULL \
}
/* define PMIX-named flags for argument required */
#define PMIX_ARG_REQD required_argument
#define PMIX_ARG_NONE no_argument
#define PMIX_ARG_OPTIONAL optional_argument
/* define PMIX-named flags for whether parsing
* CLI shall include deprecation warnings */
#define PMIX_CLI_SILENT true
#define PMIX_CLI_WARN false
/* define a long option that has no short option equivalent
*
* n = name of the option (see below for definitions)
* a = whether or not it requires an argument
*/
#define PMIX_OPTION_DEFINE(n, a) \
{ \
.name = (n), \
.has_arg = (a), \
.flag = NULL, \
.val = 0 \
}
/* define a long option that has a short option equivalent
*
* n = name of the option (see below for definitions)
* a = whether or not it requires an argument
* c = single character equivalent option
*/
#define PMIX_OPTION_SHORT_DEFINE(n, a, c) \
{ \
.name = (n), \
.has_arg = (a), \
.flag = NULL, \
.val = (c) \
}
#define PMIX_OPTION_END {0, 0, 0, 0}
// NAME STRING ARGUMENT
// Basic options
#define PMIX_CLI_HELP "help" // optional
#define PMIX_CLI_VERSION "version" // none
#define PMIX_CLI_VERBOSE "verbose" // number of instances => verbosity level
#define PMIX_CLI_PMIXMCA "pmixmca" // requires TWO
// Tool connection options
#define PMIX_CLI_SYS_SERVER_FIRST "system-server-first" // none
#define PMIX_CLI_SYSTEM_SERVER "system-server" // none
#define PMIX_CLI_SYS_SERVER_ONLY "system-server-only" // none
#define PMIX_CLI_DO_NOT_CONNECT "do-not-connect" // none
#define PMIX_CLI_WAIT_TO_CONNECT "wait-to-connect" // required
#define PMIX_CLI_NUM_CONNECT_RETRIES "num-connect-retries" // required
#define PMIX_CLI_PID "pid" // required
#define PMIX_CLI_NAMESPACE "namespace" // required
#define PMIX_CLI_NSPACE "nspace" // required
#define PMIX_CLI_URI "uri" // required
#define PMIX_CLI_TIMEOUT "timeout" // required
#define PMIX_CLI_TMPDIR "tmpdir" // required
#define PMIX_CLI_CONNECTION_ORDER "connect-order" // required
#define PMIX_CLI_SYS_CONTROLLER "system-controller" // none
// Allocation request options
#define PMIX_CLI_REQ_ID "request-id" // required
#define PMIX_CLI_QUEUE "queue" // required, short is 'q'
#define PMIX_CLI_RESOURCES "resources" // required
#define PMIX_CLI_NODES "nodes" // required, short is 'N'
#define PMIX_CLI_IMAGE "image" // required, short is 'i'
#define PMIX_CLI_EXCLUDE "exclude" // required, short is 'x'
#define PMIX_CLI_WAIT_ALL_NODES "wait-all-nodes" // none
#define PMIX_CLI_NODELIST "nodelist" // required, short is 'w'
#define PMIX_CLI_UID "uid" // required
#define PMIX_CLI_GID "gid" // required
#define PMIX_CLI_TIME "time" // required, short is 't'
#define PMIX_CLI_SIGNAL "signal" // required
#define PMIX_CLI_SHARE "share" // none
#define PMIX_CLI_EXTEND "extend" // none
#define PMIX_CLI_SHRINK "shrink" // none
#define PMIX_CLI_NO_SHELL "no-shell" // none
#define PMIX_CLI_BEGIN "begin" // required
#define PMIX_CLI_IMMEDIATE "immediate" // optional, short is 'I'
#define PMIX_CLI_DEPENDENCY "dependency" // required, short is 'd'
#define PMIX_CLI_DO_NOT_WAIT "do-not-wait" // none
// Job control options
#define PMIX_CLI_PAUSE "pause" // none
#define PMIX_CLI_RESUME "resume" // none
#define PMIX_CLI_CANCEL "cancel" // required
#define PMIX_CLI_KILL "kill" // none
#define PMIX_CLI_RESTART "restart" // required
#define PMIX_CLI_CHKPT "checkpoint" // required
#define PMIX_CLI_TARGETS "targets" // required
#define PMIX_CLI_TERMINATE "terminate" // none
#define PMIX_CLI_PSET_NAME "pset" // required
typedef void (*pmix_cmd_line_store_fn_t)(const char *name, const char *option,
pmix_cli_result_t *results);
PMIX_EXPORT int pmix_cmd_line_parse(char **argv, char *shorts,
struct option myoptions[],
pmix_cmd_line_store_fn_t storefn,
pmix_cli_result_t *results,
char *helpfile);
static inline pmix_cli_item_t* pmix_cmd_line_get_param(pmix_cli_result_t *results,
const char *key)
{
pmix_cli_item_t *opt;
PMIX_LIST_FOREACH(opt, &results->instances, pmix_cli_item_t) {
if (0 == strcmp(opt->key, key)) {
return opt;
}
}
return NULL;
}
static inline bool pmix_cmd_line_is_taken(pmix_cli_result_t *results,
const char *key)
{
if (NULL == pmix_cmd_line_get_param(results, key)) {
return false;
}
return true;
}
static inline int pmix_cmd_line_get_ninsts(pmix_cli_result_t *results,
const char *key)
{
pmix_cli_item_t *opt;
opt = pmix_cmd_line_get_param(results, key);
if (NULL == opt) {
return 0;
}
return PMIx_Argv_count(opt->values);
}
static inline char* pmix_cmd_line_get_nth_instance(pmix_cli_result_t *results,
const char *key, int idx)
{
pmix_cli_item_t *opt;
int ninst;
opt = pmix_cmd_line_get_param(results, key);
if (NULL == opt) {
return NULL;
}
ninst = PMIx_Argv_count(opt->values);
if (ninst < idx) {
return NULL;
}
return opt->values[idx];
}
/* USAGE:
* param "a" is the input command line string
* param "b" is the defined CLI option
*/
static inline bool pmix_check_cli_option(char *a, char *b)
{
size_t len1, len2, len, n;
char **asplit, **bsplit;
int match;
/* if there exists a '-' in either argument,
* then we are dealing with a multi-word
* option. Parse those by checking each
* word segment individually for a match
* so the user doesn't have to spell it all
* out unless necessary. We consider it a
* valid match if all provided segments match
* that of the target option */
if (NULL != strchr(b, '-') ||
NULL != strchr(a, '-')) {
asplit = PMIx_Argv_split(a, '-');
bsplit = PMIx_Argv_split(b, '-');
if (PMIx_Argv_count(asplit) > PMIx_Argv_count(bsplit)) {
PMIx_Argv_free(asplit);
PMIx_Argv_free(bsplit);
return false;
}
match = 0;
for (n=0; NULL != asplit[n] && NULL != bsplit[n]; n++) {
len1 = strlen(asplit[n]);
len2 = strlen(bsplit[n]);
len = len1 < len2 ? len1 : len2;
if (0 == strncasecmp(asplit[n], bsplit[n], len)) {
++match;
} else {
PMIx_Argv_free(asplit);
PMIx_Argv_free(bsplit);
return false;
}
}
PMIx_Argv_free(asplit);
PMIx_Argv_free(bsplit);
if (match == PMIx_Argv_count(asplit)) {
/* all provided segments match */
return true;
}
return false;
}
/* if this is not a multi-word option, we just
* check the strings */
len1 = strlen(a);
len2 = strlen(b);
len = (len1 < len2) ? len1 : len2;
if (0 == strncasecmp(a, b, len)) {
return true;
}
return false;
}
#define PMIX_CHECK_CLI_OPTION(a, b) \
pmix_check_cli_option(a, b)
static inline unsigned int pmix_convert_string_to_time(const char *t)
{
char **tmp = PMIx_Argv_split(t, ':');
int sz = PMIx_Argv_count(tmp);
unsigned int tm;
/* work upwards from the bottom, where the
* bottom represents seconds, then minutes,
* then hours, and then days */
tm = strtoul(tmp[sz-1], NULL, 10);
if (0 <= (sz-2) && NULL != tmp[sz-2]) {
tm += 60 * strtoul(tmp[sz-2], NULL, 10);
}
if (0 <= (sz-3) && NULL != tmp[sz-3]) {
tm += 60 * 60 * strtoul(tmp[sz-3], NULL, 10);
}
if (0 <= (sz-4) && NULL != tmp[sz-4]) {
tm += 24 * 60 * 60 * strtoul(tmp[sz-4], NULL, 10);
}
PMIx_Argv_free(tmp);
return tm;
}
#define PMIX_CONVERT_TIME(s) \
pmix_convert_string_to_time(s)
#define PMIX_CLI_DEBUG_LIST(r) \
do { \
pmix_cli_item_t *_c; \
char *_tail; \
pmix_output(0, "\n[%s:%s:%d]", __FILE__, __func__, __LINE__); \
PMIX_LIST_FOREACH(_c, &(r)->instances, pmix_cli_item_t) { \
pmix_output(0, "KEY: %s", _c->key); \
if (NULL != _c->values) { \
for (int _n=0; NULL != _c->values[_n]; _n++) { \
pmix_output(0, " VAL[%d]: %s", _n, _c->values[_n]); \
} \
} \
} \
_tail = PMIx_Argv_join((r)->tail, ' '); \
pmix_output(0, "TAIL: %s", _tail); \
free(_tail); \
pmix_output(0, "\n"); \
} while(0)
#define PMIX_CLI_REMOVE_DEPRECATED(r, o) \
do { \
pmix_list_remove_item(&(r)->instances, &(o)->super); \
PMIX_RELEASE(o); \
} while(0)
END_C_DECLS
#endif /* PMIX_CMD_LINE_H */

View File

@@ -0,0 +1,43 @@
/*
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2006 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2008 Sun Microsystems, Inc. All rights reserved.
* Copyright (c) 2019-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2022 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
/** @file:
*
*/
#ifndef _PMIX_CONTEXT_FNS_H_
#define _PMIX_CONTEXT_FNS_H_
#include "src/include/pmix_config.h"
#include "pmix_common.h"
BEGIN_C_DECLS
PMIX_EXPORT pmix_status_t pmix_util_check_context_cwd(char **incwd,
bool want_chdir,
bool user_cwd);
PMIX_EXPORT pmix_status_t pmix_util_check_context_app(char **incmd,
char *cwd,
char **env);
END_C_DECLS
#endif

View File

@@ -0,0 +1,155 @@
/*
* Copyright (c) 2004-2007 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2005 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2007-2013 Los Alamos National Security, LLC. All rights
* reserved.
* Copyright (c) 2015-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2015 Research Organization for Information Science
* and Technology (RIST). All rights reserved.
* Copyright (c) 2016 IBM Corporation. All rights reserved.
* Copyright (c) 2022 Amazon.com, Inc. or its affiliates.
* All Rights reserved.
* Copyright (c) 2021-2022 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
/**
* @file
*
* Generic helper routines for environment manipulation.
*/
#ifndef PMIX_ENVIRON_H
#define PMIX_ENVIRON_H
#include <unistd.h>
#ifdef HAVE_CRT_EXTERNS_H
# include <crt_externs.h>
#endif
#include "pmix_common.h"
#include "src/class/pmix_list.h"
BEGIN_C_DECLS
/**
* Merge two environ-like arrays into a single, new array, ensuring
* that there are no duplicate entries.
*
* @param minor Set 1 of the environ's to merge
* @param major Set 2 of the environ's to merge
* @retval New array of environ
*
* Merge two environ-like arrays into a single, new array,
* ensuring that there are no duplicate entries. If there are
* duplicates, entries in the \em major array are favored over
* those in the \em minor array.
*
* Both \em major and \em minor are expected to be argv-style
* arrays (i.e., terminated with a NULL pointer).
*
* The array that is returned is an unencumbered array that should
* later be freed with a call to PMIx_Argv_free().
*
* Either (or both) of \em major and \em minor can be NULL. If
* one of the two is NULL, the other list is simply copied to the
* output. If both are NULL, NULL is returned.
*/
PMIX_EXPORT char **pmix_environ_merge(char **minor,
char **major) __pmix_attribute_warn_unused_result__;
/**
* Merge contents of an environ-like array into a second environ-like
* array
*
* @param orig The environment to update
* @param additions The environment to merge into orig
*
* Merge the contents of \em additions into \em orig. If a key from
* \em additions is found in \em orig, then the value in orig is not
* updated (ie, it is an additions-only merge). The original
* environment cannot be environ, because pmix_argv_append is used to
* extend the environment, and PMIx_Argv_append_nosize() may not be
* safe to call on environ (for the same reason that realloc() may
* note be safe to call on environ).
*
* New strings are allocated when copied, so both \em orig and \em
* additions individually maintain their ability to be freed with
* PMIx_Argv_free().
*
* Note that on error, the \em orig array may be partially updated
* with values from additions, but the array will still be a valid
* argv-style array.
*/
PMIX_EXPORT pmix_status_t pmix_environ_merge_inplace(char ***orig,
char **additions)
__pmix_attribute_warn_unused_result__ __pmix_attribute_nonnull__(1);
/**
* Portable version of getenv(3), allowing searches of any key=value array
*
* @param name String name of the environment variable to look for
* @param env The environment to use
*
* The return value will be a pointer to the start of the value
* string. The string returned should not be free()ed or modified by
* the caller, similar to getenv().
*
* Unlike getenv(), pmix_getenv() will accept a \em name in key=value
* format. In that case, only the key portion of \em name is used for
* the search, and the return value of pmix_getenv() is the value of
* the same key in \em env.
*/
PMIX_EXPORT char * pmix_getenv(const char *name, char **env) __pmix_attribute_nonnull__(1);
/**
* Portable version of unsetenv(3), allowing editing of any
* environ-like array.
*
* @param name String name of the environment variable to look for
* @param env The environment to use
*
* @retval PMIX_ERR_OUT_OF_RESOURCE If an internal malloc fails.
* @retval PMIX_ERR_NOT_FOUND If \em name is not found in \em env.
* @retval PMIX_SUCCESS If \em name is found and successfully deleted.
*
* If \em name is found in \em env, the string corresponding to
* that entry is freed and its entry is eliminated from the array.
*/
PMIX_EXPORT pmix_status_t pmix_unsetenv(const char *name, char ***env)
__pmix_attribute_nonnull__(1);
/* A consistent way to retrieve the home and tmp directory on all supported
* platforms.
*/
PMIX_EXPORT const char *pmix_home_directory(uid_t uid);
PMIX_EXPORT const char *pmix_tmp_directory(void);
/* Provide a utility for harvesting envars */
PMIX_EXPORT pmix_status_t pmix_util_harvest_envars(char **incvars, char **excvars,
pmix_list_t *ilist);
/* Some care is needed with environ on OS X when dealing with shared
libraries. Handle that care here... */
#ifdef HAVE__NSGETENVIRON
# define environ (*_NSGetEnviron())
#else
extern char **environ;
#endif
END_C_DECLS
#endif /* PMIX_ENVIRON */

View File

@@ -0,0 +1,54 @@
/*
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2006 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2015-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2021-2023 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
#ifndef PMIX_UTIL_ERROR_H
#define PMIX_UTIL_ERROR_H
#include "src/include/pmix_config.h"
#include "pmix.h"
#include "src/util/pmix_output.h"
BEGIN_C_DECLS
/* define a starting point for PMIx internal error codes
* that are never exposed outside the library */
#define PMIX_INTERNAL_ERR_BASE -1330
/**** PMIX ERROR CONSTANTS ****/
/* internal error codes - never exposed outside of the library */
#define PMIX_ERR_FABRIC_NOT_PARSEABLE -1363
#define PMIX_ERR_TAKE_NEXT_OPTION -1366
#define PMIX_ERR_TEMP_UNAVAILABLE -1367
#define PMIX_INTERNAL_ERR_DONE -2000
#define PMIX_ERROR_LOG(r) \
do { \
if (PMIX_ERR_SILENT != (r)) { \
pmix_output(0, "PMIX ERROR: %s in file %s at line %d", PMIx_Error_string((r)), \
__FILE__, __LINE__); \
} \
} while (0)
END_C_DECLS
#endif /* PMIX_UTIL_ERROR_H */

View File

@@ -0,0 +1,111 @@
/*
* Copyright (c) 2008-2014 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2009 Sandia National Laboratories. All rights reserved.
* Copyright (c) 2014-2020 Intel, Inc. All rights reserved.
*
* Copyright (c) 2015 Research Organization for Information Science
* and Technology (RIST). All rights reserved.
* Copyright (c) 2021-2022 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
/* @file */
#ifndef PMIX_UTIL_FD_H_
#define PMIX_UTIL_FD_H_
#include "src/include/pmix_config.h"
#include "pmix_common.h"
BEGIN_C_DECLS
/**
* Read a complete buffer from a file descriptor.
*
* @param fd File descriptor
* @param len Number of bytes to read
* @param buffer Pre-allocated buffer (large enough to hold len bytes)
*
* @returns PMIX_SUCCESS upon success.
* @returns PMIX_ERR_TIMEOUT if the fd closes before reading the full amount.
* @returns PMIX_ERR_IN_ERRNO otherwise.
*
* Loop over reading from the fd until len bytes are read or an error
* occurs. EAGAIN and EINTR are transparently handled.
*/
PMIX_EXPORT pmix_status_t pmix_fd_read(int fd, int len, void *buffer);
/**
* Write a complete buffer to a file descriptor.
*
* @param fd File descriptor
* @param len Number of bytes to write
* @param buffer Buffer to write from
*
* @returns PMIX_SUCCESS upon success.
* @returns PMIX_ERR_IN_ERRNO otherwise.
*
* Loop over writing to the fd until len bytes are written or an error
* occurs. EAGAIN and EINTR are transparently handled.
*/
PMIX_EXPORT pmix_status_t pmix_fd_write(int fd, int len, const void *buffer);
/**
* Convenience function to set a file descriptor to be close-on-exec.
*
* @param fd File descriptor
*
* @returns PMIX_SUCCESS upon success (or if the system does not
* support close-on-exec behavior).
* @returns PMIX_ERR_IN_ERRNO otherwise.
*
* This is simply a convenience function because there's a few steps
* to setting a file descriptor to be close-on-exec.
*/
PMIX_EXPORT pmix_status_t pmix_fd_set_cloexec(int fd);
/**
* Convenience function to check if fd point to an accessible regular file.
*
* @param fd File descriptor
*
* @returns true if "fd" points to a regular file.
* @returns false otherwise.
*/
PMIX_EXPORT bool pmix_fd_is_regular(int fd);
/**
* Convenience function to check if fd point to an accessible character device.
*
* @param fd File descriptor
*
* @returns true if "fd" points to a regular file.
* @returns false otherwise.
*/
PMIX_EXPORT bool pmix_fd_is_chardev(int fd);
/**
* Convenience function to check if fd point to an accessible block device.
*
* @param fd File descriptor
*
* @returns true if "fd" points to a regular file.
* @returns false otherwise.
*/
PMIX_EXPORT bool pmix_fd_is_blkdev(int fd);
/**
* Close all open sockets other than stdin/out/err prior to
* exec'ing a new binary
*/
PMIX_EXPORT void pmix_close_open_file_descriptors(int protected_fd);
PMIX_EXPORT const char *pmix_fd_get_peer_name(int fd);
END_C_DECLS
#endif

View File

@@ -0,0 +1,63 @@
/*
* Copyright (c) 2004-2007 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2005 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2019-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2022 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
#ifndef PMIX_FEW_H
#define PMIX_FEW_H
#include "pmix_config.h"
#include "pmix_common.h"
BEGIN_C_DECLS
/**
* Forks, execs, and waits for a subordinate program
*
* @param argv Null-terminated argument vector; argv[0] is the program
* (same as arguments to execvp())
*
* @param status Upon success, will be filled with the return status
* from waitpid(2). The WIF* macros can be used to examine the value
* (see waitpid(2)).
*
* @retval PMIX_SUCCESS If the child launched and exited.
* @retval PMIX_ERROR If a failure occurred, errno should be
* examined for the specific error.
*
* This function forks, execs, and waits for an executable to
* complete. The input argv must be a NULL-terminated array (perhaps
* built with the pmix_arr_*() interface). Upon success, PMIX_SUCCESS
* is returned. This function will wait either until the child
* process has exited or waitpid() returns an error other than EINTR.
*
* Note that a return of PMIX_SUCCESS does \em not imply that the child
* process exited successfully -- it simply indicates that the child
* process exited. The WIF* macros (see waitpid(2)) should be used to
* examine the status to see hold the child exited.
*
* \warning This function should not be called if \c orte_init()
* or \c MPI_Init() have been called. This function is not
* safe in a multi-threaded environment in which a handler
* for \c SIGCHLD has been registered.
*/
PMIX_EXPORT pmix_status_t pmix_few(char *argv[], int *status);
END_C_DECLS
#endif /* PMIX_FEW_H */

View File

@@ -0,0 +1,51 @@
/*
* Copyright (c) 2007-2020 Cisco Systems, Inc. All rights reserved
* Copyright (c) 2019 Intel, Inc. All rights reserved.
* Copyright (c) 2021-2022 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
/**
* @file
*
* Per https://svn.open-mpi.org/trac/ompi/ticket/933, use a
* combination of $PWD and getcwd() to find the current working
* directory.
*/
#ifndef PMIX_GETCWD_H
#define PMIX_GETCWD_H
#include "src/include/pmix_config.h"
BEGIN_C_DECLS
/**
* Per https://svn.open-mpi.org/trac/ompi/ticket/933, use a
* combination of $PWD and getcwd() to find the current working
* directory.
*
* Use $PWD instead of getcwd() a) if $PWD exists and b) is a valid
* synonym for the results from getcwd(). If both of these conditions
* are not met, just fall back and use the results of getcwd().
*
* @param buf Caller-allocated buffer to put the result
* @param size Length of the buf array
*
* @retval PMIX_ERR_OUT_OF_RESOURCE If internal malloc() fails.
* @retval PMIX_ERR_TEMP_OUT_OF_RESOURCE If the supplied buf buffer
* was not long enough to handle the result.
* @retval PMIX_ERR_BAD_PARAM If buf is NULL or size>INT_MAX
* @retval PMIX_ERR_IN_ERRNO If an other error occurred
* @retval PMIX_SUCCESS If all went well and a valid value was placed
* in the buf buffer.
*/
PMIX_EXPORT int pmix_getcwd(char *buf, size_t size);
END_C_DECLS
#endif /* PMIX_GETCWD_H */

View File

@@ -0,0 +1,31 @@
/*
* Copyright (c) 2016-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2021-2022 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
#ifndef PMIX_GETID_H
#define PMIX_GETID_H
#include "src/include/pmix_config.h"
#include "pmix_common.h"
#ifdef HAVE_UNISTD_H
# include <unistd.h>
#endif
#ifdef HAVE_SYS_TYPES_H
# include <sys/types.h>
#endif
BEGIN_C_DECLS
/* lookup the effective uid and gid of a socket */
PMIX_EXPORT pmix_status_t pmix_util_getid(int sd, uid_t *uid, gid_t *gid);
END_C_DECLS
#endif /* PMIX_PRINTF_H */

View File

@@ -0,0 +1,108 @@
/*
* Copyright (c) 2010 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2012 Los Alamos National Security, Inc. All rights reserved.
* Copyright (c) 2014-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2015 Research Organization for Information Science
* and Technology (RIST). All rights reserved.
* Copyright (c) 2021-2022 Nanook Consulting. All rights reserved.
* Copyright (c) 2023 Triad National Security, LLC. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
#ifndef PMIX_HASH_H
#define PMIX_HASH_H
#include "src/include/pmix_config.h"
#include "src/class/pmix_hash_table.h"
#include "src/include/pmix_globals.h"
#include "src/mca/bfrops/bfrops_types.h"
BEGIN_C_DECLS
/* store a value in the given hash table for the specified
* rank index.*/
PMIX_EXPORT pmix_status_t pmix_hash_store(pmix_hash_table_t *table,
pmix_rank_t rank, pmix_kval_t *kin,
pmix_info_t *qualifiers, size_t nquals,
pmix_keyindex_t *kidx);
/* Fetch the value for a specified key and rank from within
* the given hash_table */
PMIX_EXPORT pmix_status_t pmix_hash_fetch(pmix_hash_table_t *table, pmix_rank_t rank,
const char *key,
pmix_info_t *qualifiers, size_t nquals,
pmix_list_t *kvals,
pmix_keyindex_t *kidx);
/* remove the specified key-value from the given hash_table.
* A NULL key will result in removal of all data for the
* given rank. A rank of PMIX_RANK_WILDCARD indicates that
* the specified key is to be removed from the data for all
* ranks in the table. Combining key=NULL with rank=PMIX_RANK_WILDCARD
* will therefore result in removal of all data from the
* table */
PMIX_EXPORT pmix_status_t pmix_hash_remove_data(pmix_hash_table_t *table,
pmix_rank_t rank,
const char *key,
pmix_keyindex_t *kidx);
PMIX_EXPORT void pmix_hash_register_key(uint32_t inid,
pmix_regattr_input_t *ptr,
pmix_keyindex_t *kidx);
PMIX_EXPORT pmix_regattr_input_t* pmix_hash_lookup_key(uint32_t inid,
const char *key,
pmix_keyindex_t *kidx);
#define PMIX_HASH_TRACE_KEY_ACTUAL(s, r, k, id, tbl, v) \
do { \
const char *_k; \
char *_v; \
pmix_regattr_input_t *_p; \
if (NULL == (k) && UINT32_MAX != id) { \
_p = pmix_hash_lookup_key((id), NULL, NULL); \
if (NULL == _p) { \
_k = "KEY NOT FOUND"; \
} else { \
_k = _p->string; \
} \
} else if (NULL != (k)) { \
_k = (k); \
} else { \
_k = NULL; \
} \
if (NULL != _k) { \
if (0 == strcmp((s), _k)) { \
if (NULL != (v)) { \
_v = PMIx_Value_string(v); \
} else { \
_v = strdup("\tValue is NULL"); \
} \
pmix_output(0, "[%s:%s:%d] %s: Rank %s Key %s\n%s\n\n", \
__FILE__, __func__, __LINE__, \
(tbl)->ht_label, PMIX_RANK_PRINT(r), \
PMIx_Get_attribute_name(_k), _v); \
free(_v); \
} \
} \
} while(0)
#define PMIX_HASH_TRACE_KEY(c, r, s, k, id, v, tbl) \
do { \
if (0 == strcasecmp(c, "SERVER") && \
PMIX_PEER_IS_SERVER(pmix_globals.mypeer)) { \
PMIX_HASH_TRACE_KEY_ACTUAL(s, r, k, id, tbl, v); \
} else if (0 == strcasecmp(c, "CLIENT") && \
!PMIX_PEER_IS_SERVER(pmix_globals.mypeer)) { \
PMIX_HASH_TRACE_KEY_ACTUAL(s, r, k, id, tbl, v); \
} \
} while (0)
END_C_DECLS
#endif /* PMIX_HASH_H */

View File

@@ -0,0 +1,241 @@
/*
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2005 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2007 Los Alamos National Security, LLC. All rights
* reserved.
* Copyright (c) 2008 Sun Microsystems, Inc. All rights reserved.
* Copyright (c) 2013 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2016-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2021-2023 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
/* @file */
#ifndef PMIX_PIF_UTIL_
#define PMIX_PIF_UTIL_
#include "src/include/pmix_config.h"
#ifdef HAVE_SYS_TYPES_H
# include <sys/types.h>
#endif
#ifdef HAVE_SYS_SOCKET_H
# include <sys/socket.h>
#endif
#ifdef HAVE_NETINET_IN_H
# include <netinet/in.h>
#endif
#include "pmix_common.h"
#include "src/class/pmix_list.h"
#define PMIX_IF_NAMESIZE 256
BEGIN_C_DECLS
#define PMIX_PIF_FORMAT_ADDR(n) \
(((n) >> 24) & 0x000000FF), (((n) >> 16) & 0x000000FF), (((n) >> 8) & 0x000000FF), \
((n) &0x000000FF)
#define PMIX_PIF_ASSEMBLE_FABRIC(n1, n2, n3, n4) \
(((n1) << 24) & 0xFF000000) | (((n2) << 16) & 0x00FF0000) | (((n3) << 8) & 0x0000FF00) \
| ((n4) &0x000000FF)
typedef struct pmix_pif_t {
pmix_list_item_t super;
char if_name[PMIX_IF_NAMESIZE + 1];
int if_index;
uint16_t if_kernel_index;
uint16_t af_family;
int if_flags;
int if_speed;
struct sockaddr_storage if_addr;
uint32_t if_mask;
uint32_t if_bandwidth;
uint8_t if_mac[6];
int ifmtu; /* Can't use if_mtu because of a
#define collision on some BSDs */
} pmix_pif_t;
PMIX_EXPORT PMIX_CLASS_DECLARATION(pmix_pif_t);
/* "global" list of available interfaces */
PMIX_EXPORT extern pmix_list_t pmix_if_list;
/* global flags */
PMIX_EXPORT extern bool pmix_if_do_not_resolve;
PMIX_EXPORT extern bool pmix_if_retain_loopback;
/**
* Lookup an interface by address and return its name.
*
* @param if_addr (IN) Interface address (hostname or dotted-quad)
* @param if_name (OUT) Interface name buffer
* @param size (IN) Interface name buffer size
*/
PMIX_EXPORT int pmix_ifaddrtoname(const char *if_addr, char *if_name, int size);
/**
* Lookup an interface by name and return its pmix_list index.
*
* @param if_name (IN) Interface name
* @return Interface pmix_list index
*/
PMIX_EXPORT int pmix_ifnametoindex(const char *if_name);
/**
* Lookup an interface by name and return its kernel index.
*
* @param if_name (IN) Interface name
* @return Interface kernel index
*/
PMIX_EXPORT int16_t pmix_ifnametokindex(const char *if_name);
/*
* Attempt to resolve an address (given as either IPv4/IPv6 string
* or hostname) and return the kernel index of the interface
* that is on the same network as the specified address
*/
PMIX_EXPORT int16_t pmix_ifaddrtokindex(const char *if_addr);
/**
* Lookup an interface by pmix_list index and return its kernel index.
*
* @param if_name (IN) Interface pmix_list index
* @return Interface kernel index
*/
PMIX_EXPORT int pmix_ifindextokindex(int if_index);
/**
* Returns the number of available interfaces.
*/
PMIX_EXPORT int pmix_ifcount(void);
/**
* Returns the index of the first available interface.
*/
PMIX_EXPORT int pmix_ifbegin(void);
/**
* Lookup the current position in the interface list by
* index and return the next available index (if it exists).
*
* @param if_index Returns the next available index from the
* current position.
*/
PMIX_EXPORT int pmix_ifnext(int if_index);
/**
* Lookup an interface by index and return its name.
*
* @param if_index (IN) Interface index
* @param if_name (OUT) Interface name buffer
* @param size (IN) Interface name buffer size
*/
PMIX_EXPORT int pmix_ifindextoname(int if_index, char *if_name, int);
/**
* Lookup an interface by kernel index and return its name.
*
* @param if_index (IN) Interface kernel index
* @param if_name (OUT) Interface name buffer
* @param size (IN) Interface name buffer size
*/
PMIX_EXPORT int pmix_ifkindextoname(int if_kindex, char *if_name, int);
/**
* Lookup an interface by index and return its primary address.
*
* @param if_index (IN) Interface index
* @param if_name (OUT) Interface address buffer
* @param size (IN) Interface address buffer size
*/
PMIX_EXPORT int pmix_ifindextoaddr(int if_index, struct sockaddr *, unsigned int);
PMIX_EXPORT int pmix_ifkindextoaddr(int if_kindex, struct sockaddr *if_addr, unsigned int length);
/**
* Lookup an interface by index and return its network mask (in CIDR
* notation -- NOT the actual netmask itself!).
*
* @param if_index (IN) Interface index
* @param if_name (OUT) Interface address buffer
* @param size (IN) Interface address buffer size
*/
PMIX_EXPORT int pmix_ifindextomask(int if_index, uint32_t *, int);
/**
* Lookup an interface by index and return its MAC address.
*
* @param if_index (IN) Interface index
* @param if_mac (OUT) Interface's MAC address
*/
PMIX_EXPORT int pmix_ifindextomac(int if_index, uint8_t if_mac[6]);
/**
* Lookup an interface by index and return its MTU.
*
* @param if_index (IN) Interface index
* @param if_mtu (OUT) Interface's MTU
*/
PMIX_EXPORT int pmix_ifindextomtu(int if_index, int *mtu);
/**
* Lookup an interface by index and return its flags.
*
* @param if_index (IN) Interface index
* @param if_flags (OUT) Interface flags
*/
PMIX_EXPORT int pmix_ifindextoflags(int if_index, uint32_t *);
/**
* Determine if given hostname / IP address is a local address
*
* @param hostname (IN) Hostname (or stringified IP address)
* @return true if \c hostname is local, false otherwise
*/
PMIX_EXPORT bool pmix_ifislocal(const char *hostname);
/**
* Convert a dot-delimited network tuple to an IP address
*
* @param addr (IN) character string tuple
* @param net (IN) Pointer to returned network address
* @param mask (IN) Pointer to returned netmask
* @return PMIX_SUCCESS if no problems encountered
* @return PMIX_ERROR if data could not be released
*/
PMIX_EXPORT int pmix_iftupletoaddr(const char *addr, uint32_t *net, uint32_t *mask);
/**
* Determine if given interface is loopback
*
* @param if_index (IN) Interface index
*/
PMIX_EXPORT bool pmix_ifisloopback(int if_index);
/*
* Determine if a specified interface is included in a NULL-terminated argv array
*/
PMIX_EXPORT int pmix_ifmatches(int kidx, char **nets);
/*
* Provide a list of strings that contain all known aliases for this node
*/
PMIX_EXPORT void pmix_ifgetaliases(char ***aliases);
END_C_DECLS
#endif

View File

@@ -0,0 +1,62 @@
/*
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2005 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2016-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2021-2022 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
/** @file */
#ifndef PMIX_UTIL_KEYVAL_PARSE_H
#define PMIX_UTIL_KEYVAL_PARSE_H
#include "src/include/pmix_config.h"
BEGIN_C_DECLS
PMIX_EXPORT extern int pmix_util_keyval_parse_lineno;
/**
* Callback triggered for each key = value pair
*
* Callback triggered from pmix_util_keyval_parse for each key = value
* pair. Both key and value will be pointers into static buffers.
* The buffers must not be free()ed and contents may be overwritten
* immediately after the callback returns.
*/
typedef void (*pmix_keyval_parse_fn_t)(const char *file, int lineno,
const char *name,
const char *value);
/**
* Parse \c filename, made up of key = value pairs.
*
* Parse \c filename, made up of key = value pairs. For each line
* that appears to contain a key = value pair, \c callback will be
* called exactly once. In a multithreaded context, calls to
* pmix_util_keyval_parse() will serialize multiple calls.
*/
PMIX_EXPORT int pmix_util_keyval_parse(const char *filename, pmix_keyval_parse_fn_t callback);
PMIX_EXPORT int pmix_util_keyval_parse_init(void);
PMIX_EXPORT void pmix_util_keyval_parse_finalize(void);
PMIX_EXPORT int pmix_util_keyval_save_internal_envars(pmix_keyval_parse_fn_t callback);
END_C_DECLS
#endif

View File

@@ -0,0 +1,62 @@
/*
* Copyright (c) 2004-2008 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2011 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2010 Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 2014-2016 Research Organization for Information Science
* and Technology (RIST). All rights reserved.
* Copyright (c) 2018-2020 Intel, Inc. All rights reserved.
* Copyright (c) 2021-2022 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
#ifndef _PMIX_NAME_FNS_H_
#define _PMIX_NAME_FNS_H_
#include "src/include/pmix_config.h"
#ifdef HAVE_STDINT_h
# include <stdint.h>
#endif
#include "pmix_common.h"
BEGIN_C_DECLS
/* define an internal-only process name that has
* a dynamically-sized nspace field to save memory */
typedef struct {
char *nspace;
pmix_rank_t rank;
} pmix_name_t;
#define PMIX_CHECK_NAMES(a, b) \
(PMIX_CHECK_NSPACE((a)->nspace, (b)->nspace) && ((a)->rank == (b)->rank || (PMIX_RANK_WILDCARD == (a)->rank || PMIX_RANK_WILDCARD == (b)->rank)))
/* useful define to print name args in output messages */
PMIX_EXPORT char *pmix_util_print_name_args(const pmix_proc_t *name);
#define PMIX_NAME_PRINT(n) pmix_util_print_name_args(n)
PMIX_EXPORT char *pmix_util_print_pname_args(const pmix_name_t *name);
#define PMIX_PNAME_PRINT(n) pmix_util_print_pname_args(n)
PMIX_EXPORT char *pmix_util_print_rank(const pmix_rank_t vpid);
#define PMIX_RANK_PRINT(n) pmix_util_print_rank(n)
#define PMIX_PEER_PRINT(p) pmix_util_print_pname_args(&(p)->info->pname)
PMIX_EXPORT int pmix_util_compare_proc(const void *a, const void *b);
END_C_DECLS
#endif

View File

@@ -0,0 +1,155 @@
/*
* Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana
* University Research and Technology
* Corporation. All rights reserved.
* Copyright (c) 2004-2005 The University of Tennessee and The University
* of Tennessee Research Foundation. All rights
* reserved.
* Copyright (c) 2004-2005 High Performance Computing Center Stuttgart,
* University of Stuttgart. All rights reserved.
* Copyright (c) 2004-2005 The Regents of the University of California.
* All rights reserved.
* Copyright (c) 2007 Los Alamos National Security, LLC. All rights
* reserved.
* Copyright (c) 2017 Intel, Inc. All rights reserved.
* Copyright (c) 2021-2022 Nanook Consulting. All rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*/
/* @file */
#ifndef PMIX_UTIL_NET_H
#define PMIX_UTIL_NET_H
#include "src/include/pmix_config.h"
#ifdef HAVE_SYS_TYPES_H
# include <sys/types.h>
#endif
#ifdef HAVE_SYS_SOCKET_H
# include <sys/socket.h>
#endif
#ifdef HAVE_NETINET_IN_H
# include <netinet/in.h>
#endif
#include "pmix_common.h"
BEGIN_C_DECLS
/**
* Initialize the network helper subsystem
*
* Initialize the network helper subsystem. Should be called exactly
* once for any process that will use any function in the network
* helper subsystem.
*
* @retval PMIX_SUCCESS Success
* @retval PMIX_ERR_TEMP_OUT_OF_RESOURCE Not enough memory for static
* buffer creation
*/
PMIX_EXPORT int pmix_net_init(void);
/**
* Finalize the network helper subsystem
*
* Finalize the network helper subsystem. Should be called exactly
* once for any process that will use any function in the network
* helper subsystem.
*
* @retval PMIX_SUCCESS Success
*/
PMIX_EXPORT int pmix_net_finalize(void);
/**
* Calculate netmask in network byte order from CIDR notation
*
* @param prefixlen (IN) CIDR prefixlen
* @return netmask in network byte order
*/
PMIX_EXPORT uint32_t pmix_net_prefix2netmask(uint32_t prefixlen);
/**
* Determine if given IP address is in the localhost range
*
* Determine if the given IP address is in the localhost range
* (127.0.0.0/8), meaning that it can't be used to connect to machines
* outside the current host.
*
* @param addr struct sockaddr_in of IP address
* @return true if \c addr is a localhost address,
* false otherwise.
*/
PMIX_EXPORT bool pmix_net_islocalhost(const struct sockaddr *addr);
/**
* Are we on the same network?
*
* For IPv6, we only need to check for /64, there are no other
* local netmasks.
*
* @param addr1 struct sockaddr of address
* @param addr2 struct sockaddr of address
* @param prefixlen netmask (either CIDR or IPv6 prefixlen)
* @return true if \c addr1 and \c addr2 are on the
* same net, false otherwise.
*/
PMIX_EXPORT bool pmix_net_samenetwork(const struct sockaddr_storage *addr1,
const struct sockaddr_storage *addr2,
uint32_t prefixlen);
/**
* Is the given address a link-local IPv6 address? Returns false for IPv4
* address.
*
* @param addr address as struct sockaddr
* @return true, if \c addr is IPv6 link-local, false otherwise
*/
PMIX_EXPORT bool pmix_net_addr_isipv6linklocal(const struct sockaddr *addr);
/**
* Is the given address a public IPv4 address? Returns false for IPv6
* address.
*
* @param addr address as struct sockaddr
* @return true, if \c addr is IPv4 public, false otherwise
*/
PMIX_EXPORT bool pmix_net_addr_isipv4public(const struct sockaddr *addr);
/**
* Get string version of address
*
* Return the un-resolved address in a string format. The string will
* be returned in a per-thread static buffer and should not be freed
* by the user.
*
* @param addr struct sockaddr of address
* @return literal representation of \c addr
*/
PMIX_EXPORT char *pmix_net_get_hostname(const struct sockaddr *addr);
/**
* Get port number from struct sockaddr
*
* Return the port number (as an integr) from either a struct
* sockaddr_in or a struct sockaddr_in6.
*
* @param addr struct sockaddr containing address
* @return port number from \addr
*/
PMIX_EXPORT int pmix_net_get_port(const struct sockaddr *addr);
/**
* Test if a string is actually an IP address
*
* Returns true if the string is of IPv4 or IPv6 address form
*/
PMIX_EXPORT bool pmix_net_isaddr(const char *name);
END_C_DECLS
#endif /* PMIX_UTIL_NET_H */

Some files were not shown because too many files have changed in this diff Show More