From 45be8d67be0083c923ca31e4803de861177a2383 Mon Sep 17 00:00:00 2001 From: Martin Panter Date: Tue, 8 Dec 2015 00:03:20 +0000 Subject: Issue #25701: Document C API functions that both set and delete objects Also document that the separate functions that delete objects are preferred; using PyObject_SetAttr(), _SetAttrString(), and PySequence_SetItem() to delete is deprecated. --- Doc/c-api/object.rst | 27 +++++++++++++++++++-------- Doc/c-api/sequence.rst | 6 +++++- Doc/c-api/typeobj.rst | 26 ++++++++++++++++---------- Include/abstract.h | 20 ++++++++++---------- 4 files changed, 50 insertions(+), 29 deletions(-) diff --git a/Doc/c-api/object.rst b/Doc/c-api/object.rst index 97b45b1..b761c80 100644 --- a/Doc/c-api/object.rst +++ b/Doc/c-api/object.rst @@ -68,25 +68,35 @@ Object Protocol .. c:function:: int PyObject_SetAttr(PyObject *o, PyObject *attr_name, PyObject *v) Set the value of the attribute named *attr_name*, for object *o*, to the value - *v*. Returns ``-1`` on failure. This is the equivalent of the Python statement + *v*. Raise an exception and return ``-1`` on failure; + return ``0`` on success. This is the equivalent of the Python statement ``o.attr_name = v``. + If *v* is *NULL*, the attribute is deleted, however this feature is + deprecated in favour of using :c:func:`PyObject_DelAttr`. + .. c:function:: int PyObject_SetAttrString(PyObject *o, const char *attr_name, PyObject *v) Set the value of the attribute named *attr_name*, for object *o*, to the value - *v*. Returns ``-1`` on failure. This is the equivalent of the Python statement + *v*. Raise an exception and return ``-1`` on failure; + return ``0`` on success. This is the equivalent of the Python statement ``o.attr_name = v``. + If *v* is *NULL*, the attribute is deleted, however this feature is + deprecated in favour of using :c:func:`PyObject_DelAttrString`. + .. c:function:: int PyObject_GenericSetAttr(PyObject *o, PyObject *name, PyObject *value) - Generic attribute setter function that is meant to be put into a type - object's ``tp_setattro`` slot. It looks for a data descriptor in the + Generic attribute setter and deleter function that is meant + to be put into a type object's :c:member:`~PyTypeObject.tp_setattro` + slot. It looks for a data descriptor in the dictionary of classes in the object's MRO, and if found it takes preference - over setting the attribute in the instance dictionary. Otherwise, the - attribute is set in the object's :attr:`~object.__dict__` (if present). - Otherwise, an :exc:`AttributeError` is raised and ``-1`` is returned. + over setting or deleting the attribute in the instance dictionary. Otherwise, the + attribute is set or deleted in the object's :attr:`~object.__dict__` (if present). + On success, ``0`` is returned, otherwise an :exc:`AttributeError` + is raised and ``-1`` is returned. .. c:function:: int PyObject_DelAttr(PyObject *o, PyObject *attr_name) @@ -378,7 +388,8 @@ Object Protocol .. c:function:: int PyObject_SetItem(PyObject *o, PyObject *key, PyObject *v) - Map the object *key* to the value *v*. Returns ``-1`` on failure. This is the + Map the object *key* to the value *v*. Raise an exception and + return ``-1`` on failure; return ``0`` on success. This is the equivalent of the Python statement ``o[key] = v``. diff --git a/Doc/c-api/sequence.rst b/Doc/c-api/sequence.rst index 5960db9..f1825f0 100644 --- a/Doc/c-api/sequence.rst +++ b/Doc/c-api/sequence.rst @@ -62,10 +62,14 @@ Sequence Protocol .. c:function:: int PySequence_SetItem(PyObject *o, Py_ssize_t i, PyObject *v) - Assign object *v* to the *i*\ th element of *o*. Returns ``-1`` on failure. This + Assign object *v* to the *i*\ th element of *o*. Raise an exception + and return ``-1`` on failure; return ``0`` on success. This is the equivalent of the Python statement ``o[i] = v``. This function *does not* steal a reference to *v*. + If *v* is *NULL*, the element is deleted, however this feature is + deprecated in favour of using :c:func:`PySequence_DelItem`. + .. c:function:: int PySequence_DelItem(PyObject *o, Py_ssize_t i) diff --git a/Doc/c-api/typeobj.rst b/Doc/c-api/typeobj.rst index b5113aa..ac589b8 100644 --- a/Doc/c-api/typeobj.rst +++ b/Doc/c-api/typeobj.rst @@ -208,12 +208,13 @@ type objects) *must* have the :attr:`ob_size` field. .. c:member:: setattrfunc PyTypeObject.tp_setattr - An optional pointer to the set-attribute-string function. + An optional pointer to the function for setting and deleting attributes. This field is deprecated. When it is defined, it should point to a function that acts the same as the :c:member:`~PyTypeObject.tp_setattro` function, but taking a C string instead of a Python string object to give the attribute name. The signature is - the same as for :c:func:`PyObject_SetAttrString`. + the same as for :c:func:`PyObject_SetAttrString`, but setting + *v* to *NULL* to delete an attribute must be supported. This field is inherited by subtypes together with :c:member:`~PyTypeObject.tp_setattro`: a subtype inherits both :c:member:`~PyTypeObject.tp_setattr` and :c:member:`~PyTypeObject.tp_setattro` from its base type when @@ -351,9 +352,10 @@ type objects) *must* have the :attr:`ob_size` field. .. c:member:: setattrofunc PyTypeObject.tp_setattro - An optional pointer to the set-attribute function. + An optional pointer to the function for setting and deleting attributes. - The signature is the same as for :c:func:`PyObject_SetAttr`. It is usually + The signature is the same as for :c:func:`PyObject_SetAttr`, but setting + *v* to *NULL* to delete an attribute must be supported. It is usually convenient to set this field to :c:func:`PyObject_GenericSetAttr`, which implements the normal way of setting object attributes. @@ -724,7 +726,7 @@ type objects) *must* have the :attr:`ob_size` field. typedef struct PyGetSetDef { char *name; /* attribute name */ getter get; /* C function to get the attribute */ - setter set; /* C function to set the attribute */ + setter set; /* C function to set or delete the attribute */ char *doc; /* optional doc string */ void *closure; /* optional additional data for getter and setter */ } PyGetSetDef; @@ -775,12 +777,14 @@ type objects) *must* have the :attr:`ob_size` field. .. c:member:: descrsetfunc PyTypeObject.tp_descr_set - An optional pointer to a "descriptor set" function. + An optional pointer to a function for setting and deleting + a descriptor's value. The function signature is :: int tp_descr_set(PyObject *self, PyObject *obj, PyObject *value); + The *value* argument is set to *NULL* to delete the value. This field is inherited by subtypes. .. XXX explain. @@ -1171,9 +1175,11 @@ Mapping Object Structures .. c:member:: objobjargproc PyMappingMethods.mp_ass_subscript - This function is used by :c:func:`PyObject_SetItem` and has the same - signature. If this slot is *NULL*, the object does not support item - assignment. + This function is used by :c:func:`PyObject_SetItem` and + :c:func:`PyObject_DelItem`. It has the same signature as + :c:func:`PyObject_SetItem`, but *v* can also be set to *NULL* to delete + an item. If this slot is *NULL*, the object does not support item + assignment and deletion. .. _sequence-structs: @@ -1222,7 +1228,7 @@ Sequence Object Structures This function is used by :c:func:`PySequence_SetItem` and has the same signature. This slot may be left to *NULL* if the object does not support - item assignment. + item assignment and deletion. .. c:member:: objobjproc PySequenceMethods.sq_contains diff --git a/Include/abstract.h b/Include/abstract.h index 6afba09..48b29a7 100644 --- a/Include/abstract.h +++ b/Include/abstract.h @@ -192,8 +192,8 @@ xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx*/ int PyObject_SetAttrString(PyObject *o, const char *attr_name, PyObject *v); Set the value of the attribute named attr_name, for object o, - to the value, v. Returns -1 on failure. This is - the equivalent of the Python statement: o.attr_name=v. + to the value v. Raise an exception and return -1 on failure; return 0 on + success. This is the equivalent of the Python statement o.attr_name=v. */ @@ -202,8 +202,8 @@ xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx*/ int PyObject_SetAttr(PyObject *o, PyObject *attr_name, PyObject *v); Set the value of the attribute named attr_name, for object o, - to the value, v. Returns -1 on failure. This is - the equivalent of the Python statement: o.attr_name=v. + to the value v. Raise an exception and return -1 on failure; return 0 on + success. This is the equivalent of the Python statement o.attr_name=v. */ @@ -435,9 +435,9 @@ xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx*/ PyAPI_FUNC(int) PyObject_SetItem(PyObject *o, PyObject *key, PyObject *v); /* - Map the object, key, to the value, v. Returns - -1 on failure. This is the equivalent of the Python - statement: o[key]=v. + Map the object key to the value v. Raise an exception and return -1 + on failure; return 0 on success. This is the equivalent of the Python + statement o[key]=v. */ PyAPI_FUNC(int) PyObject_DelItemString(PyObject *o, const char *key); @@ -993,9 +993,9 @@ xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx*/ PyAPI_FUNC(int) PySequence_SetItem(PyObject *o, Py_ssize_t i, PyObject *v); /* - Assign object v to the ith element of o. Returns - -1 on failure. This is the equivalent of the Python - statement: o[i]=v. + Assign object v to the ith element of o. Raise an exception and return + -1 on failure; return 0 on success. This is the equivalent of the + Python statement o[i]=v. */ PyAPI_FUNC(int) PySequence_DelItem(PyObject *o, Py_ssize_t i); -- cgit v0.12 ='n59' href='#n59'>59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249 250 251 252 253 254 255 256 257 258 259 260 261 262 263 264 265 266 267 268 269 270 271 272 273 274 275 276 277 278 279 280 281 282 283 284 285 286 287 288 289 290 291 292 293 294 295 296 297 298 299 300 301 302 303 304 305 306
/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
 * Copyright by The HDF Group.                                               *
 * All rights reserved.                                                      *
 *                                                                           *
 * This file is part of HDF5.  The full HDF5 copyright notice, including     *
 * terms governing use, modification, and redistribution, is contained in    *
 * the COPYING file, which can be found at the root of the source code       *
 * distribution tree, or in https://www.hdfgroup.org/licenses.               *
 * If you do not have access to either file, you may request a copy from     *
 * help@hdfgroup.org.                                                        *
 * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */

