gcc/libcilkrts/include/cilk/cilk_api.h

425 lines
14 KiB
C
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

/* cilk_api.h
*
* @copyright
* Copyright (C) 2009-2013, Intel Corporation
* All rights reserved.
*
* @copyright
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
*
* * Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* * Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in
* the documentation and/or other materials provided with the
* distribution.
* * Neither the name of Intel Corporation nor the names of its
* contributors may be used to endorse or promote products derived
* from this software without specific prior written permission.
*
* @copyright
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
* LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
* A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
* HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
* INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
* BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
* OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
* AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY
* WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
* POSSIBILITY OF SUCH DAMAGE.
*/
/** @file cilk_api.h
*
* @brief Defines the documented API exposed by the Cilk Plus for use
* by applications.
*
* @ingroup api
*/
#ifndef INCLUDED_CILK_API_H
#define INCLUDED_CILK_API_H
/** @defgroup api Runtime API
* API to allow user programs to interact with the Cilk runtime.
* @{
*/
#ifndef CILK_STUB /* Real (non-stub) definitions */
#if ! defined(__cilk) && ! defined(USE_CILK_API)
# ifdef _WIN32
# error Cilk API is being used with non-Cilk compiler (or Cilk is disabled)
# else
# warning Cilk API is being used with non-Cilk compiler (or Cilk is disabled)
# endif
#endif
#include <cilk/common.h>
#ifdef __cplusplus
# include <cstddef> /* Defines size_t */
#else
# include <stddef.h> /* Defines size_t */
#endif
#ifdef _WIN32
# ifndef IN_CILK_RUNTIME
/* Ensure the library is brought if any of these functions are being called. */
# pragma comment(lib, "cilkrts")
# endif
# ifndef __cplusplus
# include <wchar.h>
# endif
#endif /* _WIN32 */
__CILKRTS_BEGIN_EXTERN_C
/** Return values from __cilkrts_set_param() and __cilkrts_set_param_w()
*/
enum __cilkrts_set_param_status {
__CILKRTS_SET_PARAM_SUCCESS = 0, /**< Success - parameter set */
__CILKRTS_SET_PARAM_UNIMP = 1, /**< Unimplemented parameter */
__CILKRTS_SET_PARAM_XRANGE = 2, /**< Parameter value out of range */
__CILKRTS_SET_PARAM_INVALID = 3, /**< Invalid parameter value */
__CILKRTS_SET_PARAM_LATE = 4 /**< Too late to change parameter value */
};
/** Set user controllable runtime parameters
*
* Call this function to set runtime parameters that control the behavior
* of the Cilk scheduler.
*
* @param param A string specifying the parameter to be set. One of:
* - `"nworkers"`
* - `"force reduce"`
* @param value A string specifying the parameter value.
* @returns A value from the @ref __cilkrts_set_param_status
* enumeration indicating the result of the operation.
*
* @par The "nworkers" parameter
*
* This parameter specifies the number of worker threads to be created by the
* Cilk runtime. @a Value must be a string of digits to be parsed by
* `strtol()`.
*
* The number of worker threads is:
* 1. the value set with `__cilkrts_set_param("nworkers")`, if it is
* positive; otherwise,
* 2. the value of the CILK_NWORKERS environment variable, if it is
* defined; otherwise
* 3. the number of cores available, as reported by the operating system.
*
* @note
* Technically, Cilk distinguishes between the _user thread_ (the thread that
* the user code was executing on when the Cilk runtime started), and
* _worker threads_ (new threads created by the Cilk runtime to support
* Cilk parallelism). `nworkers` actually includes both the user thread and
* the worker threads; that is, it is one greater than the number of true
* “worker threads”.
*
* @note
* Setting `nworkers = 1` produces serial behavior. Cilk spawns and syncs will
* be executed, but with only one worker, continuations will never be stolen,
* so all code will execute in serial.
*
* @warning
* The number of worker threads can only be set *before* the runtime has
* started. Attempting to set it when the runtime is running will have no
* effect, and will return an error code. You can call __cilkrts_end_cilk()
* to shut down the runtime to change the number of workers.
*
* @warning
* The default Cilk scheduler behavior is usually pretty good. The ability
* to override `nworkers` can be useful for experimentation, but it wont
* usually be necessary for getting good performance.
*
* @par The "force reduce" parameter
*
* This parameter controls whether the runtime should allocate a new view
* for a reducer for every parallel strand that it is accessed on. (See
* @ref pagereducers.) @a Value must be `"1"` or `"true"` to enable the
* “force reduce” behavior, or `"0"` or `"false"` to disable it.
*
* “Force reduce” behavior will also be enabled if
* `__cilkrts_set_param("force reduce")` is not called, but the
* `CILK_FORCE_REDUCE` environment variable is defined.
*
* @warning
* When this option is enabled, `nworkers` should be set to `1`. Using “force
* reduce” with more than one worker may result in runtime errors.
*
* @warning
* Enabling this option can significantly reduce performance. It should
* _only_ be used as a debugging tool.
*/
CILK_API(int) __cilkrts_set_param(const char *param, const char *value);
#ifdef _WIN32
/**
* Set user controllable parameters using wide strings
*
* @note This variant of __cilkrts_set_param() is only available
* on Windows.
*
* @copydetails __cilkrts_set_param
*/
CILK_API(int) __cilkrts_set_param_w(const wchar_t *param, const wchar_t *value);
#endif
/** Shut down and deallocate all Cilk state. The runtime will abort the
* application if Cilk is still in use by this thread. Otherwise the runtime
* will wait for all other threads using Cilk to exit.
*/
CILK_API(void) __cilkrts_end_cilk(void);
/** Initialize the Cilk data structures and start the runtime.
*/
CILK_API(void) __cilkrts_init(void);
/** Return the runtime `nworkers` parameter. (See the discussion of `nworkers`
* in the documentation for __cilkrts_set_param().)
*/
CILK_API(int) __cilkrts_get_nworkers(void);
/** Return the number of thread data structures.
*
* This function returns the number of data structures that has been allocated
* allocated by the runtime to hold information about user and worker threads.
*
* If you dont already know what this is good for, then you probably dont
* need it.
*/
CILK_API(int) __cilkrts_get_total_workers(void);
/** What thread is the function running on?
*
* Return a small integer identifying the current thread. Each worker thread
* started by the Cilk runtime library has a unique worker number in the range
* `1 .. nworkers - 1`.
*
* All _user_ threads (threads started by the user, or by other libraries) are
* identified as worker number 0. Therefore, the worker number is not unique
* across multiple user threads.
*/
CILK_API(int) __cilkrts_get_worker_number(void);
/** Test whether “force reduce” behavior is enabled.
*
* @return Non-zero if force-reduce mode is on, zero if it is off.
*/
CILK_API(int) __cilkrts_get_force_reduce(void);
/** Interact with tools
*/
CILK_API(void)
__cilkrts_metacall(unsigned int tool, unsigned int code, void *data);
#ifdef _WIN32
/// Windows exception description record.
typedef struct _EXCEPTION_RECORD _EXCEPTION_RECORD;
/** Function signature for Windows exception notification callbacks.
*/
typedef void (*__cilkrts_pfn_seh_callback)(const _EXCEPTION_RECORD *exception);
/** Specify a function to call when a non-C++ exception is caught.
*
* Cilk Plus parallelism plays nicely with C++ exception handling, but the
* Cilk Plus runtime has no way to unwind the stack across a strand boundary
* for Microsoft SEH (“Structured Exception Handling”) exceptions. Therefore,
* when the runtime catches such an exception, it must abort the application.
*
* If an SEH callback has been set, the runtime will call it before aborting.
*
* @param pfn A pointer to a callback function to be called before the
* runtime aborts the program because of an SEH exception.
*/
CILK_API(int) __cilkrts_set_seh_callback(__cilkrts_pfn_seh_callback pfn);
#endif /* _WIN32 */
#if __CILKRTS_ABI_VERSION >= 1
/* Pedigree API is available only for compilers that use ABI version >= 1. */
/** @name Pedigrees
*/
//@{
// @cond internal
/** Support for __cilkrts_get_pedigree.
*/
CILK_API(__cilkrts_pedigree)
__cilkrts_get_pedigree_internal(__cilkrts_worker *w);
/** Support for __cilkrts_bump_worker_rank.
*/
CILK_API(int)
__cilkrts_bump_worker_rank_internal(__cilkrts_worker* w);
/// @endcond
/** Get the current pedigree, in a linked list representation.
*
* This routine returns a copy of the last node in the pedigree list.
* For example, if the current pedigree (in order) is <1, 2, 3, 4>,
* then this method returns a node with rank == 4, and whose parent
* field points to the node with rank of 3. In summary, following the
* nodes in the chain visits the terms of the pedigree in reverse.
*
* The returned node is guaranteed to be valid only until the caller
* of this routine has returned.
*/
__CILKRTS_INLINE
__cilkrts_pedigree __cilkrts_get_pedigree(void)
{
return __cilkrts_get_pedigree_internal(__cilkrts_get_tls_worker());
}
/** Context used by __cilkrts_get_pedigree_info.
*
* @deprecated
* This data structure is only used by the deprecated
* __cilkrts_get_pedigree_info function.
*
* Callers should initialize the `data` array to NULL and set the `size`
* field to `sizeof(__cilkrts_pedigree_context_t)` before the first call
* to __cilkrts_get_pedigree_info(), and should not examine or modify it
* thereafter.
*/
typedef struct
{
__STDNS size_t size; /**< Size of the struct in bytes */
void *data[3]; /**< Opaque context data */
} __cilkrts_pedigree_context_t;
/** Get pedigree information.
*
* @deprecated
* Use __cilkrts_get_pedigree() instead.
*
* This routine allows code to walk up the stack of Cilk frames to gather
* the pedigree.
*
* Initialize the pedigree walk by filling the pedigree context with NULLs
* and setting the size field to sizeof(__cilkrts_pedigree_context).
* Other than initialization to NULL to start the walk, user coder should
* consider the pedigree context data opaque and should not examine or
* modify it.
*
* @returns 0 - Success - birthrank is valid
* @returns >0 - End of pedigree walk
* @returns -1 - Failure - No worker bound to thread
* @returns -2 - Failure - Sanity check failed,
* @returns -3 - Failure - Invalid context size
* @returns -4 - Failure - Internal error - walked off end of chain of frames
*/
CILK_API(int)
__cilkrts_get_pedigree_info(/* In/Out */ __cilkrts_pedigree_context_t *context,
/* Out */ uint64_t *sf_birthrank);
/** Get the rank of the currently executing worker.
*
* @deprecated
* Use `__cilkrts_get_pedigree().rank` instead.
*
* @returns 0 - Success - *rank is valid
* @returns <0 - Failure - *rank is not changed
*/
CILK_EXPORT_AND_INLINE
int __cilkrts_get_worker_rank(uint64_t *rank)
{
*rank = __cilkrts_get_pedigree().rank;
return 0;
}
/** Increment the pedigree rank of the currently executing worker.
*
* @returns 0 - Success - rank was incremented
* @returns-1 - Failure
*/
CILK_EXPORT_AND_INLINE
int __cilkrts_bump_worker_rank(void)
{
return __cilkrts_bump_worker_rank_internal(__cilkrts_get_tls_worker());
}
/** Increment the pedigree rank for a cilk_for loop.
* Obsolete.
*
* @deprecated
* This function was provided to allow the user to manipulate the pedigree
* rank of a `cilk_for` loop. The compiler now generates code to do that
* manipulation automatically, so this function is now unnecessary. It may
* be called, but will have no effect.
*/
CILK_EXPORT_AND_INLINE
int __cilkrts_bump_loop_rank(void)
{
return 0;
}
//@}
#endif /* __CILKRTS_ABI_VERSION >= 1 */
__CILKRTS_END_EXTERN_C
#else /* CILK_STUB */
// Programs compiled with CILK_STUB are not linked with the Cilk runtime
// library, so they should not have external references to runtime functions.
// Therefore, the functions are replaced with stubs.
#ifdef _WIN32
#define __cilkrts_set_param_w(name,value) ((value), 0)
#define __cilkrts_set_seh_callback(pfn) (0)
#endif
#define __cilkrts_set_param(name,value) ((value), 0)
#define __cilkrts_end_cilk() ((void) 0)
#define __cilkrts_init() ((void) 0)
#define __cilkrts_get_nworkers() (1)
#define __cilkrts_get_total_workers() (1)
#define __cilkrts_get_worker_number() (0)
#define __cilkrts_get_force_reduce() (0)
#define __cilkrts_metacall(tool,code,data) ((tool), (code), (data), 0)
#if __CILKRTS_ABI_VERSION >= 1
/* Pedigree stubs */
#define __cilkrts_get_pedigree_info(context, sf_birthrank) (-1)
#define __cilkrts_get_worker_rank(rank) (*(rank) = 0)
#define __cilkrts_bump_worker_rank() (-1)
#define __cilkrts_bump_loop_rank() (-1)
/*
* A stub method for __cilkrts_get_pedigree.
* Returns an empty __cilkrts_pedigree.
*/
__CILKRTS_INLINE
__cilkrts_pedigree __cilkrts_get_pedigree_stub(void)
{
__cilkrts_pedigree ans;
ans.rank = 0;
ans.parent = NULL;
return ans;
}
/* Renamed to an actual stub method. */
#define __cilkrts_get_pedigree() __cilkrts_get_pedigree_stub()
#endif /* __CILKRTS_ABI_VERSION >= 1 */
#endif /* CILK_STUB */
//@}
#endif /* INCLUDED_CILK_API_H */