/*
 * This file contains private information about the H5S module
 */
#ifndef H5Sprivate_H
#define H5Sprivate_H

/* Include package's public header */
#include "H5Spublic.h"

/* Public headers needed by this file */
#include "H5Dpublic.h" /* Datasets				*/

/* Private headers needed by this file */
#include "H5private.h"  /* Generic Functions			*/
#include "H5Fprivate.h" /* Files				*/
#include "H5Gprivate.h" /* Groups				*/
#include "H5Pprivate.h" /* Property lists			*/
#include "H5Tprivate.h" /* Datatypes				*/

/* Forward references of package typedefs */
typedef struct H5S_extent_t          H5S_extent_t;
typedef struct H5S_pnt_node_t        H5S_pnt_node_t;
typedef struct H5S_pnt_list_t        H5S_pnt_list_t;
typedef struct H5S_hyper_span_t      H5S_hyper_span_t;
typedef struct H5S_hyper_span_info_t H5S_hyper_span_info_t;

/* Information about one dimension in a hyperslab selection */
typedef struct H5S_hyper_dim_t {
    hsize_t start;
    hsize_t stride;
    hsize_t count;
    hsize_t block;
} H5S_hyper_dim_t;

/* Point selection iteration container */
typedef struct {
    H5S_pnt_list_t *pnt_lst; /* Pointer to point list */
    H5S_pnt_node_t *curr;    /* Pointer to next node to output */
} H5S_point_iter_t;

/* Hyperslab selection iteration container */
typedef struct {
    /* Common fields for all hyperslab selections */
    hsize_t  off[H5S_MAX_RANK];  /* Offset in span node (used as position for regular hyperslabs) */
    hsize_t  slab[H5S_MAX_RANK]; /* Cumulative size of each dimension in bytes */
    unsigned iter_rank;          /* Rank of iterator information */
                                 /* (This should always be the same as the dataspace
                                  *  rank, except for regular hyperslab selections in
                                  *  which there are contiguous regions in the lower
                                  *  dimensions that have been "flattened")
                                  */
    hbool_t diminfo_valid;       /* Whether the dimension information is valid */

    /* "Flattened" regular hyperslab selection fields */
    H5S_hyper_dim_t diminfo[H5S_MAX_RANK];   /* "Flattened" regular selection information */
    hsize_t         size[H5S_MAX_RANK];      /* "Flattened" dataspace extent information */
    hssize_t        sel_off[H5S_MAX_RANK];   /* "Flattened" selection offset information */
    hbool_t         flattened[H5S_MAX_RANK]; /* Whether this dimension has been flattened */

    /* Irregular hyperslab selection fields */
    hsize_t loc_off[H5S_MAX_RANK]; /* Byte offset in buffer, for each dimension's current offset */
    H5S_hyper_span_info_t *spans;  /* Pointer to copy of the span tree */
    H5S_hyper_span_t      *span[H5S_MAX_RANK]; /* Array of pointers to span nodes */
} H5S_hyper_iter_t;

/* "All" selection iteration container */
typedef struct {
    hsize_t elmt_offset; /* Next element to output */
    hsize_t byte_offset; /* Next byte to output */
} H5S_all_iter_t;

/* Forward declaration of selection iteration class */
struct H5S_sel_iter_class_t;

/* Selection iteration container */
typedef struct H5S_sel_iter_t {
    /* Selection class */
    const struct H5S_sel_iter_class_t *type; /* Selection iteration class info */

    /* Information common to all iterators */
    unsigned rank;                  /* Rank of dataspace the selection iterator is operating on */
    hsize_t  dims[H5S_MAX_RANK];    /* Dimensions of dataspace the selection is operating on */
    hssize_t sel_off[H5S_MAX_RANK]; /* Selection offset in dataspace */
    hsize_t  elmt_left;             /* Number of elements left to iterate over */
    size_t   elmt_size;             /* Size of elements to iterate over */
    unsigned flags;                 /* Flags controlling iterator behavior */

    /* Information specific to each type of iterator */
    union {
        H5S_point_iter_t pnt; /* Point selection iteration information */
        H5S_hyper_iter_t hyp; /* New Hyperslab selection iteration information */
        H5S_all_iter_t   all; /* "All" selection iteration information */
    } u;
} H5S_sel_iter_t;

/* Selection iteration operator for internal library callbacks */
typedef herr_t (*H5S_sel_iter_lib_op_t)(void *elem, const H5T_t *type, unsigned ndim, const hsize_t *point,
                                        void *op_data);

/* Describe kind of callback to make */
typedef enum H5S_sel_iter_op_type_t {
    H5S_SEL_ITER_OP_APP, /* Application callback */
    H5S_SEL_ITER_OP_LIB  /* Library internal callback */
} H5S_sel_iter_op_type_t;

typedef struct H5S_sel_iter_app_op_t {
    H5D_operator_t op;      /* Callback */
    hid_t          type_id; /* Type ID to be passed to callback */
} H5S_sel_iter_app_op_t;

typedef struct H5S_sel_iter_op_t {
    H5S_sel_iter_op_type_t op_type;
    union {
        H5S_sel_iter_app_op_t app_op; /* Application callback */
        H5S_sel_iter_lib_op_t lib_op; /* Library internal callback */
    } u;
} H5S_sel_iter_op_t;

/* If the module using this macro is allowed access to the private variables, access them directly */
#ifdef H5S_MODULE
#define H5S_GET_EXTENT_TYPE(S)                  ((S)->extent.type)
#define H5S_GET_EXTENT_NDIMS(S)                 ((S)->extent.rank)
#define H5S_GET_EXTENT_NPOINTS(S)               ((S)->extent.nelem)
#define H5S_GET_SELECT_NPOINTS(S)               ((S)->select.num_elem)
#define H5S_GET_SELECT_TYPE(S)                  ((S)->select.type->type)
#define H5S_SELECT_VALID(S)                     ((*(S)->select.type->is_valid)(S))
#define H5S_SELECT_SERIAL_SIZE(S)               ((*(S)->select.type->serial_size)(S))
#define H5S_SELECT_SERIALIZE(S, BUF)            ((*(S)->select.type->serialize)(S, BUF))
#define H5S_SELECT_BOUNDS(S, START, END)        ((*(S)->select.type->bounds)(S, START, END))
#define H5S_SELECT_OFFSET(S, OFFSET)            ((*(S)->select.type->offset)(S, OFFSET))
#define H5S_SELECT_IS_CONTIGUOUS(S)             ((*(S)->select.type->is_contiguous)(S))
#define H5S_SELECT_IS_SINGLE(S)                 ((*(S)->select.type->is_single)(S))
#define H5S_SELECT_IS_REGULAR(S)                ((*(S)->select.type->is_regular)(S))
#define H5S_SELECT_ADJUST_U(S, O)               ((*(S)->select.type->adjust_u)(S, O))
#define H5S_SELECT_ADJUST_S(S, O)               ((*(S)->select.type->adjust_s)(S, O))
#define H5S_SELECT_PROJECT_SCALAR(S, O)         ((*(S)->select.type->project_scalar)(S, O))
#define H5S_SELECT_PROJECT_SIMPLE(S, NS, O)     ((*(S)->select.type->project_simple)(S, NS, O))
#define H5S_SELECT_ITER_COORDS(ITER, COORDS)    ((*(ITER)->type->iter_coords)(ITER, COORDS))
#define H5S_SELECT_ITER_BLOCK(ITER, START, END) ((*(ITER)->type->iter_block)(ITER, START, END))
#define H5S_SELECT_ITER_NELMTS(ITER)            ((*(ITER)->type->iter_nelmts)(ITER))
#define H5S_SELECT_ITER_HAS_NEXT_BLOCK(ITER)    ((*(ITER)->type->iter_has_next_block)(ITER))
#define H5S_SELECT_ITER_NEXT(ITER, NELEM)       ((*(ITER)->type->iter_next)(ITER, NELEM))
#define H5S_SELECT_ITER_NEXT_BLOCK(ITER)        ((*(ITER)->type->iter_next_block)(ITER))
#define H5S_SELECT_ITER_GET_SEQ_LIST(ITER, MAXSEQ, MAXBYTES, NSEQ, NBYTES, OFF, LEN)                         \
    ((*(ITER)->type->iter_get_seq_list)(ITER, MAXSEQ, MAXBYTES, NSEQ, NBYTES, OFF, LEN))
#define H5S_SELECT_ITER_RELEASE(ITER) ((*(ITER)->type->iter_release)(ITER))
#else /* H5S_MODULE */
#define H5S_GET_EXTENT_TYPE(S)                  (H5S_get_simple_extent_type(S))
#define H5S_GET_EXTENT_NDIMS(S)                 (H5S_get_simple_extent_ndims(S))
#define H5S_GET_EXTENT_NPOINTS(S)               (H5S_get_simple_extent_npoints(S))
#define H5S_GET_SELECT_NPOINTS(S)               (H5S_get_select_npoints(S))
#define H5S_GET_SELECT_TYPE(S)                  (H5S_get_select_type(S))
#define H5S_SELECT_VALID(S)                     (H5S_select_valid(S))
#define H5S_SELECT_SERIAL_SIZE(S)               (H5S_select_serial_size(S))
#define H5S_SELECT_SERIALIZE(S, BUF)            (H5S_select_serialize(S, BUF))
#define H5S_SELECT_BOUNDS(S, START, END)        (H5S_get_select_bounds(S, START, END))
#define H5S_SELECT_OFFSET(S, OFFSET)            (H5S_get_select_offset(S, OFFSET))
#define H5S_SELECT_IS_CONTIGUOUS(S)             (H5S_select_is_contiguous(S))
#define H5S_SELECT_IS_SINGLE(S)                 (H5S_select_is_single(S))
#define H5S_SELECT_IS_REGULAR(S)                (H5S_select_is_regular(S))
#define H5S_SELECT_ADJUST_U(S, O)               (H5S_select_adjust_u(S, O))
#define H5S_SELECT_ADJUST_S(S, O)               (H5S_select_adjust_s(S, O))
#define H5S_SELECT_PROJECT_SCALAR(S, O)         (H5S_select_project_scalar(S, O))
#define H5S_SELECT_PROJECT_SIMPLE(S, NS, O)     (H5S_select_project_simple(S, NS, O))
#define H5S_SELECT_ITER_COORDS(ITER, COORDS)    (H5S_select_iter_coords(ITER, COORDS))
#define H5S_SELECT_ITER_BLOCK(ITER, START, END) (H5S_select_iter_block(ITER, START, END))
#define H5S_SELECT_ITER_NELMTS(ITER)            (H5S_select_iter_nelmts(ITER))
#define H5S_SELECT_ITER_HAS_NEXT_BLOCK(ITER)    (H5S_select_iter_has_next_block(ITER))
#define H5S_SELECT_ITER_NEXT(ITER, NELEM)       (H5S_select_iter_next(ITER, NELEM))
#define H5S_SELECT_ITER_NEXT_BLOCK(ITER)        (H5S_select_iter_next_block(ITER))
#define H5S_SELECT_ITER_GET_SEQ_LIST(ITER, MAXSEQ, MAXBYTES, NSEQ, NBYTES, OFF, LEN)                         \
    (H5S_select_iter_get_seq_list(ITER, MAXSEQ, MAXBYTES, NSEQ, NBYTES, OFF, LEN))
#define H5S_SELECT_ITER_RELEASE(ITER) (H5S_select_iter_release(ITER))
#endif /* H5S_MODULE */

/* Handle these callbacks in a special way, since they have prologs that need to be executed */
#define H5S_SELECT_COPY(DST, SRC, SHARE)          (H5S_select_copy(DST, SRC, SHARE))
#define H5S_SELECT_SHAPE_SAME(S1, S2)             (H5S_select_shape_same(S1, S2))
#define H5S_SELECT_INTERSECT_BLOCK(S, START, END) (H5S_select_intersect_block(S, START, END))
#define H5S_SELECT_RELEASE(S)                     (H5S_select_release(S))
#define H5S_SELECT_DESERIALIZE(S, BUF)            (H5S_select_deserialize(S, BUF))

/* Forward declaration of structs used below */
struct H5O_t;
struct H5O_loc_t;

/* Early typedef to avoid circular dependencies */
typedef struct H5S_t H5S_t;

/* Operations on dataspaces */
H5_DLL herr_t      H5S_init(void);
H5_DLL H5S_t      *H5S_copy(const H5S_t *src, hbool_t share_selection, hbool_t copy_max);
H5_DLL herr_t      H5S_close(H5S_t *ds);
H5_DLL H5S_class_t H5S_get_simple_extent_type(const H5S_t *ds);
H5_DLL hssize_t    H5S_get_simple_extent_npoints(const H5S_t *ds);
H5_DLL hsize_t     H5S_get_npoints_max(const H5S_t *ds);
H5_DLL hbool_t     H5S_has_extent(const H5S_t *ds);
H5_DLL int         H5S_get_simple_extent_ndims(const H5S_t *ds);
H5_DLL int    H5S_get_simple_extent_dims(const H5S_t *ds, hsize_t dims[] /*out*/, hsize_t max_dims[] /*out*/);
H5_DLL herr_t H5S_write(H5F_t *f, struct H5O_t *oh, unsigned update_flags, H5S_t *ds);
H5_DLL herr_t H5S_append(H5F_t *f, struct H5O_t *oh, H5S_t *ds);
H5_DLL H5S_t *H5S_read(const struct H5O_loc_t *loc);
H5_DLL htri_t H5S_set_extent(H5S_t *space, const hsize_t *size);
H5_DLL herr_t H5S_set_extent_real(H5S_t *space, const hsize_t *size);
H5_DLL herr_t H5S_set_extent_simple(H5S_t *space, unsigned rank, const hsize_t *dims, const hsize_t *max);
H5_DLL H5S_t *H5S_create(H5S_class_t type);
H5_DLL H5S_t *H5S_create_simple(unsigned rank, const hsize_t dims[/*rank*/], const hsize_t maxdims[/*rank*/]);
H5_DLL herr_t H5S_set_version(H5F_t *f, H5S_t *ds);
H5_DLL herr_t H5S_encode(H5S_t *obj, unsigned char **p, size_t *nalloc);
H5_DLL H5S_t *H5S_decode(const unsigned char **p);
H5_DLL herr_t H5S_debug(H5F_t *f, const void *_mesg, FILE *stream, int indent, int fwidth);

/* Operations on dataspace extents */
H5_DLL hsize_t H5S_extent_nelem(const H5S_extent_t *ext);
H5_DLL int     H5S_extent_get_dims(const H5S_extent_t *ext, hsize_t dims[], hsize_t max_dims[]);
H5_DLL htri_t  H5S_extent_equal(const H5S_t *ds1, const H5S_t *ds2);
H5_DLL herr_t  H5S_extent_copy(H5S_t *dst, const H5S_t *src);

/* Operations on selections */
H5_DLL herr_t       H5S_select_deserialize(H5S_t **space, const uint8_t **p);
H5_DLL H5S_sel_type H5S_get_select_type(const H5S_t *space);
H5_DLL herr_t   H5S_select_iterate(void *buf, const H5T_t *type, H5S_t *space, const H5S_sel_iter_op_t *op,
                                   void *op_data);
H5_DLL herr_t   H5S_select_fill(const void *fill, size_t fill_size, H5S_t *space, void *buf);
H5_DLL htri_t   H5S_select_valid(const H5S_t *space);
H5_DLL hsize_t  H5S_get_select_npoints(const H5S_t *space);
H5_DLL herr_t   H5S_get_select_bounds(const H5S_t *space, hsize_t *start, hsize_t *end);
H5_DLL herr_t   H5S_get_select_offset(const H5S_t *space, hsize_t *offset);
H5_DLL int      H5S_get_select_unlim_dim(const H5S_t *space);
H5_DLL herr_t   H5S_get_select_num_elem_non_unlim(const H5S_t *space, hsize_t *num_elem_non_unlim);
H5_DLL herr_t   H5S_select_offset(H5S_t *space, const hssize_t *offset);
H5_DLL herr_t   H5S_select_copy(H5S_t *dst, const H5S_t *src, hbool_t share_selection);
H5_DLL htri_t   H5S_select_shape_same(H5S_t *space1, H5S_t *space2);
H5_DLL htri_t   H5S_select_intersect_block(H5S_t *space, const hsize_t *start, const hsize_t *end);
H5_DLL herr_t   H5S_select_construct_projection(H5S_t *base_space, H5S_t **new_space_ptr,
                                                unsigned new_space_rank, hsize_t element_size,
                                                ptrdiff_t *buf_adj);
H5_DLL herr_t   H5S_select_release(H5S_t *ds);
H5_DLL hssize_t H5S_select_serial_size(H5S_t *space);
H5_DLL herr_t   H5S_select_serialize(H5S_t *space, uint8_t **p);
H5_DLL htri_t   H5S_select_is_contiguous(const H5S_t *space);
H5_DLL htri_t   H5S_select_is_single(const H5S_t *space);
H5_DLL htri_t   H5S_select_is_regular(H5S_t *space);
H5_DLL herr_t   H5S_select_adjust_u(H5S_t *space, const hsize_t *offset);
H5_DLL herr_t   H5S_select_adjust_s(H5S_t *space, const hssize_t *offset);
H5_DLL herr_t   H5S_select_project_scalar(const H5S_t *space, hsize_t *offset);
H5_DLL herr_t   H5S_select_project_simple(const H5S_t *space, H5S_t *new_space, hsize_t *offset);
H5_DLL herr_t H5S_select_project_intersection(H5S_t *src_space, H5S_t *dst_space, H5S_t *src_intersect_space,
                                              H5S_t **new_space_ptr, hbool_t share_space);
H5_DLL herr_t H5S_select_subtract(H5S_t *space, H5S_t *subtract_space);

/* Operations on all selections */
H5_DLL herr_t H5S_select_all(H5S_t *space, hbool_t rel_prev);

/* Operations on none selections */
H5_DLL herr_t H5S_select_none(H5S_t *space);

/* Operations on point selections */
H5_DLL herr_t H5S_select_elements(H5S_t *space, H5S_seloper_t op, size_t num_elem, const hsize_t *coord);

/* Operations on hyperslab selections */
H5_DLL herr_t  H5S_select_hyperslab(H5S_t *space, H5S_seloper_t op, const hsize_t start[],
                                    const hsize_t *stride, const hsize_t count[], const hsize_t *block);
H5_DLL herr_t  H5S_combine_hyperslab(const H5S_t *old_space, H5S_seloper_t op, const hsize_t start[],
                                     const hsize_t *stride, const hsize_t count[], const hsize_t *block,
                                     H5S_t **new_space);
H5_DLL herr_t  H5S_hyper_add_span_element(H5S_t *space, unsigned rank, const hsize_t *coords);
H5_DLL htri_t  H5S_hyper_normalize_offset(H5S_t *space, hssize_t *old_offset);
H5_DLL herr_t  H5S_hyper_denormalize_offset(H5S_t *space, const hssize_t *old_offset);
H5_DLL herr_t  H5S_hyper_clip_unlim(H5S_t *space, hsize_t clip_size);
H5_DLL hsize_t H5S_hyper_get_clip_extent(const H5S_t *clip_space, const H5S_t *match_space,
                                         hbool_t incl_trail);
H5_DLL hsize_t H5S_hyper_get_clip_extent_match(const H5S_t *clip_space, const H5S_t *match_space,
                                               hsize_t match_clip_size, hbool_t incl_trail);
H5_DLL H5S_t  *H5S_hyper_get_unlim_block(const H5S_t *space, hsize_t block_index);
H5_DLL hsize_t H5S_hyper_get_first_inc_block(const H5S_t *space, hsize_t clip_size, hbool_t *partial);

/* Operations on selection iterators */
H5_DLL herr_t  H5S_select_iter_init(H5S_sel_iter_t *iter, H5S_t *space, size_t elmt_size, unsigned flags);
H5_DLL herr_t  H5S_select_iter_coords(const H5S_sel_iter_t *sel_iter, hsize_t *coords);
H5_DLL hsize_t H5S_select_iter_nelmts(const H5S_sel_iter_t *sel_iter);
H5_DLL herr_t  H5S_select_iter_next(H5S_sel_iter_t *sel_iter, size_t nelem);
H5_DLL herr_t H5S_select_iter_get_seq_list(H5S_sel_iter_t *iter, size_t maxseq, size_t maxbytes, size_t *nseq,
                                           size_t *nbytes, hsize_t *off, size_t *len);
H5_DLL herr_t H5S_select_iter_release(H5S_sel_iter_t *sel_iter);
H5_DLL herr_t H5S_sel_iter_close(H5S_sel_iter_t *sel_iter);

#ifdef H5_HAVE_PARALLEL
H5_DLL herr_t H5S_mpio_space_type(H5S_t *space, size_t elmt_size,
                                  /* out: */ MPI_Datatype *new_type, int *count, hbool_t *is_derived_type,
                                  hbool_t do_permute, hsize_t **permute_map, hbool_t *is_permuted);
#endif /* H5_HAVE_PARALLEL */

#endif /* H5Sprivate_H */