SDDS ToolKit Programs and Libraries for C and Python
Loading...
Searching...
No Matches
SDDS.h File Reference

Detailed Description

SDDS (Self Describing Data Set) Data Types Definitions and Function Prototypes.

This header file defines the data types, macros, structures, and function prototypes used for handling SDDS files. SDDS is a file protocol designed to store and transfer scientific data efficiently.

License This file is distributed under the terms of the Software License Agreement
found in the file LICENSE included with this distribution.
Authors
M. Borland, C. Saunders, R. Soliday, H. Shang

Definition in file SDDS.h.

#include <stdio.h>
#include <stdarg.h>
#include <stdlib.h>
#include "SDDStypes.h"
#include <inttypes.h>
#include <lzma.h>

Go to the source code of this file.

Typedefs

typedef void * voidp
 
typedef voidp gzFile
 
typedef SDDS_DATASET SDDS_TABLE
 

Functions

epicsShareFuncSDDS int SDDS_CompareIndexedNames (const void *s1, const void *s2)
 Compares two SORTED_INDEX structures by their name fields.
 
epicsShareFuncSDDS int SDDS_CompareIndexedNamesPtr (const void *s1, const void *s2)
 Compares two pointers to SORTED_INDEX structures by their name fields.
 
epicsShareFuncSDDS int32_t SDDS_InitializeOutput (SDDS_DATASET *SDDS_dataset, int32_t data_mode, int32_t lines_per_row, const char *description, const char *contents, const char *filename)
 Initializes the SDDS output dataset.
 
epicsShareFuncSDDS int32_t SDDS_Parallel_InitializeOutput (SDDS_DATASET *SDDS_dataset, const char *description, const char *contents, const char *filename)
 Initializes the SDDS output dataset for parallel processing.
 
epicsShareFuncSDDS int32_t SDDS_InitializeAppend (SDDS_DATASET *SDDS_dataset, const char *filename)
 Initializes the SDDS dataset for appending data by adding a new page to an existing file.
 
epicsShareFuncSDDS int32_t SDDS_InitializeAppendToPage (SDDS_DATASET *SDDS_dataset, const char *filename, int64_t updateInterval, int64_t *rowsPresentReturn)
 Initializes the SDDS dataset for appending data to the last page of an existing file.
 
epicsShareFuncSDDS int32_t SDDS_DisconnectFile (SDDS_DATASET *SDDS_dataset)
 Disconnects the SDDS dataset from its associated file.
 
epicsShareFuncSDDS int32_t SDDS_ReconnectFile (SDDS_DATASET *SDDS_dataset)
 Reconnects the SDDS dataset to its previously associated file.
 
epicsShareFuncSDDS long SDDS_DisconnectInputFile (SDDS_DATASET *SDDS_dataset)
 Disconnects the input file from the SDDS dataset.
 
epicsShareFuncSDDS int32_t SDDS_ReconnectInputFile (SDDS_DATASET *SDDS_dataset, long position)
 Reconnects the input file for the SDDS dataset at a specified position.
 
epicsShareFuncSDDS int32_t SDDS_ReadNewBinaryRows (SDDS_DATASET *SDDS_dataset)
 Reads new binary rows from the SDDS dataset.
 
epicsShareFuncSDDS int32_t SDDS_FreeStringData (SDDS_DATASET *SDDS_dataset)
 
epicsShareFuncSDDS int32_t SDDS_Terminate (SDDS_DATASET *SDDS_dataset)
 
epicsShareFuncSDDS void SDDS_SetTerminateMode (uint32_t mode)
 
epicsShareFuncSDDS void SDDS_SetColumnMemoryMode (SDDS_DATASET *SDDS_dataset, uint32_t mode)
 
epicsShareFuncSDDS int32_t SDDS_GetColumnMemoryMode (SDDS_DATASET *SDDS_dataset)
 
epicsShareFuncSDDS int32_t SDDS_SetRowCountMode (SDDS_DATASET *SDDS_dataset, uint32_t mode)
 Sets the row count mode for the SDDS dataset.
 
epicsShareFuncSDDS int32_t SDDS_SetAutoReadRecovery (SDDS_DATASET *SDDS_dataset, uint32_t mode)
 
epicsShareFuncSDDS int32_t SDDS_UpdateRowCount (SDDS_DATASET *SDDS_dataset)
 
epicsShareFuncSDDS void SDDS_DisableFSync (SDDS_DATASET *SDDS_dataset)
 Disables file synchronization for the SDDS dataset.
 
epicsShareFuncSDDS void SDDS_EnableFSync (SDDS_DATASET *SDDS_dataset)
 Enables file synchronization for the SDDS dataset.
 
epicsShareFuncSDDS int32_t SDDS_DoFSync (SDDS_DATASET *SDDS_dataset)
 Synchronizes the SDDS dataset's file to disk.
 
epicsShareFuncSDDS void SDDS_SetLZMACompressionLevel (int32_t level)
 
epicsShareFuncSDDS int32_t SDDS_GetLZMACompressionLevel (void)
 
epicsShareFuncSDDS int32_t SDDS_DefineParameter (SDDS_DATASET *SDDS_dataset, const char *name, const char *symbol, const char *units, const char *description, const char *format_string, int32_t type, char *fixed_value)
 Defines a data parameter with a fixed string value.
 
epicsShareFuncSDDS int32_t SDDS_DefineParameter1 (SDDS_DATASET *SDDS_dataset, const char *name, const char *symbol, const char *units, const char *description, const char *format_string, int32_t type, void *fixed_value)
 Defines a data parameter with a fixed numerical value.
 
epicsShareFuncSDDS int32_t SDDS_DefineColumn (SDDS_DATASET *SDDS_dataset, const char *name, const char *symbol, const char *units, const char *description, const char *format_string, int32_t type, int32_t field_length)
 Defines a data column within the SDDS dataset.
 
epicsShareFuncSDDS int32_t SDDS_DefineArray (SDDS_DATASET *SDDS_dataset, const char *name, const char *symbol, const char *units, const char *description, const char *format_string, int32_t type, int32_t field_length, int32_t dimensions, const char *group_name)
 Defines a data array within the SDDS dataset.
 
epicsShareFuncSDDS int32_t SDDS_DefineAssociate (SDDS_DATASET *SDDS_dataset, const char *name, const char *filename, const char *path, const char *description, const char *contents, int32_t sdds)
 Defines an associate for the SDDS dataset.
 
epicsShareFuncSDDS int32_t SDDS_IsValidName (const char *name, const char *dataClass)
 Checks if a given name is valid for a specified class within the SDDS dataset.
 
epicsShareFuncSDDS int32_t SDDS_SetNameValidityFlags (uint32_t flags)
 Sets the validity flags for parameter and column names in the SDDS dataset.
 
epicsShareFuncSDDS int32_t SDDS_DefineSimpleColumn (SDDS_DATASET *SDDS_dataset, const char *name, const char *unit, int32_t type)
 Defines a simple data column within the SDDS dataset.
 
epicsShareFuncSDDS int32_t SDDS_DefineSimpleParameter (SDDS_DATASET *SDDS_dataset, const char *name, const char *unit, int32_t type)
 Defines a simple data parameter within the SDDS dataset.
 
epicsShareFuncSDDS int32_t SDDS_DefineSimpleColumns (SDDS_DATASET *SDDS_dataset, int32_t number, char **name, char **unit, int32_t type)
 Defines multiple simple data columns of the same data type within the SDDS dataset.
 
epicsShareFuncSDDS int32_t SDDS_DefineSimpleParameters (SDDS_DATASET *SDDS_dataset, int32_t number, char **name, char **unit, int32_t type)
 Defines multiple simple data parameters of the same data type within the SDDS dataset.
 
epicsShareFuncSDDS int32_t SDDS_SetNoRowCounts (SDDS_DATASET *SDDS_dataset, int32_t value)
 Sets the flag to enable or disable row counts in the SDDS dataset.
 
epicsShareFuncSDDS int32_t SDDS_WriteLayout (SDDS_DATASET *SDDS_dataset)
 Writes the SDDS layout header to the output file.
 
epicsShareFuncSDDS int32_t SDDS_EraseData (SDDS_DATASET *SDDS_dataset)
 Erases all data entries in the SDDS dataset.
 
epicsShareFuncSDDS int32_t SDDS_ProcessColumnString (SDDS_DATASET *SDDS_dataset, char *string, int32_t mode)
 Process a column definition string.
 
epicsShareFuncSDDS int32_t SDDS_ProcessParameterString (SDDS_DATASET *SDDS_dataset, char *string, int32_t mode)
 Process a parameter definition string.
 
epicsShareFuncSDDS int32_t SDDS_ProcessArrayString (SDDS_DATASET *SDDS_dataset, char *string)
 Process an array definition string.
 
epicsShareFuncSDDS int32_t SDDS_ProcessAssociateString (SDDS_DATASET *SDDS_dataset, char *string)
 Process an associate definition string.
 
epicsShareFuncSDDS int32_t SDDS_InitializeCopy (SDDS_DATASET *SDDS_target, SDDS_DATASET *SDDS_source, char *filename, char *filemode)
 
epicsShareFuncSDDS int32_t SDDS_CopyLayout (SDDS_DATASET *SDDS_target, SDDS_DATASET *SDDS_source)
 
epicsShareFuncSDDS int32_t SDDS_AppendLayout (SDDS_DATASET *SDDS_target, SDDS_DATASET *SDDS_source, uint32_t mode)
 
epicsShareFuncSDDS int32_t SDDS_CopyPage (SDDS_DATASET *SDDS_target, SDDS_DATASET *SDDS_source)
 
epicsShareFuncSDDS int32_t SDDS_CopyParameters (SDDS_DATASET *SDDS_target, SDDS_DATASET *SDDS_source)
 
epicsShareFuncSDDS int32_t SDDS_CopyArrays (SDDS_DATASET *SDDS_target, SDDS_DATASET *SDDS_source)
 
epicsShareFuncSDDS int32_t SDDS_CopyColumns (SDDS_DATASET *SDDS_target, SDDS_DATASET *SDDS_source)
 
epicsShareFuncSDDS int32_t SDDS_CopyRowsOfInterest (SDDS_DATASET *SDDS_target, SDDS_DATASET *SDDS_source)
 
epicsShareFuncSDDS int32_t SDDS_CopyRow (SDDS_DATASET *SDDS_target, int64_t target_row, SDDS_DATASET *SDDS_source, int64_t source_srow)
 
epicsShareFuncSDDS int32_t SDDS_CopyRowDirect (SDDS_DATASET *SDDS_target, int64_t target_row, SDDS_DATASET *SDDS_source, int64_t source_row)
 
epicsShareFuncSDDS int32_t SDDS_CopyAdditionalRows (SDDS_DATASET *SDDS_target, SDDS_DATASET *SDDS_source)
 
epicsShareFuncSDDS int32_t SDDS_CopyRows (SDDS_DATASET *SDDS_target, SDDS_DATASET *SDDS_source, int64_t firstRow, int64_t lastRow)
 
epicsShareFuncSDDS void SDDS_DeferSavingLayout (SDDS_DATASET *SDDS_dataset, int32_t mode)
 
epicsShareFuncSDDS int32_t SDDS_SaveLayout (SDDS_DATASET *SDDS_dataset)
 
epicsShareFuncSDDS int32_t SDDS_RestoreLayout (SDDS_DATASET *SDDS_dataset)
 
epicsShareFuncSDDS int32_t SDDS_StartPage (SDDS_DATASET *SDDS_dataset, int64_t expected_n_rows)
 
epicsShareFuncSDDS int32_t SDDS_ClearPage (SDDS_DATASET *SDDS_dataset)
 
epicsShareFuncSDDS int32_t SDDS_LengthenTable (SDDS_DATASET *SDDS_dataset, int64_t n_additional_rows)
 
epicsShareFuncSDDS int32_t SDDS_ShortenTable (SDDS_DATASET *SDDS_dataset, int64_t rows)
 
epicsShareFuncSDDS int32_t SDDS_SetParameters (SDDS_DATASET *SDDS_dataset, int32_t mode,...)
 
epicsShareFuncSDDS int32_t SDDS_SetParameter (SDDS_DATASET *SDDS_dataset, int32_t mode,...)
 
epicsShareFuncSDDS int32_t SDDS_SetRowValues (SDDS_DATASET *SDDS_dataset, int32_t mode, int64_t row,...)
 
epicsShareFuncSDDS int32_t SDDS_WritePage (SDDS_DATASET *SDDS_dataset)
 Writes the current data table to the output file.
 
epicsShareFuncSDDS int32_t SDDS_UpdatePage (SDDS_DATASET *SDDS_dataset, uint32_t mode)
 Updates the current page of the SDDS dataset.
 
epicsShareFuncSDDS int32_t SDDS_SyncDataSet (SDDS_DATASET *SDDS_dataset)
 Synchronizes the SDDS dataset with the disk by flushing buffered data.
 
epicsShareFuncSDDS int32_t SDDS_SetColumn (SDDS_DATASET *SDDS_dataset, int32_t mode, void *data, int64_t rows,...)
 Sets the values for one data column in the current data table of an SDDS dataset.
 
epicsShareFuncSDDS int32_t SDDS_SetColumnFromDoubles (SDDS_DATASET *SDDS_dataset, int32_t mode, double *data, int64_t rows,...)
 Sets the values for a single data column using double-precision floating-point numbers.
 
epicsShareFuncSDDS int32_t SDDS_SetColumnFromFloats (SDDS_DATASET *SDDS_dataset, int32_t mode, float *data, int64_t rows,...)
 Sets the values for a single data column using single-precision floating-point numbers.
 
epicsShareFuncSDDS int32_t SDDS_SetColumnFromLongs (SDDS_DATASET *SDDS_dataset, int32_t mode, int32_t *data, int64_t rows,...)
 Sets the values for a single data column using long integer numbers.
 
epicsShareFuncSDDS int32_t SDDS_SetParametersFromDoubles (SDDS_DATASET *SDDS_dataset, int32_t mode,...)
 
epicsShareFuncSDDS int32_t SDDS_GetColumnInformation (SDDS_DATASET *SDDS_dataset, char *field_name, void *memory, int32_t mode,...)
 Retrieves information about a specified column in the SDDS dataset.
 
epicsShareFuncSDDS int32_t SDDS_GetParameterInformation (SDDS_DATASET *SDDS_dataset, char *field_name, void *memory, int32_t mode,...)
 Retrieves information about a specified parameter in the SDDS dataset.
 
epicsShareFuncSDDS int32_t SDDS_GetArrayInformation (SDDS_DATASET *SDDS_dataset, char *field_name, void *memory, int32_t mode,...)
 Retrieves information about a specified array in the SDDS dataset.
 
epicsShareFuncSDDS int32_t SDDS_GetAssociateInformation (SDDS_DATASET *SDDS_dataset, char *field_name, void *memory, int32_t mode,...)
 Retrieves information about a specified associate in the SDDS dataset.
 
epicsShareFuncSDDS int32_t SDDS_ChangeColumnInformation (SDDS_DATASET *SDDS_dataset, char *field_name, void *memory, int32_t mode,...)
 Modifies a specific field in a column definition within the SDDS dataset.
 
epicsShareFuncSDDS int32_t SDDS_ChangeParameterInformation (SDDS_DATASET *SDDS_dataset, char *field_name, void *memory, int32_t mode,...)
 Modifies a specific field in a parameter definition within the SDDS dataset.
 
epicsShareFuncSDDS int32_t SDDS_ChangeArrayInformation (SDDS_DATASET *SDDS_dataset, char *field_name, void *memory, int32_t mode,...)
 Modifies a specific field in an array definition within the SDDS dataset.
 
epicsShareFuncSDDS void SDDS_SetReadRecoveryMode (SDDS_DATASET *SDDS_dataset, int32_t mode)
 Sets the read recovery mode for an SDDS dataset.
 
epicsShareFuncSDDS int32_t SDDS_SetDefaultIOBufferSize (int32_t bufferSize)
 
epicsShareFuncSDDS int32_t SDDS_InitializeInputFromSearchPath (SDDS_DATASET *SDDSin, char *file)
 
epicsShareFuncSDDS int32_t SDDS_InitializeInput (SDDS_DATASET *SDDS_dataset, char *filename)
 
epicsShareFuncSDDS int32_t SDDS_ReadLayout (SDDS_DATASET *SDDS_dataset, FILE *fp)
 
epicsShareFuncSDDS int32_t SDDS_InitializeHeaderlessInput (SDDS_DATASET *SDDS_dataset, char *filename)
 Initializes the SDDS dataset for headerless input.
 
epicsShareFuncSDDS int64_t SDDS_GetRowLimit ()
 
epicsShareFuncSDDS int64_t SDDS_SetRowLimit (int64_t limit)
 
epicsShareFuncSDDS int32_t SDDS_GotoPage (SDDS_DATASET *SDDS_dataset, int32_t page_number)
 Sets the current page of the SDDS dataset to the specified page number.
 
epicsShareFuncSDDS int32_t SDDS_CheckEndOfFile (SDDS_DATASET *SDDS_dataset)
 
epicsShareFuncSDDS int32_t SDDS_ReadPage (SDDS_DATASET *SDDS_dataset)
 
epicsShareFuncSDDS int32_t SDDS_ReadPageSparse (SDDS_DATASET *SDDS_dataset, uint32_t mode, int64_t sparse_interval, int64_t sparse_offset, int32_t sparse_statistics)
 
epicsShareFuncSDDS int32_t SDDS_ReadPageLastRows (SDDS_DATASET *SDDS_dataset, int64_t last_rows)
 
epicsShareFuncSDDS int32_t SDDS_ReadAsciiPage (SDDS_DATASET *SDDS_dataset, int64_t sparse_interval, int64_t sparse_offset, int32_t sparse_statistics)
 Reads the next SDDS ASCII page into memory with optional data sparsity and statistics.
 
epicsShareFuncSDDS int32_t SDDS_ReadRecoveryPossible (SDDS_DATASET *SDDS_dataset)
 Checks if any data in an SDDS page was recovered after an error was detected.
 
epicsShareFuncSDDS int32_t SDDS_SetColumnFlags (SDDS_DATASET *SDDS_dataset, int32_t column_flag_value)
 Sets the acceptance flags for all columns in the current data table of a data set.
 
epicsShareFuncSDDS int32_t SDDS_SetRowFlags (SDDS_DATASET *SDDS_dataset, int32_t row_flag_value)
 Sets the acceptance flags for all rows in the current data table of a data set.
 
epicsShareFuncSDDS int32_t SDDS_GetRowFlag (SDDS_DATASET *SDDS_dataset, int64_t row)
 Retrieves the acceptance flag of a specific row in the current data table.
 
epicsShareFuncSDDS int32_t SDDS_GetRowFlags (SDDS_DATASET *SDDS_dataset, int32_t *flag, int64_t rows)
 Retrieves the acceptance flags for all rows in the current data table.
 
epicsShareFuncSDDS int32_t SDDS_BufferedRead (void *target, int64_t targetSize, FILE *fp, SDDS_FILEBUFFER *fBuffer, int32_t type, int32_t byteOrder)
 
epicsShareFuncSDDS int32_t SDDS_AssertRowFlags (SDDS_DATASET *SDDS_dataset, uint32_t mode,...)
 Sets acceptance flags for rows based on specified criteria.
 
epicsShareFuncSDDS int32_t SDDS_MatchColumns (SDDS_DATASET *SDDS_dataset, char ***match, int32_t matchMode, int32_t typeMode,...)
 Matches and retrieves column names from an SDDS dataset based on specified criteria.
 
epicsShareFuncSDDS int32_t SDDS_MatchParameters (SDDS_DATASET *SDDS_dataset, char ***match, int32_t matchMode, int32_t typeMode,...)
 Matches and retrieves parameter names from an SDDS dataset based on specified criteria.
 
epicsShareFuncSDDS int32_t SDDS_MatchArrays (SDDS_DATASET *SDDS_dataset, char ***match, int32_t matchMode, int32_t typeMode,...)
 Matches and retrieves array names from an SDDS dataset based on specified criteria.
 
epicsShareFuncSDDS int32_t SDDS_Logic (int32_t previous, int32_t match, uint32_t logic)
 Applies logical operations to determine the new state of a row flag based on previous and current match conditions.
 
epicsShareFuncSDDS int32_t SDDS_SetColumnsOfInterest (SDDS_DATASET *SDDS_dataset, int32_t mode,...)
 Sets the acceptance flags for columns based on specified naming criteria.
 
epicsShareFuncSDDS int32_t SDDS_AssertColumnFlags (SDDS_DATASET *SDDS_dataset, uint32_t mode,...)
 Sets acceptance flags for columns based on specified criteria.
 
epicsShareFuncSDDS int64_t SDDS_SetRowsOfInterest (SDDS_DATASET *SDDS_dataset, char *selection_column, int32_t mode,...)
 Sets the rows of interest in an SDDS dataset based on various selection criteria.
 
epicsShareFuncSDDS int64_t SDDS_MatchRowsOfInterest (SDDS_DATASET *SDDS_dataset, char *selection_column, char *label_to_match, int32_t logic)
 Matches and marks rows of interest in an SDDS dataset based on label matching.
 
epicsShareFuncSDDS int32_t SDDS_DeleteColumn (SDDS_DATASET *SDDS_dataset, char *column_name)
 Deletes a specified column from an SDDS dataset.
 
epicsShareFuncSDDS int32_t SDDS_DeleteParameter (SDDS_DATASET *SDDS_dataset, char *parameter_name)
 Deletes a specified parameter from an SDDS dataset.
 
epicsShareFuncSDDS int32_t SDDS_DeleteUnsetColumns (SDDS_DATASET *SDDS_dataset)
 Deletes all columns from an SDDS dataset that are not marked as "of interest".
 
epicsShareFuncSDDS int32_t SDDS_CountColumnsOfInterest (SDDS_DATASET *SDDS_dataset)
 Counts the number of columns marked as "of interest" in the current data table.
 
epicsShareFuncSDDS int32_t SDDS_ColumnIsOfInterest (SDDS_DATASET *SDDS_dataset, char *name)
 Determines if a specified column is marked as of interest in the dataset.
 
epicsShareFuncSDDS int32_t SDDS_ColumnCount (SDDS_DATASET *dataset)
 Retrieves the number of columns in the SDDS dataset.
 
epicsShareFuncSDDS int32_t SDDS_ParameterCount (SDDS_DATASET *dataset)
 Retrieves the number of parameters in the SDDS dataset.
 
epicsShareFuncSDDS int32_t SDDS_ArrayCount (SDDS_DATASET *dataset)
 Retrieves the number of arrays in the SDDS dataset.
 
epicsShareFuncSDDS int64_t SDDS_CountRowsOfInterest (SDDS_DATASET *SDDS_dataset)
 Counts the number of rows marked as "of interest" in the current data table.
 
epicsShareFuncSDDS int32_t SDDS_DeleteUnsetRows (SDDS_DATASET *SDDS_dataset)
 Deletes rows from an SDDS dataset that are not marked as "of interest".
 
epicsShareFuncSDDS int64_t SDDS_FilterRowsOfInterest (SDDS_DATASET *SDDS_dataset, char *filter_column, double lower, double upper, int32_t logic)
 Filters rows of interest in an SDDS dataset based on numeric ranges in a specified column.
 
epicsShareFuncSDDS int32_t SDDS_ItemInsideWindow (void *data, int64_t index, int32_t type, double lower_limit, double upper_limit)
 Checks whether a data item is within a specified numeric window.
 
epicsShareFuncSDDS int64_t SDDS_FilterRowsByNumScan (SDDS_DATASET *SDDS_dataset, char *filter_column, uint32_t mode)
 Filters rows of interest in an SDDS dataset based on numeric scanning of a specified column.
 
epicsShareFuncSDDS void * SDDS_GetColumn (SDDS_DATASET *SDDS_dataset, char *column_name)
 Retrieves a copy of the data for a specified column, including only rows marked as "of interest".
 
epicsShareFuncSDDS void * SDDS_GetInternalColumn (SDDS_DATASET *SDDS_dataset, char *column_name)
 Retrieves an internal pointer to the data of a specified column, including all rows.
 
epicsShareFuncSDDS double * SDDS_GetColumnInDoubles (SDDS_DATASET *SDDS_dataset, char *column_name)
 Retrieves the data of a specified numerical column as an array of doubles, considering only rows marked as "of interest".
 
epicsShareFuncSDDS float * SDDS_GetColumnInFloats (SDDS_DATASET *SDDS_dataset, char *column_name)
 Retrieves the data of a specified numerical column as an array of floats, considering only rows marked as "of interest".
 
epicsShareFuncSDDS int32_t * SDDS_GetColumnInLong (SDDS_DATASET *SDDS_dataset, char *column_name)
 Retrieves the data of a specified numerical column as an array of 32-bit integers, considering only rows marked as "of interest".
 
epicsShareFuncSDDS short * SDDS_GetColumnInShort (SDDS_DATASET *SDDS_dataset, char *column_name)
 Retrieves the data of a specified numerical column as an array of short integers, considering only rows marked as "of interest".
 
epicsShareFuncSDDS char ** SDDS_GetColumnInString (SDDS_DATASET *SDDS_dataset, char *column_name)
 Retrieves the data of a specified column as an array of strings, considering only rows marked as "of interest".
 
epicsShareFuncSDDS void * SDDS_GetNumericColumn (SDDS_DATASET *SDDS_dataset, char *column_name, int32_t desiredType)
 Retrieves the data of a specified numerical column as an array of a desired numerical type, considering only rows marked as "of interest".
 
epicsShareFuncSDDS void * SDDS_GetRow (SDDS_DATASET *SDDS_dataset, int64_t srow_index, void *memory)
 Retrieves the data of a specific selected row as an array, considering only columns marked as "of interest".
 
epicsShareFuncSDDS void * SDDS_GetValue (SDDS_DATASET *SDDS_dataset, char *column_name, int64_t srow_index, void *memory)
 Retrieves the value from a specified column and selected row, optionally storing it in provided memory.
 
epicsShareFuncSDDS double SDDS_GetValueAsDouble (SDDS_DATASET *SDDS_dataset, char *column_name, int64_t srow_index)
 Retrieves the value from a specified column and selected row, casting it to a double.
 
epicsShareFuncSDDS double SDDS_GetValueByIndexAsDouble (SDDS_DATASET *SDDS_dataset, int32_t column_index, int64_t srow_index)
 Retrieves the value from a specified column and selected row, casting it to a double.
 
epicsShareFuncSDDS void * SDDS_GetValueByIndex (SDDS_DATASET *SDDS_dataset, int32_t column_index, int64_t srow_index, void *memory)
 Retrieves the value from a specified column and selected row, optionally storing it in provided memory.
 
epicsShareFuncSDDS void * SDDS_GetValueByAbsIndex (SDDS_DATASET *SDDS_dataset, int32_t column_index, int64_t srow_index, void *memory)
 Retrieves the value from a specified column and absolute row index, optionally storing it in provided memory.
 
epicsShareFuncSDDS void * SDDS_GetParameter (SDDS_DATASET *SDDS_dataset, char *parameter_name, void *memory)
 Retrieves the value of a specified parameter from the current data table of a data set.
 
epicsShareFuncSDDS void * SDDS_GetParameterByIndex (SDDS_DATASET *SDDS_dataset, int32_t index, void *memory)
 Retrieves the value of a specified parameter by its index from the current data table of a data set.
 
epicsShareFuncSDDS long double * SDDS_GetParameterAsLongDouble (SDDS_DATASET *SDDS_dataset, char *parameter_name, long double *data)
 Retrieves the value of a specified parameter as a long double from the current data table of an SDDS dataset.
 
epicsShareFuncSDDS double * SDDS_GetParameterAsDouble (SDDS_DATASET *SDDS_dataset, char *parameter_name, double *data)
 Retrieves the value of a specified parameter as a double from the current data table of an SDDS dataset.
 
epicsShareFuncSDDS int32_t * SDDS_GetParameterAsLong (SDDS_DATASET *SDDS_dataset, char *parameter_name, int32_t *data)
 Retrieves the value of a specified parameter as a 32-bit integer from the current data table of a data set.
 
epicsShareFuncSDDS int64_t * SDDS_GetParameterAsLong64 (SDDS_DATASET *SDDS_dataset, char *parameter_name, int64_t *data)
 Retrieves the value of a specified parameter as a 64-bit integer from the current data table of an SDDS dataset.
 
epicsShareFuncSDDS char * SDDS_GetParameterAsString (SDDS_DATASET *SDDS_dataset, char *parameter_name, char **memory)
 Retrieves the value of a specified parameter as a string from the current data table of an SDDS dataset.
 
epicsShareFuncSDDS char * SDDS_GetParameterAsFormattedString (SDDS_DATASET *SDDS_dataset, char *parameter_name, char **memory, char *suppliedformat)
 Retrieves the value of a specified parameter as a formatted string from the current data table of an SDDS dataset.
 
epicsShareFuncSDDS int32_t SDDS_GetParameters (SDDS_DATASET *SDDS_dataset,...)
 Retrieves multiple parameter values from the current data table of a data set.
 
epicsShareFuncSDDS void * SDDS_GetFixedValueParameter (SDDS_DATASET *SDDS_dataset, char *parameter_name, void *memory)
 Retrieves the fixed value of a specified parameter from an SDDS dataset.
 
epicsShareFuncSDDS int32_t SDDS_GetDescription (SDDS_DATASET *SDDS_dataset, char **text, char **contents)
 Retrieves the text and contents descriptions from an SDDS dataset.
 
epicsShareFuncSDDS int32_t SDDS_SetArrayUnitsConversion (SDDS_DATASET *SDDS_dataset, char *column_name, char *new_units, char *old_units, double factor)
 Sets unit conversions for a specified array in an SDDS dataset.
 
epicsShareFuncSDDS int32_t SDDS_SetColumnUnitsConversion (SDDS_DATASET *SDDS_dataset, char *column_name, char *new_units, char *old_units, double factor)
 Sets unit conversions for a specified column in an SDDS dataset.
 
epicsShareFuncSDDS int32_t SDDS_SetParameterUnitsConversion (SDDS_DATASET *SDDS_dataset, char *column_name, char *new_units, char *old_units, double factor)
 Sets unit conversions for a specified parameter in an SDDS dataset.
 
epicsShareFuncSDDS void * SDDS_GetMatrixOfRows (SDDS_DATASET *SDDS_dataset, int64_t *n_rows)
 Retrieves all rows marked as "of interest" as a matrix (array of row arrays).
 
epicsShareFuncSDDS void * SDDS_GetCastMatrixOfRows (SDDS_DATASET *SDDS_dataset, int64_t *n_rows, int32_t sddsType)
 Retrieves all rows marked as "of interest" as a matrix, casting each value to a specified numerical type.
 
epicsShareFuncSDDS void * SDDS_GetMatrixFromColumn (SDDS_DATASET *SDDS_dataset, char *column_name, int64_t dimension1, int64_t dimension2, int32_t mode)
 Extracts a matrix from a specified column in the current data table of an SDDS dataset.
 
epicsShareFuncSDDS void * SDDS_GetDoubleMatrixFromColumn (SDDS_DATASET *SDDS_dataset, char *column_name, int64_t dimension1, int64_t dimension2, int32_t mode)
 Extracts a matrix of doubles from a specified column in the current data table of an SDDS dataset.
 
epicsShareFuncSDDS SDDS_ARRAYSDDS_GetArray (SDDS_DATASET *SDDS_dataset, char *array_name, SDDS_ARRAY *memory)
 Retrieves an array from the current data table of an SDDS dataset.
 
epicsShareFuncSDDS double * SDDS_GetArrayInDoubles (SDDS_DATASET *SDDS_dataset, char *array_name, int32_t *values)
 Retrieves an array from the current data table of an SDDS dataset and converts its elements to doubles.
 
epicsShareFuncSDDS int32_t * SDDS_GetArrayInLong (SDDS_DATASET *SDDS_dataset, char *array_name, int32_t *values)
 Retrieves an array from the current data table of an SDDS dataset and converts its elements to 32-bit integers.
 
epicsShareFuncSDDS char ** SDDS_GetArrayInString (SDDS_DATASET *SDDS_dataset, char *array_name, int32_t *values)
 Retrieves an array from the current data table of an SDDS dataset and converts its elements to strings.
 
epicsShareFuncSDDS int32_t SDDS_SetArrayVararg (SDDS_DATASET *SDDS_dataset, char *array_name, int32_t mode, void *data_pointer,...)
 Sets the values of an array variable in the SDDS dataset using variable arguments for dimensions.
 
epicsShareFuncSDDS int32_t SDDS_SetArray (SDDS_DATASET *SDDS_dataset, char *array_name, int32_t mode, void *data_pointer, int32_t *dimension)
 Sets the values of an array variable in the SDDS dataset using specified dimensions.
 
epicsShareFuncSDDS int32_t SDDS_AppendToArrayVararg (SDDS_DATASET *SDDS_dataset, char *array_name, int32_t mode, void *data_pointer, int32_t elements,...)
 Appends data to an existing array variable in the SDDS dataset using variable arguments for dimensions.
 
epicsShareFuncSDDS void * SDDS_Realloc (void *old_ptr, size_t new_size)
 Reallocates memory to a new size.
 
epicsShareFuncSDDS void * SDDS_Malloc (size_t size)
 Allocates memory of a specified size.
 
epicsShareFuncSDDS void SDDS_Free (void *mem)
 Free memory previously allocated by SDDS_Malloc.
 
epicsShareFuncSDDS void * SDDS_Calloc (size_t nelem, size_t elem_size)
 Allocates zero-initialized memory for an array of elements.
 
epicsShareFuncSDDS int32_t SDDS_NumberOfErrors (void)
 Retrieves the number of errors recorded by SDDS library routines.
 
epicsShareFuncSDDS void SDDS_ClearErrors (void)
 Clears all recorded error messages from the SDDS error stack.
 
epicsShareFuncSDDS void SDDS_SetError (char *error_text)
 Records an error message in the SDDS error stack.
 
epicsShareFuncSDDS void SDDS_SetError0 (char *error_text)
 Internal function to record an error message in the SDDS error stack.
 
epicsShareFuncSDDS void SDDS_Bomb (char *message)
 Terminates the program after printing an error message and recorded errors.
 
epicsShareFuncSDDS void SDDS_Warning (char *message)
 Prints a warning message to stderr.
 
epicsShareFuncSDDS void SDDS_RegisterProgramName (const char *name)
 Registers the executable program name for use in error messages.
 
epicsShareFuncSDDS void SDDS_PrintErrors (FILE *fp, int32_t mode)
 Prints recorded error messages to a specified file stream.
 
epicsShareFuncSDDS char ** SDDS_GetErrorMessages (int32_t *number, int32_t mode)
 Retrieves recorded error messages from the SDDS error stack.
 
epicsShareFuncSDDS char ** SDDS_GetColumnNames (SDDS_DATASET *SDDS_dataset, int32_t *number)
 Retrieves the names of all columns in the SDDS dataset.
 
epicsShareFuncSDDS char ** SDDS_GetParameterNames (SDDS_DATASET *SDDS_dataset, int32_t *number)
 Retrieves the names of all parameters in the SDDS dataset.
 
epicsShareFuncSDDS char ** SDDS_GetAssociateNames (SDDS_DATASET *SDDS_dataset, int32_t *number)
 Retrieves the names of all associates in the SDDS dataset.
 
epicsShareFuncSDDS char ** SDDS_GetArrayNames (SDDS_DATASET *SDDS_dataset, int32_t *number)
 Retrieves the names of all arrays in the SDDS dataset.
 
epicsShareFuncSDDS COLUMN_DEFINITIONSDDS_GetColumnDefinition (SDDS_DATASET *SDDS_dataset, char *name)
 Retrieves the definition of a specified column from the SDDS dataset.
 
epicsShareFuncSDDS COLUMN_DEFINITIONSDDS_CopyColumnDefinition (COLUMN_DEFINITION **target, COLUMN_DEFINITION *source)
 Creates a copy of a column definition.
 
epicsShareFuncSDDS int32_t SDDS_FreeColumnDefinition (COLUMN_DEFINITION *source)
 Frees memory allocated for a column definition.
 
epicsShareFuncSDDS int32_t SDDS_TransferColumnDefinition (SDDS_DATASET *target, SDDS_DATASET *source, char *name, char *newName)
 Transfers a column definition from a source dataset to a target dataset.
 
epicsShareFuncSDDS int32_t SDDS_DefineColumnLikeParameter (SDDS_DATASET *target, SDDS_DATASET *source, char *name, char *newName)
 Defines a column in the target dataset based on a parameter definition from the source dataset.
 
epicsShareFuncSDDS int32_t SDDS_DefineColumnLikeArray (SDDS_DATASET *target, SDDS_DATASET *source, char *name, char *newName)
 Defines a column in the target dataset based on an array definition from the source dataset.
 
epicsShareFuncSDDS int32_t SDDS_TransferAllColumnDefinitions (SDDS_DATASET *SDDS_target, SDDS_DATASET *SDDS_source, uint32_t mode)
 Transfers all column definitions from a source dataset to a target dataset.
 
epicsShareFuncSDDS int32_t SDDS_ParseNamelist (void *data, SDDS_FIELD_INFORMATION *fieldInfo, int32_t fieldInfos, char *s)
 Parse a namelist string and populate the corresponding data structure.
 
epicsShareFuncSDDS PARAMETER_DEFINITIONSDDS_GetParameterDefinition (SDDS_DATASET *SDDS_dataset, char *name)
 Retrieves the definition of a specified parameter from the SDDS dataset.
 
epicsShareFuncSDDS PARAMETER_DEFINITIONSDDS_CopyParameterDefinition (PARAMETER_DEFINITION **target, PARAMETER_DEFINITION *source)
 Creates a copy of a parameter definition.
 
epicsShareFuncSDDS int32_t SDDS_FreeParameterDefinition (PARAMETER_DEFINITION *source)
 Frees memory allocated for a parameter definition.
 
epicsShareFuncSDDS int32_t SDDS_TransferParameterDefinition (SDDS_DATASET *target, SDDS_DATASET *source, char *name, char *newName)
 Transfers a parameter definition from a source dataset to a target dataset.
 
epicsShareFuncSDDS int32_t SDDS_DefineParameterLikeColumn (SDDS_DATASET *target, SDDS_DATASET *source, char *name, char *newName)
 Defines a parameter in the target dataset based on a column definition from the source dataset.
 
epicsShareFuncSDDS int32_t SDDS_DefineParameterLikeArray (SDDS_DATASET *target, SDDS_DATASET *source, char *name, char *newName)
 Defines a parameter in the target dataset based on an array definition from the source dataset.
 
epicsShareFuncSDDS int32_t SDDS_TransferAllParameterDefinitions (SDDS_DATASET *SDDS_target, SDDS_DATASET *SDDS_source, uint32_t mode)
 Transfers all parameter definitions from a source dataset to a target dataset.
 
epicsShareFuncSDDS ARRAY_DEFINITIONSDDS_GetArrayDefinition (SDDS_DATASET *SDDS_dataset, char *name)
 Retrieves the definition of a specified array from the SDDS dataset.
 
epicsShareFuncSDDS ARRAY_DEFINITIONSDDS_CopyArrayDefinition (ARRAY_DEFINITION **target, ARRAY_DEFINITION *source)
 Creates a copy of an array definition.
 
epicsShareFuncSDDS int32_t SDDS_FreeArrayDefinition (ARRAY_DEFINITION *source)
 Frees memory allocated for an array definition.
 
epicsShareFuncSDDS int32_t SDDS_TransferArrayDefinition (SDDS_DATASET *target, SDDS_DATASET *source, char *name, char *newName)
 Transfers an array definition from a source dataset to a target dataset.
 
epicsShareFuncSDDS int32_t SDDS_TransferAllArrayDefinitions (SDDS_DATASET *SDDS_target, SDDS_DATASET *SDDS_source, uint32_t mode)
 Transfers all array definitions from a source dataset to a target dataset.
 
epicsShareFuncSDDS ASSOCIATE_DEFINITIONSDDS_GetAssociateDefinition (SDDS_DATASET *SDDS_dataset, char *name)
 Retrieves the definition of a specified associate from the SDDS dataset.
 
epicsShareFuncSDDS ASSOCIATE_DEFINITIONSDDS_CopyAssociateDefinition (ASSOCIATE_DEFINITION **target, ASSOCIATE_DEFINITION *source)
 Creates a copy of an associate definition.
 
epicsShareFuncSDDS int32_t SDDS_FreeAssociateDefinition (ASSOCIATE_DEFINITION *source)
 Frees memory allocated for an associate definition.
 
epicsShareFuncSDDS int32_t SDDS_TransferAssociateDefinition (SDDS_DATASET *target, SDDS_DATASET *source, char *name, char *newName)
 Transfers an associate definition from a source dataset to a target dataset.
 
epicsShareFuncSDDS int32_t SDDS_GetColumnIndex (SDDS_DATASET *SDDS_dataset, char *name)
 Retrieves the index of a named column in the SDDS dataset.
 
epicsShareFuncSDDS int32_t SDDS_GetParameterIndex (SDDS_DATASET *SDDS_dataset, char *name)
 Retrieves the index of a named parameter in the SDDS dataset.
 
epicsShareFuncSDDS int32_t SDDS_GetArrayIndex (SDDS_DATASET *SDDS_dataset, char *name)
 Retrieves the index of a named array in the SDDS dataset.
 
epicsShareFuncSDDS int32_t SDDS_GetAssociateIndex (SDDS_DATASET *SDDS_dataset, char *name)
 Retrieves the index of a named associate in the SDDS dataset.
 
epicsShareFuncSDDS int32_t SDDS_GetColumnType (SDDS_DATASET *SDDS_dataset, int32_t index)
 Retrieves the data type of a column in the SDDS dataset by its index.
 
epicsShareFuncSDDS int32_t SDDS_GetNamedColumnType (SDDS_DATASET *SDDS_dataset, char *name)
 Retrieves the data type of a column in the SDDS dataset by its name.
 
epicsShareFuncSDDS int32_t SDDS_GetParameterType (SDDS_DATASET *SDDS_dataset, int32_t index)
 Retrieves the data type of a parameter in the SDDS dataset by its index.
 
epicsShareFuncSDDS int32_t SDDS_GetNamedParameterType (SDDS_DATASET *SDDS_dataset, char *name)
 Retrieves the data type of a parameter in the SDDS dataset by its name.
 
epicsShareFuncSDDS int32_t SDDS_GetArrayType (SDDS_DATASET *SDDS_dataset, int32_t index)
 Retrieves the data type of an array in the SDDS dataset by its index.
 
epicsShareFuncSDDS int32_t SDDS_GetNamedArrayType (SDDS_DATASET *SDDS_dataset, char *name)
 Retrieves the data type of an array in the SDDS dataset by its name.
 
epicsShareFuncSDDS int32_t SDDS_GetTypeSize (int32_t type)
 Retrieves the size in bytes of a specified SDDS data type.
 
epicsShareFuncSDDS char * SDDS_GetTypeName (int32_t type)
 Retrieves the name of a specified SDDS data type as a string.
 
epicsShareFuncSDDS int32_t SDDS_IdentifyType (char *typeName)
 Identifies the SDDS data type based on its string name.
 
epicsShareFuncSDDS char * SDDS_FindColumn (SDDS_DATASET *SDDS_dataset, int32_t mode,...)
 Finds the first column in the SDDS dataset that matches the specified criteria.
 
epicsShareFuncSDDS char * SDDS_FindParameter (SDDS_DATASET *SDDS_dataset, int32_t mode,...)
 Finds the first parameter in the SDDS dataset that matches the specified criteria.
 
epicsShareFuncSDDS char * SDDS_FindArray (SDDS_DATASET *SDDS_dataset, int32_t mode,...)
 Finds the first array in the SDDS dataset that matches the specified criteria.
 
epicsShareFuncSDDS int32_t SDDS_CheckColumn (SDDS_DATASET *SDDS_dataset, char *name, char *units, int32_t type, FILE *fp_message)
 Checks if a column exists in the SDDS dataset with the specified name, units, and type.
 
epicsShareFuncSDDS int32_t SDDS_CheckParameter (SDDS_DATASET *SDDS_dataset, char *name, char *units, int32_t type, FILE *fp_message)
 Checks if a parameter exists in the SDDS dataset with the specified name, units, and type.
 
epicsShareFuncSDDS int32_t SDDS_CheckArray (SDDS_DATASET *SDDS_dataset, char *name, char *units, int32_t type, FILE *fp_message)
 Checks if an array exists in the SDDS dataset with the specified name, units, and type.
 
epicsShareFuncSDDS int32_t SDDS_VerifyArrayExists (SDDS_DATASET *SDDS_dataset, int32_t mode,...)
 Verifies the existence of an array in the SDDS dataset based on specified criteria.
 
epicsShareFuncSDDS int32_t SDDS_VerifyColumnExists (SDDS_DATASET *SDDS_dataset, int32_t mode,...)
 Verifies the existence of a column in the SDDS dataset based on specified criteria.
 
epicsShareFuncSDDS int32_t SDDS_VerifyParameterExists (SDDS_DATASET *SDDS_dataset, int32_t mode,...)
 Verifies the existence of a parameter in the SDDS dataset based on specified criteria.
 
epicsShareFuncSDDS int32_t SDDS_PrintCheckText (FILE *fp, char *name, char *units, int32_t type, char *class_name, int32_t error_code)
 Prints detailed error messages related to SDDS entity checks.
 
epicsShareFuncSDDS int32_t SDDS_IsActive (SDDS_DATASET *SDDS_dataset)
 Checks whether an SDDS dataset is currently active.
 
epicsShareFuncSDDS int32_t SDDS_ForceInactive (SDDS_DATASET *SDDS_dataset)
 Marks an SDDS dataset as inactive.
 
epicsShareFuncSDDS int32_t SDDS_LockFile (FILE *fp, const char *filename, const char *callerName)
 Attempts to lock a specified file.
 
epicsShareFuncSDDS int32_t SDDS_FileIsLocked (const char *filename)
 Determines if a specified file is locked.
 
epicsShareFuncSDDS int32_t SDDS_BreakIntoLockedFile (char *filename)
 Attempts to override a locked file by creating a temporary copy.
 
epicsShareFuncSDDS int32_t SDDS_CopyString (char **target, const char *source)
 Copies a source string to a target string with memory allocation.
 
epicsShareFuncSDDS int32_t SDDS_CopyStringArray (char **target, char **source, int64_t n_strings)
 Copies an array of strings from source to target.
 
epicsShareFuncSDDS int32_t SDDS_FreeStringArray (char **string, int64_t strings)
 Frees an array of strings by deallocating each individual string.
 
epicsShareFuncSDDS int32_t SDDS_VerifyPrintfFormat (const char *format_string, int32_t type)
 Verifies that a printf format string is compatible with a specified data type.
 
epicsShareFuncSDDS int32_t SDDS_HasWhitespace (char *string)
 Checks if a string contains any whitespace characters.
 
epicsShareFuncSDDS char * fgetsSkipComments (SDDS_DATASET *SDDS_dataset, char *s, int32_t slen, FILE *fp, char skip_char)
 Reads a line from a file while skipping comment lines.
 
epicsShareFuncSDDS char * fgetsSkipCommentsResize (SDDS_DATASET *SDDS_dataset, char **s, int32_t *slen, FILE *fp, char skip_char)
 Reads a line from a file with dynamic buffer resizing while skipping comment lines.
 
epicsShareFuncSDDS void SDDS_CutOutComments (SDDS_DATASET *SDDS_dataset, char *s, char cc)
 Removes comments from a string based on a specified comment character.
 
epicsShareFuncSDDS void SDDS_EscapeNewlines (char *s)
 Escapes newline characters in a string by replacing them with "\\n".
 
epicsShareFuncSDDS void SDDS_EscapeQuotes (char *s, char quote_char)
 Escapes quote characters within a string by inserting backslashes.
 
epicsShareFuncSDDS void SDDS_UnescapeQuotes (char *s, char quote_char)
 Removes escape characters from quote characters within a string.
 
epicsShareFuncSDDS int32_t SDDS_IsQuoted (char *string, char *position, char quotation_mark)
 Checks if a position in a string is within a quoted section.
 
epicsShareFuncSDDS int32_t SDDS_GetToken (char *s, char *buffer, int32_t buflen)
 Extracts the next token from a string, handling quoted substrings and escape characters.
 
epicsShareFuncSDDS int32_t SDDS_GetToken2 (char *s, char **st, int32_t *strlength, char *buffer, int32_t buflen)
 Extracts the next token from a string, handling quoted substrings and escape characters, with updated string pointers.
 
epicsShareFuncSDDS int32_t SDDS_PadToLength (char *string, int32_t length)
 Pads a string with spaces to reach a specified length.
 
epicsShareFuncSDDS void SDDS_EscapeCommentCharacters (char *string, char cc)
 Escapes comment characters within a string by inserting backslashes.
 
epicsShareFuncSDDS void SDDS_InterpretEscapes (char *s)
 Interprets and converts escape sequences in a string.
 
epicsShareFuncSDDS int32_t SDDS_ZeroMemory (void *mem, int64_t n_bytes)
 Sets a block of memory to zero.
 
epicsShareFuncSDDS int32_t SDDS_SetMemory (void *mem, int64_t n_elements, int32_t data_type,...)
 Initializes a memory block with a sequence of values based on a specified data type.
 
epicsShareFuncSDDS int32_t SDDS_SprintTypedValue (void *data, int64_t index, int32_t type, const char *format, char *buffer, uint32_t mode)
 Formats a data value of a specified type into a string buffer using an optional printf format string.
 
epicsShareFuncSDDS int32_t SDDS_SprintTypedValueFactor (void *data, int64_t index, int32_t type, const char *format, char *buffer, uint32_t mode, double factor)
 Reallocates memory to a new size and zero-initializes the additional space.
 
epicsShareFuncSDDS int32_t SDDS_PrintTypedValue (void *data, int64_t index, int32_t type, char *format, FILE *fp, uint32_t mode)
 Prints a data value of a specified type using an optional printf format string.
 
epicsShareFuncSDDS int32_t SDDS_WriteTypedValue (void *data, int64_t index, int32_t type, char *format, FILE *fp)
 Writes a typed value to an ASCII file stream.
 
epicsShareFuncSDDS void * SDDS_CastValue (void *data, int64_t index, int32_t data_type, int32_t desired_type, void *memory)
 Casts a value from one SDDS data type to another.
 
epicsShareFuncSDDS void SDDS_RemovePadding (char *s)
 Removes leading and trailing whitespace from a string.
 
epicsShareFuncSDDS int32_t SDDS_StringIsBlank (char *s)
 Checks if a string is blank (contains only whitespace characters).
 
epicsShareFuncSDDS void * SDDS_AllocateMatrix (int32_t size, int64_t dim1, int64_t dim2)
 Allocates a two-dimensional matrix with zero-initialized elements.
 
epicsShareFuncSDDS void SDDS_FreeMatrix (void **ptr, int64_t dim1)
 Frees memory allocated for a two-dimensional matrix.
 
epicsShareFuncSDDS void SDDS_FreeArray (SDDS_ARRAY *array)
 Frees memory allocated for an SDDS array structure.
 
epicsShareFuncSDDS void * SDDS_MakePointerArray (void *data, int32_t type, int32_t dimensions, int32_t *dimension)
 Creates a multi-dimensional pointer array from a contiguous data block.
 
epicsShareFuncSDDS int32_t SDDS_ApplyFactorToParameter (SDDS_DATASET *SDDS_dataset, char *name, double factor)
 Applies a scaling factor to a specific parameter in the SDDS dataset.
 
epicsShareFuncSDDS int32_t SDDS_ApplyFactorToColumn (SDDS_DATASET *SDDS_dataset, char *name, double factor)
 Applies a scaling factor to all elements of a specific column in the SDDS dataset.
 
epicsShareFuncSDDS int32_t SDDS_DeleteParameterFixedValues (SDDS_DATASET *SDDS_dataset)
 Deletes fixed values from all parameters in the SDDS dataset.
 
epicsShareFuncSDDS int32_t SDDS_SetDataMode (SDDS_DATASET *SDDS_dataset, int32_t newmode)
 Sets the data mode (ASCII or Binary) for the SDDS dataset.
 
epicsShareFuncSDDS int32_t SDDS_CheckDataset (SDDS_DATASET *SDDS_dataset, const char *caller)
 Validates the SDDS dataset pointer.
 
epicsShareFuncSDDS int32_t SDDS_CheckTabularData (SDDS_DATASET *SDDS_dataset, const char *caller)
 Validates the consistency of tabular data within an SDDS dataset.
 
epicsShareFuncSDDS int32_t SDDS_CheckDatasetStructureSize (int32_t size)
 Verifies that the size of the SDDS_DATASET structure matches the expected size.
 
epicsShareFuncSDDS uint32_t SDDS_SetAutoCheckMode (uint32_t newMode)
 Sets the automatic check mode for SDDS dataset validation.
 
epicsShareFuncSDDS int32_t SDDS_FlushBuffer (FILE *fp, SDDS_FILEBUFFER *fBuffer)
 
epicsShareFuncSDDS int32_t SDDS_BufferedWrite (void *target, int64_t targetSize, FILE *fp, SDDS_FILEBUFFER *fBuffer)
 
epicsShareFuncSDDS int32_t SDDS_ScanData (char *string, int32_t type, int32_t field_length, void *data, int64_t index, int32_t is_parameter)
 Scans a string and saves the parsed value into a data pointer according to the specified data type.
 
epicsShareFuncSDDS int32_t SDDS_ScanData2 (char *string, char **pstring, int32_t *strlength, int32_t type, int32_t field_length, void *data, int64_t index, int32_t is_parameter)
 Scans a string and saves the parsed value into a data pointer, optimized for long strings.
 
epicsShareFuncSDDS long double SDDS_ConvertToLongDouble (int32_t type, void *data, int64_t index)
 Converts a value to long double based on its type.
 
epicsShareFuncSDDS double SDDS_ConvertToDouble (int32_t type, void *data, int64_t index)
 Converts a value to double based on its type.
 
epicsShareFuncSDDS int64_t SDDS_ConvertToLong64 (int32_t type, void *data, int64_t index)
 Converts a value to a 64-bit integer based on its type.
 
epicsShareFuncSDDS int32_t SDDS_ConvertToLong (int32_t type, void *data, int64_t index)
 Converts a value to a 32-bit integer based on its type.
 
epicsShareFuncSDDS int32_t SDDS_WriteBinaryString (char *string, FILE *fp, SDDS_FILEBUFFER *fBuffer)
 Writes a binary string to a file with buffering.
 
epicsShareFuncSDDS int64_t SDDS_CreateRpnMemory (const char *name, short is_string)
 Stub function for creating RPN memory when RPN_SUPPORT is not enabled.
 
epicsShareFuncSDDS int64_t SDDS_CreateRpnArray (char *name)
 Stub function for creating RPN arrays when RPN_SUPPORT is not enabled.
 
epicsShareFuncSDDS int32_t SDDS_IsBigEndianMachine ()
 Determines whether the current machine uses big-endian byte ordering.
 
void SDDS_SwapShort (short *data)
 Swaps the endianness of a short integer.
 
void SDDS_SwapUShort (unsigned short *data)
 Swaps the endianness of an unsigned short integer.
 
epicsShareFuncSDDS void SDDS_SwapLong (int32_t *data)
 Swaps the endianness of a 32-bit integer.
 
epicsShareFuncSDDS void SDDS_SwapULong (uint32_t *data)
 Swaps the endianness of a 32-bit unsigned integer.
 
epicsShareFuncSDDS void SDDS_SwapLong64 (int64_t *data)
 Swaps the endianness of a 64-bit integer.
 
epicsShareFuncSDDS void SDDS_SwapULong64 (uint64_t *data)
 Swaps the endianness of a 64-bit unsigned integer.
 
void SDDS_SwapFloat (float *data)
 Swaps the endianness of a float.
 
void SDDS_SwapDouble (double *data)
 Swaps the endianness of a double.
 
void SDDS_SwapLongDouble (long double *data)
 Swaps the endianness of a long double.
 
epicsShareFuncSDDS int32_t SDDS_SwapEndsArrayData (SDDS_DATASET *SDDSin)
 Swaps the endianness of the array data in an SDDS dataset.
 
epicsShareFuncSDDS int32_t SDDS_SwapEndsParameterData (SDDS_DATASET *SDDSin)
 Swaps the endianness of the parameter data in an SDDS dataset.
 
epicsShareFuncSDDS int32_t SDDS_SwapEndsColumnData (SDDS_DATASET *SDDSin)
 Swaps the endianness of the column data in an SDDS dataset.
 
epicsShareFuncSDDS int32_t SDDS_ReadNonNativePage (SDDS_DATASET *SDDS_dataset)
 Reads a non-native endian page from an SDDS dataset.
 
int32_t SDDS_ReadNonNativePageSparse (SDDS_DATASET *SDDS_dataset, uint32_t mode, int64_t sparse_interval, int64_t sparse_offset)
 Reads a sparse non-native endian page from an SDDS dataset.
 
int32_t SDDS_ReadNonNativeBinaryPage (SDDS_DATASET *SDDS_dataset, int64_t sparse_interval, int64_t sparse_offset)
 Reads a non-native endian binary page from an SDDS dataset.
 
int32_t SDDS_ReadNonNativeBinaryParameters (SDDS_DATASET *SDDS_dataset)
 Reads non-native endian binary parameters from an SDDS dataset.
 
int32_t SDDS_ReadNonNativeBinaryArrays (SDDS_DATASET *SDDS_dataset)
 Reads non-native endian binary arrays from an SDDS dataset.
 
int32_t SDDS_ReadNonNativeBinaryRow (SDDS_DATASET *SDDS_dataset, int64_t row, int32_t skip)
 Reads a non-native endian binary row from an SDDS dataset.
 
char * SDDS_ReadNonNativeBinaryString (FILE *fp, SDDS_FILEBUFFER *fBuffer, int32_t skip)
 Reads a non-native endian binary string from a file.
 
epicsShareFuncSDDS int32_t SDDS_WriteNonNativeBinaryPage (SDDS_DATASET *SDDS_dataset)
 Writes a non-native endian binary page to an SDDS dataset.
 
int32_t SDDS_WriteNonNativeBinaryParameters (SDDS_DATASET *SDDS_dataset)
 Writes non-native endian binary parameters to an SDDS dataset.
 
int32_t SDDS_WriteNonNativeBinaryArrays (SDDS_DATASET *SDDS_dataset)
 Writes non-native endian binary arrays to an SDDS dataset.
 
int32_t SDDS_WriteNonNativeBinaryRow (SDDS_DATASET *SDDS_dataset, int64_t row)
 Writes a non-native endian binary row to an SDDS dataset.
 
int32_t SDDS_WriteNonNativeBinaryString (char *string, FILE *fp, SDDS_FILEBUFFER *fBuffer)
 Writes a non-native endian binary string to a file.
 
epicsShareFuncSDDS char ** getMatchingSDDSNames (SDDS_DATASET *dataset, char **matchName, int32_t matches, int32_t *names, short match_type)
 Retrieves an array of matching SDDS entity names based on specified criteria.
 
epicsShareFuncSDDS SDDS_DATASETSDDS_CreateEmptyDataset (void)
 Creates an empty SDDS dataset.
 

Typedef Documentation

◆ gzFile

typedef voidp gzFile

Definition at line 215 of file SDDS.h.

◆ SDDS_TABLE

Definition at line 362 of file SDDS.h.

◆ voidp

typedef void* voidp

Definition at line 214 of file SDDS.h.

Function Documentation

◆ fgetsSkipComments()

epicsShareFuncSDDS char * fgetsSkipComments ( SDDS_DATASET * SDDS_dataset,
char * s,
int32_t slen,
FILE * fp,
char skip_char )
extern

Reads a line from a file while skipping comment lines.

This function reads lines from the specified file stream, ignoring lines that begin with the specified skip_char. It also processes special comment lines that start with !# by parsing them using SDDS_ParseSpecialComments.

Parameters
[in]SDDS_datasetPointer to the SDDS_DATASET structure, used for processing comments.
[out]sPointer to a character array where the read line will be stored.
[in]slenThe maximum number of characters to read into s.
[in]fpPointer to the FILE stream to read from.
[in]skip_charCharacter indicating the start of a comment line. Lines beginning with this character will be skipped.
Returns
On success, returns the pointer s containing the read line. If the end of the file is reached or an error occurs, returns NULL.
Note
The function modifies the buffer s by removing comments as determined by SDDS_CutOutComments.
See also
SDDS_CutOutComments
SDDS_ParseSpecialComments

Definition at line 1517 of file SDDS_utils.c.

1517 {
1518 while (fgets(s, slen, fp)) {
1519 if (s[0] != skip_char) {
1520 SDDS_CutOutComments(SDDS_dataset, s, skip_char);
1521 return (s);
1522 } else if (s[1] == '#') {
1523 SDDS_ParseSpecialComments(SDDS_dataset, s + 2);
1524 }
1525 }
1526 return (NULL);
1527}
void SDDS_CutOutComments(SDDS_DATASET *SDDS_dataset, char *s, char cc)
Removes comments from a string based on a specified comment character.
void SDDS_ParseSpecialComments(SDDS_DATASET *SDDS_dataset, char *s)
Parses and processes special comment commands within the SDDS dataset.

◆ fgetsSkipCommentsResize()

epicsShareFuncSDDS char * fgetsSkipCommentsResize ( SDDS_DATASET * SDDS_dataset,
char ** s,
int32_t * slen,
FILE * fp,
char skip_char )
extern

Reads a line from a file with dynamic buffer resizing while skipping comment lines.

This function reads lines from the specified file stream, ignoring lines that begin with the specified skip_char. If a line exceeds the current buffer size, the buffer is dynamically resized to accommodate the entire line. It also processes special comment lines that start with !# by parsing them using SDDS_ParseSpecialComments.

Parameters
[in]SDDS_datasetPointer to the SDDS_DATASET structure, used for processing comments.
[in,out]sPointer to a pointer to a character array where the read line will be stored. This buffer may be resized if necessary.
[in,out]slenPointer to an int32_t variable specifying the current size of the buffer s. This value may be updated if the buffer is resized.
[in]fpPointer to the FILE stream to read from.
[in]skip_charCharacter indicating the start of a comment line. Lines beginning with this character will be skipped.
Returns
On success, returns the pointer *s containing the read line. If the end of the file is reached or an error occurs, returns NULL.
Note
The caller is responsible for managing the memory of the buffer *s, including freeing it when no longer needed.
See also
SDDS_CutOutComments
SDDS_ParseSpecialComments
SDDS_Realloc

Definition at line 1548 of file SDDS_utils.c.

1548 {
1549 int32_t spaceLeft, length, newLine;
1550 char *sInsert, *fgetsReturn;
1551
1552 sInsert = *s;
1553 spaceLeft = *slen;
1554 newLine = 1;
1555 while ((fgetsReturn = fgets(sInsert, spaceLeft, fp))) {
1556 if (newLine && sInsert[0] == '!')
1557 continue;
1558 SDDS_CutOutComments(SDDS_dataset, sInsert, skip_char);
1559 length = strlen(sInsert);
1560 if (sInsert[length - 1] != '\n' && !feof(fp)) {
1561 /* buffer wasn't long enough to get the whole line. Resize and add more data. */
1562 spaceLeft = *slen;
1563 *slen = *slen * 2;
1564 *s = SDDS_Realloc(*s, sizeof(**s) * *slen);
1565 sInsert = *s + strlen(*s);
1566 newLine = 0;
1567 } else
1568 break;
1569 }
1570 if (!fgetsReturn)
1571 return NULL;
1572 return (*s);
1573}
void * SDDS_Realloc(void *old_ptr, size_t new_size)
Reallocates memory to a new size.
Definition SDDS_utils.c:743

◆ getMatchingSDDSNames()

epicsShareFuncSDDS char ** getMatchingSDDSNames ( SDDS_DATASET * dataset,
char ** matchName,
int32_t matches,
int32_t * names,
short type )
extern

Retrieves an array of matching SDDS entity names based on specified criteria.

This function processes a list of SDDS entity names (columns, parameters, or arrays) and selects those that match the provided criteria. It supports wildcard matching and exact matching based on the presence of wildcards in the names.

Parameters
[in]datasetPointer to the SDDS_DATASET structure representing the dataset to be searched.
[in]matchNameArray of strings containing the names or patterns to match against the dataset's entities.
[in]matchesThe number of names/patterns provided in matchName.
[out]namesPointer to an int32_t that will be set to the number of matched names.
[in]typeSpecifies the type of SDDS entity to match. Valid values are:
  • SDDS_MATCH_COLUMN
  • SDDS_MATCH_PARAMETER
  • SDDS_MATCH_ARRAY
Returns
  • Returns an array of strings (char **) containing the names of the matched SDDS entities.
  • If no matches are found, returns NULL.
Note
  • The caller is responsible for freeing the memory allocated for the returned array and the individual strings within it.
  • The function uses wild_match for pattern matching when wildcards are present in the matchName entries.
Warning
  • Ensure that the type parameter is correctly specified to match the intended SDDS entity class.
  • Passing an invalid type value will cause the function to terminate the program with an error message.
See also
SDDS_MatchColumns, SDDS_MatchParameters, SDDS_MatchArrays, SDDS_Realloc, SDDS_CopyString

Definition at line 5647 of file SDDS_utils.c.

5647 {
5648 char **name, **selectedName, *ptr = NULL;
5649 int32_t names0 = 0, selected = 0, i, j;
5650 int32_t names32 = 0;
5651
5652 name = selectedName = NULL;
5653 switch (type) {
5654 case SDDS_MATCH_COLUMN:
5655 if (!(name = SDDS_GetColumnNames(dataset, &names0)))
5656 SDDS_PrintErrors(stderr, SDDS_EXIT_PrintErrors | SDDS_VERBOSE_PrintErrors);
5657 break;
5658 case SDDS_MATCH_PARAMETER:
5659 if (!(name = SDDS_GetParameterNames(dataset, &names32)))
5660 SDDS_PrintErrors(stderr, SDDS_EXIT_PrintErrors | SDDS_VERBOSE_PrintErrors);
5661 names0 = names32;
5662 break;
5663 case SDDS_MATCH_ARRAY:
5664 if (!(name = SDDS_GetArrayNames(dataset, &names32)))
5665 SDDS_PrintErrors(stderr, SDDS_EXIT_PrintErrors | SDDS_VERBOSE_PrintErrors);
5666 names0 = names32;
5667 break;
5668 default:
5669 SDDS_Bomb("Invalid match type provided.");
5670 break;
5671 }
5672 for (i = 0; i < matches; i++) {
5673 if (has_wildcards(matchName[i])) {
5674 ptr = expand_ranges(matchName[i]);
5675 for (j = 0; j < names0; j++) {
5676 if (wild_match(name[j], ptr)) {
5677 selectedName = SDDS_Realloc(selectedName, sizeof(*selectedName) * (selected + 1));
5678 SDDS_CopyString(&selectedName[selected], name[j]);
5679 selected++;
5680 }
5681 }
5682 free(ptr);
5683 } else {
5684 if (match_string(matchName[i], name, names0, EXACT_MATCH) < 0) {
5685 fprintf(stderr, "%s not found in input file.\n", matchName[i]);
5686 exit(1);
5687 } else {
5688 selectedName = SDDS_Realloc(selectedName, sizeof(*selectedName) * (selected + 1));
5689 SDDS_CopyString(&selectedName[selected], matchName[i]);
5690 selected++;
5691 }
5692 }
5693 }
5694 SDDS_FreeStringArray(name, names0);
5695 free(name);
5696 *names = selected;
5697 return selectedName;
5698}
int32_t SDDS_FreeStringArray(char **string, int64_t strings)
Frees an array of strings by deallocating each individual string.
char ** SDDS_GetParameterNames(SDDS_DATASET *SDDS_dataset, int32_t *number)
Retrieves the names of all parameters in the SDDS dataset.
char ** SDDS_GetColumnNames(SDDS_DATASET *SDDS_dataset, int32_t *number)
Retrieves the names of all columns in the SDDS dataset.
void SDDS_PrintErrors(FILE *fp, int32_t mode)
Prints recorded error messages to a specified file stream.
Definition SDDS_utils.c:474
void SDDS_Bomb(char *message)
Terminates the program after printing an error message and recorded errors.
Definition SDDS_utils.c:380
char ** SDDS_GetArrayNames(SDDS_DATASET *SDDS_dataset, int32_t *number)
Retrieves the names of all arrays in the SDDS dataset.
int32_t SDDS_CopyString(char **target, const char *source)
Copies a source string to a target string with memory allocation.
Definition SDDS_utils.c:922
long match_string(char *string, char **option, long n_options, long mode)
Matches a given string against an array of option strings based on specified modes.
int has_wildcards(char *template)
Check if a template string contains any wildcard characters.
Definition wild_match.c:498
char * expand_ranges(char *template)
Expand range specifiers in a wildcard template into explicit character lists.
Definition wild_match.c:429
int wild_match(char *string, char *template)
Determine whether one string is a wildcard match for another.
Definition wild_match.c:49

◆ SDDS_AllocateMatrix()

epicsShareFuncSDDS void * SDDS_AllocateMatrix ( int32_t size,
int64_t dim1,
int64_t dim2 )
extern

Allocates a two-dimensional matrix with zero-initialized elements.

This function allocates memory for a two-dimensional matrix based on the specified dimensions and element size. Each row of the matrix is individually allocated and initialized to zero.

Parameters
[in]sizeThe size in bytes of each element in the matrix.
[in]dim1The number of rows in the matrix.
[in]dim2The number of columns in the matrix.
Returns
  • Returns a pointer to the allocated two-dimensional matrix on success.
  • Returns NULL if memory allocation fails.
Note
  • The function uses calloc to ensure that all elements are zero-initialized.
  • The caller is responsible for freeing the allocated memory using SDDS_FreeMatrix.
See also
SDDS_FreeMatrix
calloc

Definition at line 2805 of file SDDS_utils.c.

2805 {
2806 int64_t i;
2807 void **data;
2808
2809 if (!(data = (void **)SDDS_Malloc(sizeof(*data) * dim1)))
2810 return (NULL);
2811 for (i = 0; i < dim1; i++)
2812 if (!(data[i] = (void *)calloc(dim2, size)))
2813 return (NULL);
2814 return (data);
2815}
void * SDDS_Malloc(size_t size)
Allocates memory of a specified size.
Definition SDDS_utils.c:705

◆ SDDS_AppendLayout()

epicsShareFuncSDDS int32_t SDDS_AppendLayout ( SDDS_DATASET * SDDS_target,
SDDS_DATASET * SDDS_source,
uint32_t mode )
extern

Appends layout definitions (columns, parameters, associates, arrays) from one SDDS_DATASET to another. Only definitions that do not already exist in the target dataset are added.

Parameters
SDDS_targetAddress of the SDDS_DATASET structure to which layout definitions will be appended.
SDDS_sourceAddress of the SDDS_DATASET structure from which layout definitions will be taken.
modeMode flag (currently unused; can be set to 0).
Returns
Returns 1 on success; 0 on failure, with an error message recorded.

Definition at line 158 of file SDDS_copy.c.

158 {
159 SDDS_LAYOUT *source;
160 int64_t i;
161
162 if (!SDDS_CheckDataset(SDDS_target, "SDDS_AppendLayout"))
163 return (0);
164 if (!SDDS_CheckDataset(SDDS_source, "SDDS_AppendLayout"))
165 return (0);
166 source = &SDDS_source->layout;
167 SDDS_DeferSavingLayout(SDDS_target, 1);
168
169 for (i = 0; i < source->n_columns; i++)
170 if (SDDS_GetColumnIndex(SDDS_target, source->column_definition[i].name) < 0 &&
171 SDDS_DefineColumn(SDDS_target, source->column_definition[i].name,
172 source->column_definition[i].symbol, source->column_definition[i].units, source->column_definition[i].description, source->column_definition[i].format_string, source->column_definition[i].type, source->column_definition[i].field_length) < 0) {
173 SDDS_DeferSavingLayout(SDDS_target, 0);
174 SDDS_SetError("Unable to define column (SDDS_AppendLayout)");
175 return (0);
176 }
177
178 for (i = 0; i < source->n_parameters; i++)
179 if (SDDS_GetParameterIndex(SDDS_target, source->parameter_definition[i].name) < 0 &&
180 SDDS_DefineParameter(SDDS_target, source->parameter_definition[i].name,
181 source->parameter_definition[i].symbol, source->parameter_definition[i].units, source->parameter_definition[i].description, source->parameter_definition[i].format_string, source->parameter_definition[i].type, source->parameter_definition[i].fixed_value) < 0) {
182 SDDS_DeferSavingLayout(SDDS_target, 0);
183 SDDS_SetError("Unable to define parameter (SDDS_AppendLayout)");
184 return (0);
185 }
186
187 for (i = 0; i < source->n_associates; i++)
188 if (SDDS_GetAssociateIndex(SDDS_target, source->associate_definition[i].name) < 0 &&
189 SDDS_DefineAssociate(SDDS_target, source->associate_definition[i].name, source->associate_definition[i].filename, source->associate_definition[i].path, source->associate_definition[i].description, source->associate_definition[i].contents, source->associate_definition[i].sdds) < 0) {
190 SDDS_DeferSavingLayout(SDDS_target, 0);
191 SDDS_SetError("Unable to define associate (SDDS_AppendLayout)");
192 return (0);
193 }
194
195 for (i = 0; i < source->n_arrays; i++)
196 if (SDDS_GetArrayIndex(SDDS_target, source->array_definition[i].name) < 0 &&
197 SDDS_DefineArray(SDDS_target, source->array_definition[i].name,
198 source->array_definition[i].symbol,
199 source->array_definition[i].units, source->array_definition[i].description,
200 source->array_definition[i].format_string, source->array_definition[i].type, source->array_definition[i].field_length, source->array_definition[i].dimensions, source->array_definition[i].group_name) < 0) {
201 SDDS_DeferSavingLayout(SDDS_target, 0);
202 SDDS_SetError("Unable to define array (SDDS_AppendLayout)");
203 return (0);
204 }
205 SDDS_DeferSavingLayout(SDDS_target, 0);
206 if (!SDDS_SaveLayout(SDDS_target)) {
207 SDDS_SetError("Unable to save layout (SDDS_AppendLayout)");
208 return (0);
209 }
210 return (1);
211}
void SDDS_DeferSavingLayout(SDDS_DATASET *SDDS_dataset, int32_t mode)
Definition SDDS_copy.c:603
int32_t SDDS_SaveLayout(SDDS_DATASET *SDDS_dataset)
Definition SDDS_copy.c:615
int32_t SDDS_DefineAssociate(SDDS_DATASET *SDDS_dataset, const char *name, const char *filename, const char *path, const char *description, const char *contents, int32_t sdds)
Defines an associate for the SDDS dataset.
int32_t SDDS_DefineArray(SDDS_DATASET *SDDS_dataset, const char *name, const char *symbol, const char *units, const char *description, const char *format_string, int32_t type, int32_t field_length, int32_t dimensions, const char *group_name)
Defines a data array within the SDDS dataset.
int32_t SDDS_DefineColumn(SDDS_DATASET *SDDS_dataset, const char *name, const char *symbol, const char *units, const char *description, const char *format_string, int32_t type, int32_t field_length)
Defines a data column within the SDDS dataset.
int32_t SDDS_DefineParameter(SDDS_DATASET *SDDS_dataset, const char *name, const char *symbol, const char *units, const char *description, const char *format_string, int32_t type, char *fixed_value)
Defines a data parameter with a fixed string value.
void SDDS_SetError(char *error_text)
Records an error message in the SDDS error stack.
Definition SDDS_utils.c:421
int32_t SDDS_GetArrayIndex(SDDS_DATASET *SDDS_dataset, char *name)
Retrieves the index of a named array in the SDDS dataset.
int32_t SDDS_GetParameterIndex(SDDS_DATASET *SDDS_dataset, char *name)
Retrieves the index of a named parameter in the SDDS dataset.
int32_t SDDS_GetColumnIndex(SDDS_DATASET *SDDS_dataset, char *name)
Retrieves the index of a named column in the SDDS dataset.
int32_t SDDS_CheckDataset(SDDS_DATASET *SDDS_dataset, const char *caller)
Validates the SDDS dataset pointer.
Definition SDDS_utils.c:618
int32_t SDDS_GetAssociateIndex(SDDS_DATASET *SDDS_dataset, char *name)
Retrieves the index of a named associate in the SDDS dataset.

◆ SDDS_AppendToArrayVararg()

epicsShareFuncSDDS int32_t SDDS_AppendToArrayVararg ( SDDS_DATASET * SDDS_dataset,
char * array_name,
int32_t mode,
void * data_pointer,
int32_t elements,
... )
extern

Appends data to an existing array variable in the SDDS dataset using variable arguments for dimensions.

This function appends additional data to a specified array within the current SDDS dataset. The elements parameter specifies the number of new elements to append. The mode parameter controls how the data is interpreted and stored. The dimensions of the array are provided as variable arguments, allowing for flexible handling of multi-dimensional arrays.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the data set.
array_nameThe name of the array to append data to within the dataset.
modeBitwise flags that determine how the array is set. Valid flags include:
  • SDDS_POINTER_ARRAY: Indicates that the array is a pointer array.
  • SDDS_CONTIGUOUS_DATA: Indicates that the data is contiguous in memory.
data_pointerPointer to the data to be appended to the array. The data must match the type defined for the array.
elementsThe number of elements to append to the array.
...Variable arguments specifying the dimensions of the array. The number of dimensions should match the array definition.
Returns
Returns 1 on successful appending of the array data. On failure, returns 0 and records an appropriate error message.
See also
SDDS_Realloc, SDDS_CopyStringArray, SDDS_SetError, SDDS_GetArrayIndex

Definition at line 1398 of file SDDS_dataprep.c.

1398 {
1399 va_list argptr;
1400 int32_t index, retval, size, startIndex = 0;
1401 SDDS_LAYOUT *layout;
1402 SDDS_ARRAY *array;
1403
1404 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_AppendToArrayVararg"))
1405 return (0);
1406 if (!(mode & SDDS_POINTER_ARRAY) && !(mode & SDDS_CONTIGUOUS_DATA)) {
1407 SDDS_SetError("Unable to set array--invalid mode (SDDS_AppendToArrayVararg)");
1408 return (0);
1409 }
1410 if ((index = SDDS_GetArrayIndex(SDDS_dataset, array_name)) < 0) {
1411 SDDS_SetError("Unable to set array--unknown array name given (SDDS_AppendToArrayVararg)");
1412 return (0);
1413 }
1414 if (!data_pointer) {
1415 SDDS_SetError("Unable to set array--data pointer is NULL (SDDS_AppendToArrayVararg)");
1416 return (0);
1417 }
1418 if (!SDDS_dataset->array) {
1419 SDDS_SetError("Unable to set array--internal array pointer is NULL (SDDS_AppendToArrayVararg)");
1420 return (0);
1421 }
1422
1423 layout = &SDDS_dataset->layout;
1424 array = SDDS_dataset->array + index;
1425 if (!layout->array_definition) {
1426 SDDS_SetError("Unable to set array--internal array definition pointer is NULL (SDDS_AppendToArrayVararg)");
1427 return (0);
1428 }
1429 array->definition = layout->array_definition + index;
1430 if (!array->dimension && !(array->dimension = (int32_t *)SDDS_Malloc(sizeof(*array->dimension) * array->definition->dimensions))) {
1431 SDDS_SetError("Unable to set array--allocation failure (SDDS_SetArrayVararg)");
1432 return (0);
1433 }
1434 if (!(array->definition->dimensions == 1 || mode & SDDS_CONTIGUOUS_DATA)) {
1435 SDDS_SetError("Unable to set array--append operation requires contiguous data (SDDS_AppendToArrayVararg)");
1436 return (0);
1437 }
1438
1439 va_start(argptr, elements);
1440
1441 /* variable arguments are dimensions */
1442 retval = 1;
1443 index = 0;
1444 array->elements = 1;
1445 do {
1446 if ((array->dimension[index] = va_arg(argptr, int32_t)) < 0) {
1447 SDDS_SetError("Unable to set array--negative dimension given (SDDS_AppendToArrayVararg)");
1448 retval = 0;
1449 break;
1450 }
1451 array->elements *= array->dimension[index];
1452 } while (retval == 1 && ++index < array->definition->dimensions);
1453 va_end(argptr);
1454
1455 if (!retval)
1456 return (0);
1457 if (!array->elements)
1458 return (1);
1459
1460 size = SDDS_type_size[array->definition->type - 1];
1461 if (!(array->data = SDDS_Realloc(array->data, size * array->elements))) {
1462 SDDS_SetError("Unable to set array--allocation failure (SDDS_AppendToArrayVararg)");
1463 return (0);
1464 }
1465
1466 startIndex = array->elements - elements;
1467
1468 /* handle 1-d arrays and contiguous data as a special case */
1469 if (array->definition->dimensions == 1 || mode & SDDS_CONTIGUOUS_DATA) {
1470 if (array->definition->type != SDDS_STRING)
1471 memcpy((char *)array->data + size * startIndex, data_pointer, size * elements);
1472 else if (!SDDS_CopyStringArray(((char **)array->data) + startIndex, data_pointer, elements)) {
1473 SDDS_SetError("Unable to set array--string copy failure (SDDS_AppendToArrayVararg)");
1474 return (0);
1475 }
1476 return (1);
1477 }
1478
1479 return (1);
1480}
int32_t SDDS_type_size[SDDS_NUM_TYPES]
Array of sizes for each supported data type.
Definition SDDS_data.c:62
int32_t SDDS_CopyStringArray(char **target, char **source, int64_t n_strings)
Copies an array of strings from source to target.
#define SDDS_STRING
Identifier for the string data type.
Definition SDDStypes.h:85

◆ SDDS_ApplyFactorToColumn()

epicsShareFuncSDDS int32_t SDDS_ApplyFactorToColumn ( SDDS_DATASET * SDDS_dataset,
char * name,
double factor )
extern

Applies a scaling factor to all elements of a specific column in the SDDS dataset.

This function multiplies each value in the specified column by the given factor. It first retrieves the column's index and verifies that it is of a numeric type. The scaling operation is performed in-place on each element of the column's data array.

Parameters
[in]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
[in]nameA NULL-terminated string specifying the name of the column to scale.
[in]factorThe scaling factor to apply to each element of the column.
Returns
  • Returns 1 on successful application of the factor to all elements.
  • Returns 0 if the column is not found, is non-numeric, or if the dataset lacks the necessary data array.
Note
  • The function modifies each element of the column's data array directly within the dataset.
  • It supports various numeric SDDS data types.
See also
SDDS_GetColumnIndex
SDDS_NUMERIC_TYPE
SDDS_SetError

Definition at line 3198 of file SDDS_utils.c.

3198 {
3199 int32_t type, index;
3200 int64_t i;
3201 void *data;
3202
3203 if ((index = SDDS_GetColumnIndex(SDDS_dataset, name)) < 0)
3204 return (0);
3205 type = SDDS_dataset->layout.column_definition[index].type;
3206 if (!SDDS_NUMERIC_TYPE(type)) {
3207 SDDS_SetError("Unable to apply factor to non-numeric column (SDDS_ApplyFactorToColumn)");
3208 return (0);
3209 }
3210 data = SDDS_dataset->data[index];
3211 for (i = 0; i < SDDS_dataset->n_rows; i++) {
3212 switch (type) {
3213 case SDDS_SHORT:
3214 *((short *)data + i) *= factor;
3215 break;
3216 case SDDS_USHORT:
3217 *((unsigned short *)data + i) *= factor;
3218 break;
3219 case SDDS_LONG:
3220 *((int32_t *)data + i) *= factor;
3221 break;
3222 case SDDS_ULONG:
3223 *((uint32_t *)data + i) *= factor;
3224 break;
3225 case SDDS_LONG64:
3226 *((int64_t *)data + i) *= factor;
3227 break;
3228 case SDDS_ULONG64:
3229 *((uint64_t *)data + i) *= factor;
3230 break;
3231 case SDDS_CHARACTER:
3232 *((char *)data + i) *= factor;
3233 break;
3234 case SDDS_FLOAT:
3235 *((float *)data + i) *= factor;
3236 break;
3237 case SDDS_DOUBLE:
3238 *((double *)data + i) *= factor;
3239 break;
3240 case SDDS_LONGDOUBLE:
3241 *((long double *)data + i) *= factor;
3242 break;
3243 default:
3244 return (0);
3245 }
3246 }
3247 return (1);
3248}
#define SDDS_ULONG
Identifier for the unsigned 32-bit integer data type.
Definition SDDStypes.h:67
#define SDDS_FLOAT
Identifier for the float data type.
Definition SDDStypes.h:43
#define SDDS_ULONG64
Identifier for the unsigned 64-bit integer data type.
Definition SDDStypes.h:55
#define SDDS_LONG
Identifier for the signed 32-bit integer data type.
Definition SDDStypes.h:61
#define SDDS_SHORT
Identifier for the signed short integer data type.
Definition SDDStypes.h:73
#define SDDS_CHARACTER
Identifier for the character data type.
Definition SDDStypes.h:91
#define SDDS_USHORT
Identifier for the unsigned short integer data type.
Definition SDDStypes.h:79
#define SDDS_DOUBLE
Identifier for the double data type.
Definition SDDStypes.h:37
#define SDDS_NUMERIC_TYPE(type)
Checks if the given type identifier corresponds to any numeric type.
Definition SDDStypes.h:138
#define SDDS_LONGDOUBLE
Identifier for the long double data type.
Definition SDDStypes.h:31
#define SDDS_LONG64
Identifier for the signed 64-bit integer data type.
Definition SDDStypes.h:49

◆ SDDS_ApplyFactorToParameter()

epicsShareFuncSDDS int32_t SDDS_ApplyFactorToParameter ( SDDS_DATASET * SDDS_dataset,
char * name,
double factor )
extern

Applies a scaling factor to a specific parameter in the SDDS dataset.

This function multiplies the value of a specified parameter by the given factor. It first retrieves the parameter's index and verifies that it is of a numeric type. The scaling operation is performed in-place on the parameter's data.

Parameters
[in]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
[in]nameA NULL-terminated string specifying the name of the parameter to scale.
[in]factorThe scaling factor to apply to the parameter's value.
Returns
  • Returns 1 on successful application of the factor.
  • Returns 0 if the parameter is not found, is non-numeric, or if the dataset lacks the necessary data array.
Note
  • The function modifies the parameter's value directly within the dataset.
  • It supports various numeric SDDS data types.
See also
SDDS_GetParameterIndex
SDDS_NUMERIC_TYPE
SDDS_SetError

Definition at line 3121 of file SDDS_utils.c.

3121 {
3122 int32_t type, index;
3123 void *data;
3124
3125 if ((index = SDDS_GetParameterIndex(SDDS_dataset, name)) < 0)
3126 return (0);
3127 type = SDDS_dataset->layout.parameter_definition[index].type;
3128 if (!SDDS_NUMERIC_TYPE(type)) {
3129 SDDS_SetError("Unable to apply factor to non-numeric parameter (SDDS_ApplyFactorToParameter)");
3130 return (0);
3131 }
3132 if (!SDDS_dataset->parameter) {
3133 SDDS_SetError("Unable to apply factor to parameter--no parameter data array (SDDS_ApplyFactorToParameter)");
3134 return (0);
3135 }
3136 if (!(data = SDDS_dataset->parameter[index])) {
3137 SDDS_SetError("Unable to apply factor to parameter--no data array (SDDS_ApplyFactorToParameter)");
3138 return (0);
3139 }
3140 switch (type) {
3141 case SDDS_SHORT:
3142 *((short *)data) *= factor;
3143 break;
3144 case SDDS_USHORT:
3145 *((unsigned short *)data) *= factor;
3146 break;
3147 case SDDS_LONG:
3148 *((int32_t *)data) *= factor;
3149 break;
3150 case SDDS_ULONG:
3151 *((uint32_t *)data) *= factor;
3152 break;
3153 case SDDS_LONG64:
3154 *((int64_t *)data) *= factor;
3155 break;
3156 case SDDS_ULONG64:
3157 *((uint64_t *)data) *= factor;
3158 break;
3159 case SDDS_CHARACTER:
3160 *((char *)data) *= factor;
3161 break;
3162 case SDDS_FLOAT:
3163 *((float *)data) *= factor;
3164 break;
3165 case SDDS_DOUBLE:
3166 *((double *)data) *= factor;
3167 break;
3168 case SDDS_LONGDOUBLE:
3169 *((long double *)data) *= factor;
3170 break;
3171 default:
3172 return (0);
3173 }
3174 return (1);
3175}

◆ SDDS_ArrayCount()

epicsShareFuncSDDS int32_t SDDS_ArrayCount ( SDDS_DATASET * page)
extern

Retrieves the number of arrays in the SDDS dataset.

This function returns the total count of arrays defined in the layout of the provided SDDS dataset.

Parameters
[in]pagePointer to the SDDS_DATASET structure representing the dataset.
Returns
  • The number of arrays (int32_t) in the dataset.
  • 0 if the provided dataset pointer is NULL.
Note
  • Ensure that the dataset is properly initialized before calling this function.
See also
SDDS_GetArrayIndex, SDDS_CheckArray

Definition at line 5144 of file SDDS_utils.c.

5144 {
5145 if (!page)
5146 return 0;
5147 return page->layout.n_arrays;
5148}

◆ SDDS_AssertColumnFlags()

epicsShareFuncSDDS int32_t SDDS_AssertColumnFlags ( SDDS_DATASET * SDDS_dataset,
uint32_t mode,
... )
extern

Sets acceptance flags for columns based on specified criteria.

This function allows setting column flags in two modes:

  • SDDS_FLAG_ARRAY: Sets flags based on an array of flag values.
  • SDDS_INDEX_LIMITS: Sets flags for a range of columns to a specific value.

A non-zero flag indicates that a column is "of interest", while a zero flag marks it for rejection.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the data set.
modeOperation mode determining how flags are set. Possible values:
  • SDDS_FLAG_ARRAY: c SDDS_AssertColumnFlags(SDDS_DATASET *SDDS_dataset, SDDS_FLAG_ARRAY, int32_t *flagArray, int32_t columnsInArray);
  • SDDS_INDEX_LIMITS: c SDDS_AssertColumnFlags(SDDS_DATASET *SDDS_dataset, SDDS_INDEX_LIMITS, int32_t start, int32_t end, int32_t value);
...Variable arguments based on the selected mode:
  • SDDS_FLAG_ARRAY:
    • int32_t *flagArray: Array of flag values to assign.
    • int32_t columnsInArray: Number of columns in flagArray.
  • SDDS_INDEX_LIMITS:
    • int32_t start: Starting column index (inclusive).
    • int32_t end: Ending column index (inclusive).
    • int32_t value: Flag value to assign to the specified range.
Returns
  • 1 on successful assignment of column flags.
  • 0 on failure, with an error message recorded (e.g., invalid parameters, memory issues).
Note
  • For SDDS_FLAG_ARRAY, if columnsInArray exceeds the number of allocated columns, it is truncated to fit.
  • For SDDS_INDEX_LIMITS, if end exceeds the number of columns, it is adjusted to the last valid column index.
See also
SDDS_SetColumnFlags, SDDS_GetColumnFlags, SDDS_GetColumnFlag

Definition at line 273 of file SDDS_extract.c.

273 {
274 int64_t i, j;
275 int32_t columns, startColumn, endColumn;
276 va_list argptr;
277 int32_t retval;
278 int32_t *flagArray, flagValue;
279
280 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_AssertColumnFlags"))
281 return (0);
282 if ((!SDDS_dataset->column_flag || !SDDS_dataset->column_order) && !SDDS_AllocateColumnFlags(SDDS_dataset))
283 return 0;
284
285 va_start(argptr, mode);
286 retval = 0;
287 switch (mode) {
288 case SDDS_FLAG_ARRAY:
289 if (!(flagArray = va_arg(argptr, int32_t *)))
290 SDDS_SetError("NULL flag array pointer seen (SDDS_AssertColumnFlags)");
291 else if ((columns = va_arg(argptr, int32_t)) < 0)
292 SDDS_SetError("invalid column count seen (SDDS_AssertColumnFlags)");
293 else {
294 if (columns >= SDDS_dataset->layout.n_columns)
295 columns = SDDS_dataset->layout.n_columns - 1;
296 for (i = 0; i < columns; i++)
297 SDDS_dataset->column_flag[i] = flagArray[i];
298 retval = 1;
299 }
300 break;
301 case SDDS_INDEX_LIMITS:
302 if ((startColumn = va_arg(argptr, int32_t)) < 0 || (endColumn = va_arg(argptr, int32_t)) < startColumn)
303 SDDS_SetError("invalid start and end column values (SDDS_AssertColumnFlags)");
304 else {
305 flagValue = va_arg(argptr, int32_t);
306 if (endColumn >= SDDS_dataset->layout.n_columns || endColumn < 0)
307 endColumn = SDDS_dataset->layout.n_columns - 1;
308 for (i = startColumn; i <= endColumn; i++)
309 SDDS_dataset->column_flag[i] = flagValue;
310 retval = 1;
311 }
312 break;
313 default:
314 SDDS_SetError("unknown mode passed (SDDS_AssertColumnFlags)");
315 break;
316 }
317 va_end(argptr);
318
319 for (i = j = 0; i < SDDS_dataset->layout.n_columns; i++) {
320 if (SDDS_dataset->column_flag[i])
321 SDDS_dataset->column_order[j++] = i;
322 }
323
324 SDDS_dataset->n_of_interest = j;
325
326 return retval;
327}
int32_t SDDS_AllocateColumnFlags(SDDS_DATASET *SDDS_target)

◆ SDDS_AssertRowFlags()

epicsShareFuncSDDS int32_t SDDS_AssertRowFlags ( SDDS_DATASET * SDDS_dataset,
uint32_t mode,
... )
extern

Sets acceptance flags for rows based on specified criteria.

This function allows setting row flags in two modes:

  • SDDS_FLAG_ARRAY: Sets flags based on an array of flag values.
  • SDDS_INDEX_LIMITS: Sets flags for a range of rows to a specific value.

A non-zero flag indicates that a row is "of interest", while a zero flag marks it for rejection.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the data set.
modeOperation mode determining how flags are set. Possible values:
  • SDDS_FLAG_ARRAY: c SDDS_AssertRowFlags(SDDS_DATASET *SDDS_dataset, SDDS_FLAG_ARRAY, int32_t *flagArray, int64_t rowsInArray);
  • SDDS_INDEX_LIMITS: c SDDS_AssertRowFlags(SDDS_DATASET *SDDS_dataset, SDDS_INDEX_LIMITS, int64_t start, int64_t end, int32_t value);
...Variable arguments based on the selected mode:
  • SDDS_FLAG_ARRAY:
    • int32_t *flagArray: Array of flag values to assign.
    • int64_t rowsInArray: Number of rows in flagArray.
  • SDDS_INDEX_LIMITS:
    • int64_t start: Starting row index (inclusive).
    • int64_t end: Ending row index (inclusive).
    • int32_t value: Flag value to assign to the specified range.
Returns
  • 1 on successful assignment of row flags.
  • 0 on failure, with an error message recorded (e.g., invalid parameters, memory issues).
Note
  • For SDDS_FLAG_ARRAY, if rowsInArray exceeds the number of allocated rows, it is truncated to fit.
  • For SDDS_INDEX_LIMITS, if end exceeds the number of rows, it is adjusted to the last valid row index.
See also
SDDS_SetRowFlags, SDDS_GetRowFlags, SDDS_GetRowFlag

Definition at line 148 of file SDDS_extract.c.

154{
155 int64_t i, rows, startRow, endRow;
156 va_list argptr;
157 int32_t retval;
158 int32_t *flagArray, flagValue;
159 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_AssertRowFlags"))
160 return (0);
161
162 va_start(argptr, mode);
163 retval = 0;
164 switch (mode) {
165 case SDDS_FLAG_ARRAY:
166 if (!(flagArray = va_arg(argptr, int32_t *)))
167 SDDS_SetError("NULL flag array pointer seen (SDDS_AssertRowFlags)");
168 else if ((rows = va_arg(argptr, int64_t)) < 0)
169 SDDS_SetError("invalid row count seen (SDDS_AssertRowFlags)");
170 else {
171 if (rows >= SDDS_dataset->n_rows)
172 rows = SDDS_dataset->n_rows;
173 for (i = 0; i < rows; i++)
174 SDDS_dataset->row_flag[i] = flagArray[i];
175 retval = 1;
176 }
177 break;
178 case SDDS_INDEX_LIMITS:
179 if ((startRow = va_arg(argptr, int64_t)) < 0 || (endRow = va_arg(argptr, int64_t)) < startRow)
180 SDDS_SetError("invalid start and end row values (SDDS_AssertRowFlags)");
181 else {
182 flagValue = va_arg(argptr, int32_t);
183 if (endRow >= SDDS_dataset->n_rows || endRow < 0)
184 endRow = SDDS_dataset->n_rows - 1;
185 for (i = startRow; i <= endRow; i++)
186 SDDS_dataset->row_flag[i] = flagValue;
187 retval = 1;
188 }
189 break;
190 default:
191 SDDS_SetError("unknown mode passed (SDDS_AssertRowFlags)");
192 break;
193 }
194
195 va_end(argptr);
196 return retval;
197}

◆ SDDS_Bomb()

epicsShareFuncSDDS void SDDS_Bomb ( char * message)
extern

Terminates the program after printing an error message and recorded errors.

This function prints a termination message to stderr, invokes SDDS_PrintErrors to display all recorded errors, and then exits the program with a non-zero status.

Parameters
[in]messageThe termination message to be printed. If NULL, a default message "?" is used.
Note
This function does not return; it exits the program.
See also
SDDS_PrintErrors
SDDS_SetError

Definition at line 380 of file SDDS_utils.c.

380 {
381 char *programName = SDDS_GetRegisteredProgramNameCopy();
382 if (programName)
383 fprintf(stderr, "Error (%s): %s\n", programName, message ? message : "?");
384 else
385 fprintf(stderr, "Error: %s\n", message ? message : "?");
386 free(programName);
387 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
388 exit(1);
389}

◆ SDDS_BreakIntoLockedFile()

epicsShareFuncSDDS int32_t SDDS_BreakIntoLockedFile ( char * filename)
extern

Attempts to override a locked file by creating a temporary copy.

This function tries to break into a locked file by creating a temporary backup and replacing the original file with this backup. The process involves:

  • Generating a temporary filename with a .blXXX suffix, where XXX ranges from 1000 to 1019.
  • Copying the original file to the temporary file while preserving file attributes.
  • Replacing the original file with the temporary copy.

On Windows systems (_WIN32 defined), the function currently does not support breaking into locked files and will output an error message.

Parameters
[in]filenameThe path to the locked file that needs to be overridden.
Returns
  • 0 on successful override of the locked file.
  • 1 if the operation fails or is not supported on the current platform.
Warning
  • The function limits the filename length to 500 characters to prevent buffer overflows.
  • Ensure that the necessary permissions are available to create and modify files in the target directory.
Note
  • This function relies on the availability of the cp and mv system commands on Unix-like systems.
  • The function attempts up to 20 different temporary filenames before failing.
See also
SDDS_FileIsLocked, SDDS_LockFile

Definition at line 3447 of file SDDS_utils.c.

3447 {
3448#if defined(_WIN32)
3449 fprintf(stderr, "Unable to break into locked file\n");
3450 return (1);
3451#else
3452 char buffer[1024];
3453 int i = 1000, j = 0;
3454 FILE *fp;
3455
3456 /* limit filename length to 500 so we don't overflow the buffer variable */
3457 if (strlen(filename) > 500) {
3458 fprintf(stderr, "Unable to break into locked file\n");
3459 return (1);
3460 }
3461
3462 /* find a temporary file name that is not already in use */
3463 for (i = 1000; i < 1020; i++) {
3464 sprintf(buffer, "%s.bl%d", filename, i);
3465 if ((fp = fopen(buffer, "r"))) {
3466 fclose(fp);
3467 } else {
3468 j = i;
3469 break;
3470 }
3471 }
3472
3473 /* if no temporary file names could be found then return with an error message */
3474 if (j == 0) {
3475 fprintf(stderr, "Unable to break into locked file\n");
3476 return (1);
3477 }
3478
3479 /* copy the original file to the temp file name and preserve the attributes */
3480 /* the temp file name has to be in the same directory to preserve ACL settings */
3481 sprintf(buffer, "cp -p %s %s.bl%d", filename, filename, j);
3482 if (system(buffer) == -1) {
3483 fprintf(stderr, "Unable to break into locked file\n");
3484 return (1);
3485 }
3486
3487 /* move the temp file on top of the original file */
3488 sprintf(buffer, "mv -f %s.bl%d %s", filename, j, filename);
3489 if (system(buffer) == -1) {
3490 fprintf(stderr, "Unable to break into locked file\n");
3491 return (1);
3492 }
3493 return (0);
3494#endif
3495}

◆ SDDS_BufferedRead()

epicsShareFuncSDDS int32_t SDDS_BufferedRead ( void * target,
int64_t targetSize,
FILE * fp,
SDDS_FILEBUFFER * fBuffer,
int32_t type,
int32_t byteOrder )
extern

Reads data from a file into a buffer, optimizing performance with buffering.

This function reads targetSize bytes from the file fp into the memory pointed to by target. It uses the provided fBuffer to buffer file data, improving read performance. If the data type is SDDS_LONGDOUBLE and the long double precision is not 18 digits, it handles conversion to double precision if the environment variable SDDS_LONGDOUBLE_64BITS is not set.

If target is NULL, the function skips over targetSize bytes in the file.

Parameters
targetPointer to the memory location where the data will be stored. If NULL, the data is skipped.
targetSizeThe number of bytes to read from the file.
fpThe file pointer from which data is read.
fBufferPointer to an SDDS_FILEBUFFER structure used for buffering file data.
typeThe SDDS data type of the data being read (e.g., SDDS_LONGDOUBLE).
byteOrderThe byte order of the data (SDDS_LITTLEENDIAN or SDDS_BIGENDIAN).
Returns
Returns 1 on success; returns 0 on error.

Definition at line 114 of file SDDS_binary.c.

114 {
115 int float80tofloat64 = 0;
116 if ((LDBL_DIG != 18) && (type == SDDS_LONGDOUBLE)) {
117 if (getenv("SDDS_LONGDOUBLE_64BITS") == NULL) {
118 targetSize *= 2;
119 float80tofloat64 = 1;
120 }
121 }
122 if (!fBuffer->bufferSize) {
123 /* just read into users buffer or seek if no buffer given */
124 if (!target)
125 return !fseek(fp, (long)targetSize, SEEK_CUR);
126 else {
127 if (float80tofloat64) {
128 unsigned char x[16];
129 double d;
130 int64_t shift = 0;
131 while (shift < targetSize) {
132 if (fread(&x, (size_t)1, 16, fp) != 16)
133 return 0;
134 d = makeFloat64FromFloat80(x, byteOrder);
135 memcpy((char *)target + shift, &d, 8);
136 shift += 16;
137 }
138 return 1;
139 } else {
140 return fread(target, (size_t)1, (size_t)targetSize, fp) == targetSize;
141 }
142 }
143 }
144 if ((fBuffer->bytesLeft -= targetSize) >= 0) {
145 /* sufficient data is already in the buffer */
146 if (target) {
147 if (float80tofloat64) {
148 unsigned char x[16];
149 double d;
150 int64_t shift = 0;
151 while (shift < targetSize) {
152 memcpy(x, (char *)fBuffer->data + shift, 16);
153 d = makeFloat64FromFloat80(x, byteOrder);
154 memcpy((char *)target + shift, &d, 8);
155 shift += 16;
156 }
157 } else {
158 memcpy((char *)target, (char *)fBuffer->data, targetSize);
159 }
160 }
161 fBuffer->data += targetSize;
162 return 1;
163 } else {
164 /* need to read additional data into buffer */
165 int64_t bytesNeeded, offset;
166 fBuffer->bytesLeft += targetSize; /* adds back amount subtracted above */
167
168 /* first, use the data that is already available. this cleans out the buffer */
169 if ((offset = fBuffer->bytesLeft)) {
170 /* some data is available in the buffer */
171 if (target) {
172 if (float80tofloat64) {
173 unsigned char x[16];
174 double d;
175 int64_t shift = 0;
176 while (shift < offset) {
177 memcpy(x, (char *)fBuffer->data + shift, 16);
178 d = makeFloat64FromFloat80(x, byteOrder);
179 memcpy((char *)target + shift, &d, 8);
180 shift += 16;
181 }
182 } else {
183 memcpy((char *)target, (char *)fBuffer->data, offset);
184 }
185 }
186 bytesNeeded = targetSize - offset;
187 fBuffer->bytesLeft = 0;
188 } else {
189 bytesNeeded = targetSize;
190 }
191 fBuffer->data = fBuffer->buffer;
192
193 if (fBuffer->bufferSize < bytesNeeded) {
194 /* just read what is needed directly into user's memory or seek */
195 if (!target)
196 return !fseek(fp, (long)bytesNeeded, SEEK_CUR);
197 else {
198 if (float80tofloat64) {
199 unsigned char x[16];
200 double d;
201 int64_t shift = 0;
202 while (shift < bytesNeeded) {
203 if (fread(&x, (size_t)1, 16, fp) != 16)
204 return 0;
205 d = makeFloat64FromFloat80(x, byteOrder);
206 memcpy((char *)target + offset + shift, &d, 8);
207 shift += 16;
208 }
209 return 1;
210 } else {
211 return fread((char *)target + offset, (size_t)1, (size_t)bytesNeeded, fp) == bytesNeeded;
212 }
213 }
214 }
215
216 /* fill the buffer */
217 if ((fBuffer->bytesLeft = fread(fBuffer->data, (size_t)1, (size_t)fBuffer->bufferSize, fp)) < bytesNeeded)
218 return 0;
219 if (target) {
220 if (float80tofloat64) {
221 unsigned char x[16];
222 double d;
223 int64_t shift = 0;
224 while (shift < bytesNeeded) {
225 memcpy(x, (char *)fBuffer->data + shift, 16);
226 d = makeFloat64FromFloat80(x, byteOrder);
227 memcpy((char *)target + offset + shift, &d, 8);
228 shift += 16;
229 }
230 } else {
231 memcpy((char *)target + offset, (char *)fBuffer->data, bytesNeeded);
232 }
233 }
234 fBuffer->data += bytesNeeded;
235 fBuffer->bytesLeft -= bytesNeeded;
236 return 1;
237 }
238}
double makeFloat64FromFloat80(unsigned char x[16], int32_t byteOrder)
Converts a 16-byte array representing a float80 value to a double.

◆ SDDS_BufferedWrite()

epicsShareFuncSDDS int32_t SDDS_BufferedWrite ( void * target,
int64_t targetSize,
FILE * fp,
SDDS_FILEBUFFER * fBuffer )
extern

Writes data to a file using a buffer to optimize performance.

This function writes targetSize bytes from the memory pointed to by target to the file fp. It uses the provided fBuffer to buffer file data, improving write performance. If the buffer is full, it flushes the buffer to the file before writing more data.

Parameters
targetPointer to the memory location of the data to write.
targetSizeThe number of bytes to write to the file.
fpThe file pointer to which data is written.
fBufferPointer to an SDDS_FILEBUFFER structure used for buffering file data.
Returns
Returns 1 on success; returns 0 on error.

Definition at line 502 of file SDDS_binary.c.

502 {
503 if (!fBuffer->bufferSize) {
504 return fwrite(target, (size_t)1, (size_t)targetSize, fp) == targetSize;
505 }
506 if ((fBuffer->bytesLeft -= targetSize) >= 0) {
507 memcpy((char *)fBuffer->data, (char *)target, targetSize);
508 fBuffer->data += targetSize;
509#ifdef DEBUG
510 fprintf(stderr, "SDDS_BufferedWrite of %" PRId64 " bytes done in-memory, %" PRId64 " bytes left\n", targetSize, fBuffer->bytesLeft);
511#endif
512 return 1;
513 } else {
514 int64_t lastLeft;
515 /* add back what was subtracted in test above.
516 * lastLeft is the number of bytes left in the buffer before doing anything
517 * and also the number of bytes from the users data that get copied into the buffer.
518 */
519 lastLeft = (fBuffer->bytesLeft += targetSize);
520 /* copy part of the data into the buffer and write the buffer out */
521 memcpy((char *)fBuffer->data, (char *)target, (size_t)fBuffer->bytesLeft);
522 if (fwrite(fBuffer->buffer, (size_t)1, (size_t)fBuffer->bufferSize, fp) != fBuffer->bufferSize)
523 return 0;
524 if (fflush(fp)) {
525 SDDS_SetError("Problem flushing file (SDDS_BufferedWrite)");
526 SDDS_SetError(strerror(errno));
527 return 0;
528 }
529 /* reset the data pointer and the bytesLeft value.
530 * also, determine if the remaining data is too large for the buffer.
531 * if so, just write it out.
532 */
533 fBuffer->data = fBuffer->buffer;
534 if ((targetSize -= lastLeft) > (fBuffer->bytesLeft = fBuffer->bufferSize)) {
535 return fwrite((char *)target + lastLeft, (size_t)1, (size_t)targetSize, fp) == targetSize;
536 }
537 /* copy remaining data into the buffer.
538 * could do this with a recursive call, but this is more efficient.
539 */
540 memcpy((char *)fBuffer->data, (char *)target + lastLeft, targetSize);
541 fBuffer->data += targetSize;
542 fBuffer->bytesLeft -= targetSize;
543 return 1;
544 }
545}

◆ SDDS_Calloc()

epicsShareFuncSDDS void * SDDS_Calloc ( size_t nelem,
size_t elem_size )
extern

Allocates zero-initialized memory for an array of elements.

This function is a wrapper around the standard calloc function, used by SDDS routines to allocate memory. It ensures that even if the requested number of elements or element size is zero or negative, a minimum of 1 element with a size of 4 bytes is allocated.

Parameters
[in]nelemNumber of elements to allocate.
[in]elem_sizeSize in bytes of each element.
Returns
Pointer to the allocated memory. If allocation fails, returns NULL.
Note
If nelem or elem_size is less than or equal to zero, the function allocates memory for one element of 4 bytes by default.
See also
SDDS_Malloc
SDDS_Free

Definition at line 683 of file SDDS_utils.c.

683 {
684 if (elem_size <= 0)
685 elem_size = 4;
686 if (nelem <= 0)
687 nelem = 1;
688 return calloc(nelem, elem_size);
689}

◆ SDDS_CastValue()

epicsShareFuncSDDS void * SDDS_CastValue ( void * data,
int64_t index,
int32_t data_type,
int32_t desired_type,
void * memory )
extern

Casts a value from one SDDS data type to another.

This function converts a value from its original SDDS data type (data_type) to a desired SDDS data type (desired_type). It retrieves the value at the specified index from the data array and stores the converted value in the provided memory location.

Parameters
[in]dataPointer to the data array containing the original values.
[in]indexThe zero-based index of the value to be casted within the data array.
[in]data_typeThe original SDDS data type of the value. Must be one of the SDDS type constants:
  • SDDS_SHORT
  • SDDS_USHORT
  • SDDS_LONG
  • SDDS_ULONG
  • SDDS_LONG64
  • SDDS_ULONG64
  • SDDS_CHARACTER
  • SDDS_FLOAT
  • SDDS_DOUBLE
  • SDDS_LONGDOUBLE
[in]desired_typeThe desired SDDS data type to which the value should be casted. Must be one of the SDDS type constants listed above.
[out]memoryPointer to the memory location where the casted value will be stored.
Returns
  • Returns a pointer to the memory location containing the casted value on success.
  • Returns NULL if the casting fails due to invalid data types or other errors.
Note
  • The function does not handle casting for SDDS_STRING types.
  • The caller must ensure that the memory location has sufficient space to store the casted value.
See also
SDDS_CopyString
SDDS_SetError

Definition at line 2694 of file SDDS_utils.c.

2694 {
2695 long long integer_value;
2696 long double fp_value;
2697 if (!data || !memory || data_type == SDDS_STRING || desired_type == SDDS_STRING)
2698 return (NULL);
2699 if (data_type == desired_type) {
2700 memcpy(memory, (char *)data + SDDS_type_size[data_type - 1] * index, SDDS_type_size[data_type - 1]);
2701 return (memory);
2702 }
2703 switch (data_type) {
2704 case SDDS_SHORT:
2705 integer_value = *((short *)data + index);
2706 fp_value = integer_value;
2707 break;
2708 case SDDS_USHORT:
2709 integer_value = *((unsigned short *)data + index);
2710 fp_value = integer_value;
2711 break;
2712 case SDDS_LONG:
2713 integer_value = *((int32_t *)data + index);
2714 fp_value = integer_value;
2715 break;
2716 case SDDS_ULONG:
2717 integer_value = *((uint32_t *)data + index);
2718 fp_value = integer_value;
2719 break;
2720 case SDDS_LONG64:
2721 integer_value = *((int64_t *)data + index);
2722 fp_value = integer_value;
2723 break;
2724 case SDDS_ULONG64:
2725 integer_value = *((uint64_t *)data + index);
2726 fp_value = integer_value;
2727 break;
2728 case SDDS_CHARACTER:
2729 integer_value = *((unsigned char *)data + index);
2730 fp_value = integer_value;
2731 break;
2732 case SDDS_FLOAT:
2733 fp_value = *((float *)data + index);
2734 integer_value = fp_value;
2735 break;
2736 case SDDS_DOUBLE:
2737 fp_value = *((double *)data + index);
2738 integer_value = fp_value;
2739 break;
2740 case SDDS_LONGDOUBLE:
2741 fp_value = *((long double *)data + index);
2742 integer_value = fp_value;
2743 break;
2744 default:
2745 return (NULL);
2746 }
2747 switch (desired_type) {
2748 case SDDS_CHARACTER:
2749 *((char *)memory) = integer_value;
2750 break;
2751 case SDDS_SHORT:
2752 *((short *)memory) = integer_value;
2753 break;
2754 case SDDS_USHORT:
2755 *((unsigned short *)memory) = integer_value;
2756 break;
2757 case SDDS_LONG:
2758 *((int32_t *)memory) = integer_value;
2759 break;
2760 case SDDS_ULONG:
2761 *((uint32_t *)memory) = integer_value;
2762 break;
2763 case SDDS_LONG64:
2764 *((int64_t *)memory) = integer_value;
2765 break;
2766 case SDDS_ULONG64:
2767 *((uint64_t *)memory) = integer_value;
2768 break;
2769 case SDDS_FLOAT:
2770 *((float *)memory) = fp_value;
2771 break;
2772 case SDDS_DOUBLE:
2773 *((double *)memory) = fp_value;
2774 break;
2775 case SDDS_LONGDOUBLE:
2776 *((long double *)memory) = fp_value;
2777 break;
2778 default:
2779 SDDS_SetError("The impossible has happened (SDDS_CastValue)");
2780 return (NULL);
2781 }
2782 return (memory);
2783}

◆ SDDS_ChangeArrayInformation()

epicsShareFuncSDDS int32_t SDDS_ChangeArrayInformation ( SDDS_DATASET * SDDS_dataset,
char * field_name,
void * memory,
int32_t mode,
... )
extern

Modifies a specific field in an array definition within the SDDS dataset.

This function allows you to change a particular field of an array definition, identified either by its name or index. The new value for the field can be provided either as a direct value or as a string, depending on the field type.

Parameters
[in]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
[in]field_nameA null-terminated string specifying the name of the field to be modified.
[in]memoryPointer to the new value for the field. The type of this pointer should correspond to the data type of the field being modified:
  • For non-string fields, provide a pointer to the appropriate data type (e.g., int32_t*, double*).
  • For string fields, provide a char*.
[in]modeA bitwise combination of the following constants to specify how to identify the array and how to pass the new value:
  • SDDS_SET_BY_INDEX: Identify the array by its index. Requires an additional argument of type int32_t (array index).
  • SDDS_SET_BY_NAME: Identify the array by its name. Requires an additional argument of type char* (array name).
  • SDDS_PASS_BY_VALUE: The new value is provided as a direct value (non-string fields).
  • SDDS_PASS_BY_STRING: The new value is provided as a string (string fields).

The valid combinations of mode are:

Returns
On success, returns the SDDS data type of the modified information. On failure, returns zero and records an error message.
Note
This function uses variable arguments to accept either the array name or index based on the mode parameter.
See also
SDDS_GetArrayInformation

Definition at line 597 of file SDDS_info.c.

597 {
598 int32_t field_index, type, array_index, givenType;
599 ARRAY_DEFINITION *arraydef;
600 char *array_name;
601 va_list argptr;
602 int32_t retval;
603 double buffer[4];
604
605 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_ChangeArrayInformation"))
606 return (0);
607
608 if (!field_name) {
609 SDDS_SetError("NULL field name passed. (SDDS_ChangeArrayInformation)");
610 return (0);
611 }
612
613 va_start(argptr, mode);
614 retval = 1;
615 if (mode & SDDS_SET_BY_INDEX) {
616 if ((array_index = va_arg(argptr, int32_t)) < 0 || array_index >= SDDS_dataset->layout.n_arrays) {
617 SDDS_SetError("Invalid array index passed. (SDDS_ChangeArrayInformation)");
618 retval = 0;
619 }
620 } else {
621 if (!(array_name = va_arg(argptr, char *))) {
622 SDDS_SetError("NULL array name passed. (SDDS_ChangeArrayInformation)");
623 retval = 0;
624 }
625 if ((array_index = SDDS_GetArrayIndex(SDDS_dataset, array_name)) < 0) {
626 SDDS_SetError("Unknown array name given (SDDS_ChangeArrayInformation)");
627 retval = 0;
628 }
629 }
630 arraydef = SDDS_dataset->layout.array_definition + array_index;
631 va_end(argptr);
632 if (!retval)
633 return (0);
634
635 for (field_index = 0; field_index < SDDS_ARRAY_FIELDS; field_index++)
636 if (strcmp(field_name, SDDS_ArrayFieldInformation[field_index].name) == 0)
637 break;
638 if (field_index == SDDS_ARRAY_FIELDS) {
639 SDDS_SetError("Unknown field name given (SDDS_ChangeArrayInformation)");
640 return (0);
641 }
642 type = SDDS_ArrayFieldInformation[field_index].type;
643 if (!memory)
644 return (type);
645 if (type == SDDS_STRING) {
646 if (!SDDS_CopyString(((char **)((char *)arraydef + SDDS_ArrayFieldInformation[field_index].offset)), (char *)memory)) {
647 SDDS_SetError("Unable to copy field data (SDDS_ChangeArrayInformation)");
648 return (0);
649 }
650 if (strcmp(field_name, "name") == 0)
651 qsort((char *)SDDS_dataset->layout.array_index, SDDS_dataset->layout.n_arrays, sizeof(*SDDS_dataset->layout.array_index), SDDS_CompareIndexedNamesPtr);
652 } else {
653 if (mode & SDDS_PASS_BY_STRING) {
654 if (strcmp(field_name, "type") == 0 && (givenType = SDDS_IdentifyType((char *)memory)) > 0)
655 /* the type has been passed as a string (e.g., "double") */
656 memcpy((char *)buffer, (char *)&givenType, sizeof(givenType));
657 else if (!SDDS_ScanData((char *)memory, type, 0, (void *)buffer, 0, 0)) {
658 SDDS_SetError("Unable to scan string data (SDDS_ChangeArrayInformation)");
659 return (0);
660 }
661 memcpy((char *)arraydef + SDDS_ArrayFieldInformation[field_index].offset, (void *)buffer, SDDS_type_size[type - 1]);
662 } else
663 memcpy((char *)arraydef + SDDS_ArrayFieldInformation[field_index].offset, memory, SDDS_type_size[type - 1]);
664 }
665
666 return (type);
667}
int32_t SDDS_ScanData(char *string, int32_t type, int32_t field_length, void *data, int64_t index, int32_t is_parameter)
Scans a string and saves the parsed value into a data pointer according to the specified data type.
SDDS_FIELD_INFORMATION SDDS_ArrayFieldInformation[SDDS_ARRAY_FIELDS]
Field information for array definitions.
Definition SDDS_data.c:175
int SDDS_CompareIndexedNamesPtr(const void *s1, const void *s2)
Compares two pointers to SORTED_INDEX structures by their name fields.
int32_t SDDS_IdentifyType(char *typeName)
Identifies the SDDS data type based on its string name.

◆ SDDS_ChangeColumnInformation()

epicsShareFuncSDDS int32_t SDDS_ChangeColumnInformation ( SDDS_DATASET * SDDS_dataset,
char * field_name,
void * memory,
int32_t mode,
... )
extern

Modifies a specific field in a column definition within the SDDS dataset.

This function allows you to change a particular field of a column definition, identified either by its name or index. The new value for the field can be provided either as a direct value or as a string, depending on the field type.

Parameters
[in]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
[in]field_nameA null-terminated string specifying the name of the field to be modified.
[in]memoryPointer to the new value for the field. The type of this pointer should correspond to the data type of the field being modified:
  • For non-string fields, provide a pointer to the appropriate data type (e.g., int32_t*, double*).
  • For string fields, provide a char*.
[in]modeA bitwise combination of the following constants to specify how to identify the column and how to pass the new value:
  • SDDS_SET_BY_INDEX: Identify the column by its index. Requires an additional argument of type int32_t (column index).
  • SDDS_SET_BY_NAME: Identify the column by its name. Requires an additional argument of type char* (column name).
  • SDDS_PASS_BY_VALUE: The new value is provided as a direct value (non-string fields).
  • SDDS_PASS_BY_STRING: The new value is provided as a string (string fields).

The valid combinations of mode are:

Returns
On success, returns the SDDS data type of the modified information. On failure, returns zero and records an error message.
Note
This function uses variable arguments to accept either the column name or index based on the mode parameter.
See also
SDDS_GetColumnInformation

Definition at line 364 of file SDDS_info.c.

364 {
365 int32_t field_index, type, givenType;
366 int32_t i, column_index;
367 COLUMN_DEFINITION *columndef;
368 char *column_name;
369 va_list argptr;
370 int32_t retval;
371 double buffer[4];
372
373 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_ChangeColumnInformation"))
374 return (0);
375
376 if (!field_name) {
377 SDDS_SetError("NULL field name passed. (SDDS_ChangeColumnInformation)");
378 return (0);
379 }
380
381 va_start(argptr, mode);
382 retval = 1;
383 if (mode & SDDS_SET_BY_INDEX) {
384 if ((column_index = va_arg(argptr, int32_t)) < 0 || column_index >= SDDS_dataset->layout.n_columns) {
385 SDDS_SetError("Invalid column index passed. (SDDS_ChangeColumnInformation)");
386 retval = 0;
387 }
388 } else {
389 if (!(column_name = va_arg(argptr, char *))) {
390 SDDS_SetError("NULL column name passed. (SDDS_ChangeColumnInformation)");
391 retval = 0;
392 }
393 if ((column_index = SDDS_GetColumnIndex(SDDS_dataset, column_name)) < 0) {
394 SDDS_SetError("Unknown column name given (SDDS_ChangeColumnInformation)");
395 retval = 0;
396 }
397 }
398 columndef = SDDS_dataset->layout.column_definition + column_index;
399 va_end(argptr);
400 if (!retval)
401 return (0);
402
403 for (field_index = 0; field_index < SDDS_COLUMN_FIELDS; field_index++)
404 if (strcmp(field_name, SDDS_ColumnFieldInformation[field_index].name) == 0)
405 break;
406 if (field_index == SDDS_COLUMN_FIELDS) {
407 SDDS_SetError("Unknown field name given (SDDS_ChangeColumnInformation)");
408 return (0);
409 }
410 type = SDDS_ColumnFieldInformation[field_index].type;
411 if (!memory)
412 return (type);
413 if (type == SDDS_STRING) {
414 if (!SDDS_CopyString(((char **)((char *)columndef + SDDS_ColumnFieldInformation[field_index].offset)), (char *)memory)) {
415 SDDS_SetError("Unable to copy field data (SDDS_ChangeColumnInformation)");
416 return (0);
417 }
418 if (strcmp(field_name, "name") == 0) {
419 for (i = 0; i < SDDS_dataset->layout.n_columns; i++)
420 if (column_index == SDDS_dataset->layout.column_index[i]->index)
421 break;
422 if (i == SDDS_dataset->layout.n_columns) {
423 SDDS_SetError("Unable to copy field data--column indexing problem (SDDS_ChangeColumnInformation)");
424 return (0);
425 }
426 SDDS_dataset->layout.column_index[i]->name = SDDS_dataset->layout.column_definition[column_index].name;
427 qsort((char *)SDDS_dataset->layout.column_index, SDDS_dataset->layout.n_columns, sizeof(*SDDS_dataset->layout.column_index), SDDS_CompareIndexedNamesPtr);
428 }
429 } else {
430 if (mode & SDDS_PASS_BY_STRING) {
431 if (strcmp(field_name, "type") == 0 && (givenType = SDDS_IdentifyType((char *)memory)) > 0)
432 /* the type has been passed as a string (e.g., "double") */
433 memcpy((char *)buffer, (char *)&givenType, sizeof(givenType));
434 else if (!SDDS_ScanData((char *)memory, type, 0, (void *)buffer, 0, 0)) {
435 SDDS_SetError("Unable to scan string data (SDDS_ChangeColumnInformation)");
436 return (0);
437 }
438 memcpy((char *)columndef + SDDS_ColumnFieldInformation[field_index].offset, (void *)buffer, SDDS_type_size[type - 1]);
439 } else
440 memcpy((char *)columndef + SDDS_ColumnFieldInformation[field_index].offset, memory, SDDS_type_size[type - 1]);
441 }
442 return (type);
443}
SDDS_FIELD_INFORMATION SDDS_ColumnFieldInformation[SDDS_COLUMN_FIELDS]
Field information for column definitions.
Definition SDDS_data.c:193

◆ SDDS_ChangeParameterInformation()

epicsShareFuncSDDS int32_t SDDS_ChangeParameterInformation ( SDDS_DATASET * SDDS_dataset,
char * field_name,
void * memory,
int32_t mode,
... )
extern

Modifies a specific field in a parameter definition within the SDDS dataset.

This function allows you to change a particular field of a parameter definition, identified either by its name or index. The new value for the field can be provided either as a direct value or as a string, depending on the field type.

Parameters
[in]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
[in]field_nameA null-terminated string specifying the name of the field to be modified.
[in]memoryPointer to the new value for the field. The type of this pointer should correspond to the data type of the field being modified:
  • For non-string fields, provide a pointer to the appropriate data type (e.g., int32_t*, double*).
  • For string fields, provide a char*.
[in]modeA bitwise combination of the following constants to specify how to identify the parameter and how to pass the new value:
  • SDDS_SET_BY_INDEX: Identify the parameter by its index. Requires an additional argument of type int32_t (parameter index).
  • SDDS_SET_BY_NAME: Identify the parameter by its name. Requires an additional argument of type char* (parameter name).
  • SDDS_PASS_BY_VALUE: The new value is provided as a direct value (non-string fields).
  • SDDS_PASS_BY_STRING: The new value is provided as a string (string fields).

The valid combinations of mode are:

Returns
On success, returns the SDDS data type of the modified information. On failure, returns zero and records an error message.
Note
This function uses variable arguments to accept either the parameter name or index based on the mode parameter.
See also
SDDS_GetParameterInformation

Definition at line 485 of file SDDS_info.c.

485 {
486 int32_t field_index, type, parameter_index, givenType;
487 PARAMETER_DEFINITION *parameterdef;
488 char *parameter_name;
489 va_list argptr;
490 int32_t retval;
491 double buffer[4];
492
493 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_ChangeParameterInformation"))
494 return (0);
495
496 if (!field_name) {
497 SDDS_SetError("NULL field name passed. (SDDS_ChangeParameterInformation)");
498 return (0);
499 }
500
501 va_start(argptr, mode);
502 retval = 1;
503 if (mode & SDDS_SET_BY_INDEX) {
504 if ((parameter_index = va_arg(argptr, int32_t)) < 0 || parameter_index >= SDDS_dataset->layout.n_parameters) {
505 SDDS_SetError("Invalid parameter index passed. (SDDS_ChangeParameterInformation)");
506 retval = 0;
507 }
508 } else {
509 if (!(parameter_name = va_arg(argptr, char *))) {
510 SDDS_SetError("NULL parameter name passed. (SDDS_ChangeParameterInformation)");
511 retval = 0;
512 }
513 if ((parameter_index = SDDS_GetParameterIndex(SDDS_dataset, parameter_name)) < 0) {
514 SDDS_SetError("Unknown parameter name given (SDDS_ChangeParameterInformation)");
515 retval = 0;
516 }
517 }
518 parameterdef = SDDS_dataset->layout.parameter_definition + parameter_index;
519 va_end(argptr);
520 if (!retval)
521 return (0);
522
523 for (field_index = 0; field_index < SDDS_PARAMETER_FIELDS; field_index++)
524 if (strcmp(field_name, SDDS_ParameterFieldInformation[field_index].name) == 0)
525 break;
526 if (field_index == SDDS_PARAMETER_FIELDS) {
527 SDDS_SetError("Unknown field name given (SDDS_ChangeParameterInformation)");
528 return (0);
529 }
530 type = SDDS_ParameterFieldInformation[field_index].type;
531 if (!memory)
532 return (type);
533 if (type == SDDS_STRING) {
534 if (!SDDS_CopyString(((char **)((char *)parameterdef + SDDS_ParameterFieldInformation[field_index].offset)), (char *)memory)) {
535 SDDS_SetError("Unable to copy field data (SDDS_ChangeParameterInformation)");
536 return (0);
537 }
538 if (strcmp(field_name, "name") == 0)
539 qsort((char *)SDDS_dataset->layout.parameter_index, SDDS_dataset->layout.n_parameters, sizeof(*SDDS_dataset->layout.parameter_index), SDDS_CompareIndexedNamesPtr);
540 } else {
541 if (mode & SDDS_PASS_BY_STRING) {
542 if (strcmp(field_name, "type") == 0 && (givenType = SDDS_IdentifyType((char *)memory)) > 0)
543 /* the type has been passed as a string (e.g., "double") */
544 memcpy((char *)buffer, (char *)&givenType, sizeof(givenType));
545 else if (!SDDS_ScanData((char *)memory, type, 0, (void *)buffer, 0, 0)) {
546 SDDS_SetError("Unable to scan string data (SDDS_ChangeParameterInformation)");
547 return (0);
548 }
549 memcpy((char *)parameterdef + SDDS_ParameterFieldInformation[field_index].offset, (void *)buffer, SDDS_type_size[type - 1]);
550 } else
551 memcpy((char *)parameterdef + SDDS_ParameterFieldInformation[field_index].offset, memory, SDDS_type_size[type - 1]);
552 }
553
554 return (type);
555}
SDDS_FIELD_INFORMATION SDDS_ParameterFieldInformation[SDDS_PARAMETER_FIELDS]
Field information for parameter definitions.
Definition SDDS_data.c:209

◆ SDDS_CheckArray()

epicsShareFuncSDDS int32_t SDDS_CheckArray ( SDDS_DATASET * SDDS_dataset,
char * name,
char * units,
int32_t type,
FILE * fp_message )
extern

Checks if an array exists in the SDDS dataset with the specified name, units, and type.

This function verifies whether an array with the given name exists within the provided SDDS dataset. Additionally, it can check if the array's units and type match the specified criteria.

Parameters
[in]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset to be checked.
[in]nameThe name of the array to check.
[in]unitsThe units of the array. This parameter may be NULL if units are not to be validated.
[in]typeSpecifies the expected type of the array. Valid values are:
  • SDDS_ANY_NUMERIC_TYPE
  • SDDS_ANY_FLOATING_TYPE
  • SDDS_ANY_INTEGER_TYPE
  • 0 (if type is to be ignored)
[in]fp_messageFile pointer where error messages will be sent. Typically, this is stderr.
Returns
  • SDDS_CHECK_OKAY if the array exists and matches the specified criteria.
  • SDDS_CHECK_NONEXISTENT if the array does not exist.
  • SDDS_CHECK_WRONGTYPE if the array exists but does not match the specified type.
  • SDDS_CHECK_WRONGUNITS if the array exists but does not match the specified units.
Note
  • If units is NULL, the function does not perform units validation.
  • The function retrieves the array's units and type using SDDS_GetArrayInformation and SDDS_GetArrayType.
Warning
  • Ensure that the SDDS dataset is properly initialized and contains arrays before calling this function.
  • The function may set error messages using SDDS_SetError if it encounters issues accessing array information.
See also
SDDS_CheckColumn, SDDS_CheckParameter, SDDS_PrintCheckText, SDDS_SetError

Definition at line 4826 of file SDDS_utils.c.

4826 {
4827 char *units1;
4828 int32_t index;
4829 if ((index = SDDS_GetArrayIndex(SDDS_dataset, name)) < 0)
4830 return (SDDS_PrintCheckText(fp_message, name, units, type, "array", SDDS_CHECK_NONEXISTENT));
4831 if (SDDS_VALID_TYPE(type)) {
4832 if (type != SDDS_GetArrayType(SDDS_dataset, index))
4833 return (SDDS_PrintCheckText(fp_message, name, units, type, "array", SDDS_CHECK_WRONGTYPE));
4834 } else {
4835 switch (type) {
4836 case 0:
4837 break;
4839 if (!SDDS_NUMERIC_TYPE(SDDS_GetArrayType(SDDS_dataset, index)))
4840 return (SDDS_PrintCheckText(fp_message, name, units, type, "array", SDDS_CHECK_WRONGTYPE));
4841 break;
4843 if (!SDDS_FLOATING_TYPE(SDDS_GetArrayType(SDDS_dataset, index)))
4844 return (SDDS_PrintCheckText(fp_message, name, units, type, "array", SDDS_CHECK_WRONGTYPE));
4845 break;
4847 if (!SDDS_INTEGER_TYPE(SDDS_GetArrayType(SDDS_dataset, index)))
4848 return (SDDS_PrintCheckText(fp_message, name, units, type, "array", SDDS_CHECK_WRONGTYPE));
4849 break;
4850 default:
4851 return (SDDS_PrintCheckText(fp_message, name, units, type, "array", SDDS_CHECK_WRONGTYPE));
4852 }
4853 }
4854 if (SDDS_GetArrayInformation(SDDS_dataset, "units", &units1, SDDS_GET_BY_NAME, name) != SDDS_STRING) {
4855 SDDS_SetError("units field of array has wrong data type!");
4856 SDDS_PrintErrors(stderr, SDDS_EXIT_PrintErrors | SDDS_VERBOSE_PrintErrors);
4857 }
4858 if (!units) {
4859 /* don't care about units */
4860 return (SDDS_CHECK_OKAY);
4861 }
4862 if (!units1) {
4863 if (SDDS_StringIsBlank(units))
4864 return (SDDS_CHECK_OKAY);
4865 return (SDDS_CHECK_OKAY);
4866 }
4867 if (strcmp(units, units1) == 0) {
4868 free(units1);
4869 return (SDDS_CHECK_OKAY);
4870 }
4871 free(units1);
4872 return (SDDS_PrintCheckText(fp_message, name, units, type, "array", SDDS_CHECK_WRONGUNITS));
4873}
int32_t SDDS_GetArrayInformation(SDDS_DATASET *SDDS_dataset, char *field_name, void *memory, int32_t mode,...)
Retrieves information about a specified array in the SDDS dataset.
Definition SDDS_info.c:192
int32_t SDDS_GetArrayType(SDDS_DATASET *SDDS_dataset, int32_t index)
Retrieves the data type of an array in the SDDS dataset by its index.
int32_t SDDS_StringIsBlank(char *s)
Checks if a string is blank (contains only whitespace characters).
int32_t SDDS_PrintCheckText(FILE *fp, char *name, char *units, int32_t type, char *class_name, int32_t error_code)
Prints detailed error messages related to SDDS entity checks.
#define SDDS_INTEGER_TYPE(type)
Checks if the given type identifier corresponds to an integer type.
Definition SDDStypes.h:109
#define SDDS_VALID_TYPE(type)
Validates whether the given type identifier is within the defined range of SDDS types.
Definition SDDStypes.h:149
#define SDDS_FLOATING_TYPE(type)
Checks if the given type identifier corresponds to a floating-point type.
Definition SDDStypes.h:124
#define SDDS_ANY_FLOATING_TYPE
Special identifier used by SDDS_Check*() routines to accept any floating-point type.
Definition SDDStypes.h:165
#define SDDS_ANY_NUMERIC_TYPE
Special identifier used by SDDS_Check*() routines to accept any numeric type.
Definition SDDStypes.h:157
#define SDDS_ANY_INTEGER_TYPE
Special identifier used by SDDS_Check*() routines to accept any integer type.
Definition SDDStypes.h:173

◆ SDDS_CheckColumn()

epicsShareFuncSDDS int32_t SDDS_CheckColumn ( SDDS_DATASET * SDDS_dataset,
char * name,
char * units,
int32_t type,
FILE * fp_message )
extern

Checks if a column exists in the SDDS dataset with the specified name, units, and type.

This function verifies whether a column with the given name exists in the SDDS dataset and optionally checks if its units and type match the specified criteria.

Parameters
[in]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset to be checked.
[in]nameThe name of the column to check.
[in]unitsThe units of the column. May be NULL if units are not to be checked.
[in]typeSpecifies the expected type of the column. Valid values are:
  • SDDS_ANY_NUMERIC_TYPE
  • SDDS_ANY_FLOATING_TYPE
  • SDDS_ANY_INTEGER_TYPE
  • 0 (if type is to be ignored)
[in]fp_messageFile pointer where error messages will be sent. Typically, this is stderr.
Returns
  • SDDS_CHECK_OKAY if the column exists and matches the specified criteria.
  • SDDS_CHECK_NONEXISTENT if the column does not exist.
  • SDDS_CHECK_WRONGTYPE if the column exists but does not match the specified type.
  • SDDS_CHECK_WRONGUNITS if the column exists but does not match the specified units.
Note
  • If units is NULL, the function does not check for units.
  • The function retrieves the column's units and type using SDDS_GetColumnInformation and SDDS_GetColumnType.
Warning
  • Ensure that the SDDS dataset is properly initialized and contains columns before calling this function.
  • The function may set error messages using SDDS_SetError if it encounters issues accessing column information.
See also
SDDS_CheckParameter, SDDS_GetColumnIndex, SDDS_SetError

Definition at line 4646 of file SDDS_utils.c.

4646 {
4647 char *units1;
4648 int32_t index;
4649 if ((index = SDDS_GetColumnIndex(SDDS_dataset, name)) < 0)
4650 return (SDDS_PrintCheckText(fp_message, name, units, type, "column", SDDS_CHECK_NONEXISTENT));
4651 if (SDDS_VALID_TYPE(type)) {
4652 if (type != SDDS_GetColumnType(SDDS_dataset, index))
4653 return (SDDS_PrintCheckText(fp_message, name, units, type, "column", SDDS_CHECK_WRONGTYPE));
4654 } else {
4655 switch (type) {
4656 case 0:
4657 break;
4659 if (!SDDS_NUMERIC_TYPE(SDDS_GetColumnType(SDDS_dataset, index)))
4660 return (SDDS_PrintCheckText(fp_message, name, units, type, "column", SDDS_CHECK_WRONGTYPE));
4661 break;
4663 if (!SDDS_FLOATING_TYPE(SDDS_GetColumnType(SDDS_dataset, index))) {
4664 return (SDDS_PrintCheckText(fp_message, name, units, type, "column", SDDS_CHECK_WRONGTYPE));
4665 }
4666 break;
4668 if (!SDDS_INTEGER_TYPE(SDDS_GetColumnType(SDDS_dataset, index))) {
4669 return (SDDS_PrintCheckText(fp_message, name, units, type, "column", SDDS_CHECK_WRONGTYPE));
4670 }
4671 break;
4672 default:
4673 return (SDDS_PrintCheckText(fp_message, name, units, type, "column", SDDS_CHECK_WRONGTYPE));
4674 }
4675 }
4676 if (!units) {
4677 /* don't care about units */
4678 return SDDS_CHECK_OKAY;
4679 }
4680 if (SDDS_GetColumnInformation(SDDS_dataset, "units", &units1, SDDS_GET_BY_NAME, name) != SDDS_STRING) {
4681 SDDS_SetError("units field of column has wrong data type!");
4682 SDDS_PrintErrors(stderr, SDDS_EXIT_PrintErrors | SDDS_VERBOSE_PrintErrors);
4683 }
4684 if (!units1) {
4685 if (SDDS_StringIsBlank(units))
4686 return (SDDS_CHECK_OKAY);
4687 return (SDDS_PrintCheckText(fp_message, name, units, type, "column", SDDS_CHECK_WRONGUNITS));
4688 }
4689 if (strcmp(units, units1) == 0) {
4690 free(units1);
4691 return (SDDS_CHECK_OKAY);
4692 }
4693 free(units1);
4694 return (SDDS_PrintCheckText(fp_message, name, units, type, "column", SDDS_CHECK_WRONGUNITS));
4695}
int32_t SDDS_GetColumnInformation(SDDS_DATASET *SDDS_dataset, char *field_name, void *memory, int32_t mode,...)
Retrieves information about a specified column in the SDDS dataset.
Definition SDDS_info.c:41
int32_t SDDS_GetColumnType(SDDS_DATASET *SDDS_dataset, int32_t index)
Retrieves the data type of a column in the SDDS dataset by its index.

◆ SDDS_CheckDataset()

epicsShareFuncSDDS int32_t SDDS_CheckDataset ( SDDS_DATASET * SDDS_dataset,
const char * caller )
extern

Validates the SDDS dataset pointer.

This function checks whether the provided SDDS_DATASET pointer is valid (non-NULL). If the check fails, it records an appropriate error message.

Parameters
[in]SDDS_datasetPointer to the SDDS_DATASET structure to be validated.
[in]callerName of the calling function, used for error reporting.
Returns
Returns 1 if the dataset pointer is valid; otherwise, returns 0 and records an error message.
See also
SDDS_SetError

Definition at line 618 of file SDDS_utils.c.

618 {
619 char buffer[100];
620 if (!SDDS_dataset) {
621 sprintf(buffer, "NULL SDDS_DATASET pointer passed to %s", caller);
622 SDDS_SetError(buffer);
623 return (0);
624 }
625 return (1);
626}

◆ SDDS_CheckDatasetStructureSize()

epicsShareFuncSDDS int32_t SDDS_CheckDatasetStructureSize ( int32_t size)
extern

Verifies that the size of the SDDS_DATASET structure matches the expected size.

This function ensures that the size of the SDDS_DATASET structure used by the program matches the size expected by the SDDS library. This check is crucial to prevent issues related to structure size mismatches, which can occur due to differences in compiler settings or library versions.

Parameters
[in]sizeThe size of the SDDS_DATASET structure as determined by the calling program (typically using sizeof(SDDS_DATASET)).
Returns
  • 1 if the provided size matches the expected size of the SDDS_DATASET structure.
  • 0 if there is a size mismatch, indicating potential incompatibility issues.
Note
  • This function should be called during initialization to ensure structural compatibility between the program and the SDDS library.
Warning
  • A size mismatch can lead to undefined behavior, including memory corruption and program crashes. Always ensure that both the program and the SDDS library are compiled with compatible settings.
See also
SDDS_DATASET, SDDS_SetError

Definition at line 5070 of file SDDS_utils.c.

5070 {
5071 char buffer[100];
5072 if (size != sizeof(SDDS_DATASET)) {
5073 SDDS_SetError("passed size is not equal to expected size for SDDS_DATASET structure");
5074 sprintf(buffer, "Passed size is %" PRId32 ", library size is %" PRId32 "\n", size, (int32_t)sizeof(SDDS_DATASET));
5075 SDDS_SetError(buffer);
5076 return 0;
5077 }
5078 return 1;
5079}

◆ SDDS_CheckEndOfFile()

epicsShareFuncSDDS int32_t SDDS_CheckEndOfFile ( SDDS_DATASET * SDDS_dataset)
extern

Checks if the end of the SDDS dataset file has been reached.

Parameters
SDDS_datasetThe SDDS dataset structure.
Returns
Returns 1 if the end of file has been reached, 0 if not, and 2 on error.

Definition at line 1021 of file SDDS_input.c.

1021 {
1022 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_EndOfFile"))
1023 return (0);
1024 if (SDDS_dataset->layout.disconnected) {
1025 SDDS_SetError("Can't check status--file is disconnected (SDDS_EndOfFile)");
1026 return 2;
1027 }
1028#if defined(zLib)
1029 if (SDDS_dataset->layout.gzipFile) {
1030 if (!SDDS_dataset->layout.gzfp) {
1031 SDDS_SetError("Unable to check status--NULL file pointer (SDDS_EndOfFile)");
1032 return 2;
1033 }
1034 } else {
1035#endif
1036 if (SDDS_dataset->layout.lzmaFile) {
1037 if (!SDDS_dataset->layout.lzmafp) {
1038 SDDS_SetError("Unable to check status--NULL file pointer (SDDS_EndOfFile)");
1039 return 2;
1040 }
1041 } else {
1042 if (!SDDS_dataset->layout.fp) {
1043 SDDS_SetError("Unable to check status--NULL file pointer (SDDS_EndOfFile)");
1044 return 2;
1045 }
1046 }
1047#if defined(zLib)
1048 }
1049#endif
1050 if (SDDS_dataset->fBuffer.bufferSize && SDDS_dataset->fBuffer.bytesLeft) {
1051 return 0;
1052 }
1053
1054#if defined(zLib)
1055 if (SDDS_dataset->layout.gzipFile) {
1056 if (gzeof(SDDS_dataset->layout.gzfp))
1057 return 1;
1058 } else {
1059#endif
1060 if (SDDS_dataset->layout.lzmaFile) {
1061 if (lzma_eof(SDDS_dataset->layout.lzmafp))
1062 return 1;
1063 } else {
1064 if (feof(SDDS_dataset->layout.fp))
1065 return 1;
1066 }
1067#if defined(zLib)
1068 }
1069#endif
1070 return 0;
1071}

◆ SDDS_CheckParameter()

epicsShareFuncSDDS int32_t SDDS_CheckParameter ( SDDS_DATASET * SDDS_dataset,
char * name,
char * units,
int32_t type,
FILE * fp_message )
extern

Checks if a parameter exists in the SDDS dataset with the specified name, units, and type.

This function verifies whether a parameter with the given name exists in the SDDS dataset and optionally checks if its units and type match the specified criteria.

Parameters
[in]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset to be checked.
[in]nameThe name of the parameter to check.
[in]unitsThe units of the parameter. May be NULL if units are not to be checked.
[in]typeSpecifies the expected type of the parameter. Valid values are:
  • SDDS_ANY_NUMERIC_TYPE
  • SDDS_ANY_FLOATING_TYPE
  • SDDS_ANY_INTEGER_TYPE
  • 0 (if type is to be ignored)
[in]fp_messageFile pointer where error messages will be sent. Typically, this is stderr.
Returns
  • SDDS_CHECK_OKAY if the parameter exists and matches the specified criteria.
  • SDDS_CHECK_NONEXISTENT if the parameter does not exist.
  • SDDS_CHECK_WRONGTYPE if the parameter exists but does not match the specified type.
  • SDDS_CHECK_WRONGUNITS if the parameter exists but does not match the specified units.
Note
  • If units is NULL, the function does not check for units.
  • The function retrieves the parameter's units and type using SDDS_GetParameterInformation and SDDS_GetParameterType.
Warning
  • Ensure that the SDDS dataset is properly initialized and contains parameters before calling this function.
  • The function may set error messages using SDDS_SetError if it encounters issues accessing parameter information.
See also
SDDS_CheckColumn, SDDS_GetParameterIndex, SDDS_SetError

Definition at line 4737 of file SDDS_utils.c.

4737 {
4738 char *units1;
4739 int32_t index;
4740 if ((index = SDDS_GetParameterIndex(SDDS_dataset, name)) < 0)
4741 return (SDDS_PrintCheckText(fp_message, name, units, type, "parameter", SDDS_CHECK_NONEXISTENT));
4742 if (SDDS_VALID_TYPE(type)) {
4743 if (type != SDDS_GetParameterType(SDDS_dataset, index))
4744 return (SDDS_PrintCheckText(fp_message, name, units, type, "parameter", SDDS_CHECK_WRONGTYPE));
4745 } else {
4746 switch (type) {
4747 case 0:
4748 break;
4750 if (!SDDS_NUMERIC_TYPE(SDDS_GetParameterType(SDDS_dataset, index)))
4751 return (SDDS_PrintCheckText(fp_message, name, units, type, "parameter", SDDS_CHECK_WRONGTYPE));
4752 break;
4754 if (!SDDS_FLOATING_TYPE(SDDS_GetParameterType(SDDS_dataset, index)))
4755 return (SDDS_PrintCheckText(fp_message, name, units, type, "parameter", SDDS_CHECK_WRONGTYPE));
4756 break;
4758 if (!SDDS_INTEGER_TYPE(SDDS_GetParameterType(SDDS_dataset, index)))
4759 return (SDDS_PrintCheckText(fp_message, name, units, type, "parameter", SDDS_CHECK_WRONGTYPE));
4760 break;
4761 default:
4762 return (SDDS_PrintCheckText(fp_message, name, units, type, "parameter", SDDS_CHECK_WRONGTYPE));
4763 }
4764 }
4765 if (!units) {
4766 /* don't care about units */
4767 return (SDDS_CHECK_OKAY);
4768 }
4769 if (SDDS_GetParameterInformation(SDDS_dataset, "units", &units1, SDDS_GET_BY_NAME, name) != SDDS_STRING) {
4770 SDDS_SetError("units field of parameter has wrong data type!");
4771 SDDS_PrintErrors(stderr, SDDS_EXIT_PrintErrors | SDDS_VERBOSE_PrintErrors);
4772 }
4773 if (!units1) {
4774 if (SDDS_StringIsBlank(units))
4775 return (SDDS_CHECK_OKAY);
4776 return (SDDS_PrintCheckText(fp_message, name, units, type, "parameter", SDDS_CHECK_WRONGUNITS));
4777 }
4778 if (strcmp(units, units1) == 0) {
4779 free(units1);
4780 return (SDDS_CHECK_OKAY);
4781 }
4782 free(units1);
4783 return (SDDS_PrintCheckText(fp_message, name, units, type, "parameter", SDDS_CHECK_WRONGUNITS));
4784}
int32_t SDDS_GetParameterInformation(SDDS_DATASET *SDDS_dataset, char *field_name, void *memory, int32_t mode,...)
Retrieves information about a specified parameter in the SDDS dataset.
Definition SDDS_info.c:117
int32_t SDDS_GetParameterType(SDDS_DATASET *SDDS_dataset, int32_t index)
Retrieves the data type of a parameter in the SDDS dataset by its index.

◆ SDDS_CheckTabularData()

epicsShareFuncSDDS int32_t SDDS_CheckTabularData ( SDDS_DATASET * SDDS_dataset,
const char * caller )
extern

Validates the consistency of tabular data within an SDDS dataset.

This function checks the integrity of tabular data in the given SDDS_DATASET. It verifies that if columns are defined, corresponding row flags and data arrays exist, and that the number of rows matches the column definitions.

Parameters
[in]SDDS_datasetPointer to the SDDS_DATASET structure to be validated.
[in]callerName of the calling function, used for error reporting.
Returns
Returns 1 if the tabular data is consistent and valid; otherwise, returns 0 and records an error message.
Note
This function performs checks only if AutoCheckMode includes TABULAR_DATA_CHECKS.
See also
SDDS_SetAutoCheckMode
SDDS_SetError

Definition at line 643 of file SDDS_utils.c.

643 {
644 int64_t i;
645 char buffer[100];
646 if (!(SDDS_GetLockedAutoCheckMode() & TABULAR_DATA_CHECKS))
647 return 1;
648 if (SDDS_dataset->layout.n_columns && (!SDDS_dataset->row_flag || !SDDS_dataset->data)) {
649 sprintf(buffer, "tabular data is invalid in %s (columns but no row flags or data array)", caller);
650 SDDS_SetError(buffer);
651 return (0);
652 }
653 if (SDDS_dataset->layout.n_columns == 0 && SDDS_dataset->n_rows) {
654 sprintf(buffer, "tabular data is invalid in %s (no columns present but nonzero row count)", caller);
655 SDDS_SetError(buffer);
656 return (0);
657 }
658 for (i = 0; i < SDDS_dataset->layout.n_columns; i++) {
659 if (!SDDS_dataset->data[i]) {
660 sprintf(buffer, "tabular data is invalid in %s (null data pointer for column %" PRId64 ")", caller, i);
661 SDDS_SetError(buffer);
662 return (0);
663 }
664 }
665 return (1);
666}

◆ SDDS_ClearErrors()

epicsShareFuncSDDS void SDDS_ClearErrors ( void )
extern

Clears all recorded error messages from the SDDS error stack.

This function removes all error messages that have been recorded by SDDS library routines, resetting the error count to zero. It should be called after handling or logging the errors to prepare for future error recording.

Note
After calling this function, SDDS_NumberOfErrors will return zero until new errors are recorded.
See also
SDDS_SetError
SDDS_PrintErrors

Definition at line 354 of file SDDS_utils.c.

354 {
355 int32_t i;
356 if (error_description) {
357 for (i=0; i<n_errors; i++) {
358 free(error_description[i]);
359 error_description[i] = NULL;
360 }
361 }
362 free(error_description);
363 error_description = NULL;
364 n_errors = 0;
365 n_errors_max = 0;
366}

◆ SDDS_ClearPage()

epicsShareFuncSDDS int32_t SDDS_ClearPage ( SDDS_DATASET * SDDS_dataset)
extern

Clears the current page in the SDDS dataset, resetting all data and flags.

This function resets the current data page in the specified SDDS dataset by reinitializing column flags and order. It frees any allocated string data and zeros out the data arrays, parameters, and arrays in the dataset.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure whose current page will be cleared.
Returns
Returns 1 on successful clearing of the page. On failure, returns 0 and records an error message.
See also
SDDS_SetMemory, SDDS_FreeStringData, SDDS_ZeroMemory

Definition at line 194 of file SDDS_dataprep.c.

194 {
195 SDDS_LAYOUT *layout;
196 int64_t i;
197 int32_t size;
198
199 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_ClearPage"))
200 return 0;
201 layout = &SDDS_dataset->layout;
202
203 if (layout->n_columns && ((SDDS_dataset->column_flag && !SDDS_SetMemory(SDDS_dataset->column_flag, layout->n_columns, SDDS_LONG, (int32_t)1, (int32_t)0)) ||
204 ((SDDS_dataset->column_order && !SDDS_SetMemory(SDDS_dataset->column_order, layout->n_columns, SDDS_LONG, (int32_t)0, (int32_t)1))))) {
205 SDDS_SetError("Unable to start page--memory initialization failure (SDDS_ClearPage)");
206 return 0;
207 }
208 SDDS_FreeStringData(SDDS_dataset);
209 if (SDDS_dataset->data) {
210 for (i = 0; i < layout->n_columns; i++) {
211 size = SDDS_type_size[layout->column_definition[i].type - 1];
212 if (SDDS_dataset->data[i])
213 SDDS_ZeroMemory(SDDS_dataset->data[i], size * SDDS_dataset->n_rows_allocated);
214 }
215 }
216 if (SDDS_dataset->parameter) {
217 for (i = 0; i < layout->n_parameters; i++) {
218 size = SDDS_type_size[layout->parameter_definition[i].type - 1];
219 SDDS_ZeroMemory(SDDS_dataset->parameter[i], size);
220 }
221 }
222 for (i = 0; i < layout->n_arrays; i++) {
223 size = SDDS_type_size[layout->array_definition[i].type - 1];
224 if (SDDS_dataset->array && SDDS_dataset->array[i].data && SDDS_dataset->array[i].elements)
225 SDDS_ZeroMemory(SDDS_dataset->array[i].data, size * SDDS_dataset->array[i].elements);
226 }
227 return 1;
228}
int32_t SDDS_FreeStringData(SDDS_DATASET *SDDS_dataset)
int32_t SDDS_ZeroMemory(void *mem, int64_t n_bytes)
Sets a block of memory to zero.
int32_t SDDS_SetMemory(void *mem, int64_t n_elements, int32_t data_type,...)
Initializes a memory block with a sequence of values based on a specified data type.

◆ SDDS_ColumnCount()

epicsShareFuncSDDS int32_t SDDS_ColumnCount ( SDDS_DATASET * page)
extern

Retrieves the number of columns in the SDDS dataset.

This function returns the total count of columns defined in the layout of the provided SDDS dataset.

Parameters
[in]pagePointer to the SDDS_DATASET structure representing the dataset.
Returns
  • The number of columns (int32_t) in the dataset.
  • 0 if the provided dataset pointer is NULL.
Note
  • Ensure that the dataset is properly initialized before calling this function.
See also
SDDS_GetColumnIndex, SDDS_CheckColumn

Definition at line 5098 of file SDDS_utils.c.

5098 {
5099 if (!page)
5100 return 0;
5101 return page->layout.n_columns;
5102}

◆ SDDS_ColumnIsOfInterest()

epicsShareFuncSDDS int32_t SDDS_ColumnIsOfInterest ( SDDS_DATASET * SDDS_dataset,
char * name )
extern

Determines if a specified column is marked as of interest in the dataset.

This function checks whether the column with the given name is flagged as of interest within the provided SDDS_dataset. It verifies the dataset's validity and then iterates through the columns to find a match based on the column_flag array.

Parameters
[in]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
[in]nameA NULL-terminated string specifying the name of the column to check.
Returns
  • Returns 1 if the column is marked as of interest.
  • Returns 0 if the column is not marked as of interest or if column_flag is not set.
  • Returns -1 if the dataset is invalid.
See also
SDDS_CheckDataset

Definition at line 2494 of file SDDS_utils.c.

2494 {
2495 int64_t i;
2496 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_ColumnIsOfInterest"))
2497 return -1;
2498 if (!SDDS_dataset->column_flag)
2499 return 0;
2500 for (i = 0; i < SDDS_dataset->layout.n_columns; i++) {
2501 if (SDDS_dataset->column_flag[i] && strcmp(name, SDDS_dataset->layout.column_definition[i].name) == 0)
2502 return 1;
2503 }
2504 return 0;
2505}

◆ SDDS_CompareIndexedNames()

epicsShareFuncSDDS int SDDS_CompareIndexedNames ( const void * s1,
const void * s2 )
extern

Compares two SORTED_INDEX structures by their name fields.

This function is used as a comparison callback for sorting functions like qsort. It compares the name fields of two SORTED_INDEX structures lexicographically.

Parameters
[in]s1Pointer to the first SORTED_INDEX structure.
[in]s2Pointer to the second SORTED_INDEX structure.
Returns
An integer less than, equal to, or greater than zero if the name of s1 is found, respectively, to be less than, to match, or be greater than the name of s2.
See also
qsort
SORTED_INDEX

Definition at line 1338 of file SDDS_utils.c.

1338 {
1339 return strcmp(((SORTED_INDEX *)s1)->name, ((SORTED_INDEX *)s2)->name);
1340}

◆ SDDS_CompareIndexedNamesPtr()

epicsShareFuncSDDS int SDDS_CompareIndexedNamesPtr ( const void * s1,
const void * s2 )
extern

Compares two pointers to SORTED_INDEX structures by their name fields.

This function is used as a comparison callback for sorting functions like qsort. It compares the name fields of two SORTED_INDEX structure pointers lexicographically.

Parameters
[in]s1Pointer to the first SORTED_INDEX* structure.
[in]s2Pointer to the second SORTED_INDEX* structure.
Returns
An integer less than, equal to, or greater than zero if the name of *s1 is found, respectively, to be less than, to match, or be greater than the name of *s2.
See also
qsort
SORTED_INDEX

Definition at line 1358 of file SDDS_utils.c.

1358 {
1359 return strcmp((*((SORTED_INDEX **)s1))->name, (*((SORTED_INDEX **)s2))->name);
1360}

◆ SDDS_ConvertToDouble()

epicsShareFuncSDDS double SDDS_ConvertToDouble ( int32_t type,
void * data,
int64_t index )
extern

Converts a value to double based on its type.

Parameters
typeThe SDDS data type of the value.
dataPointer to the data array.
indexIndex of the element to convert.
Returns
The converted double value, or 0.0 on error.

Definition at line 199 of file SDDS_rpn.c.

199 {
200 if (!data) {
201 SDDS_SetError("NULL data pointer passed (SDDS_ConvertToDouble)");
202 return (0.0);
203 }
204 switch (type) {
205 case SDDS_SHORT:
206 return ((double)*((short *)data + index));
207 case SDDS_USHORT:
208 return ((double)*((unsigned short *)data + index));
209 case SDDS_LONG:
210 return ((double)*((int32_t *)data + index));
211 case SDDS_ULONG:
212 return ((double)*((uint32_t *)data + index));
213 case SDDS_LONG64:
214 return ((double)*((int64_t *)data + index));
215 case SDDS_ULONG64:
216 return ((double)*((uint64_t *)data + index));
217 case SDDS_FLOAT:
218 return ((double)*((float *)data + index));
219 case SDDS_DOUBLE:
220 return (*((double *)data + index));
221 case SDDS_LONGDOUBLE:
222 return ((double)*((long double *)data + index));
223 case SDDS_CHARACTER:
224 return ((double)*((unsigned char *)data + index));
225 default:
226 SDDS_SetError("Invalid data type seen (SDDS_ConvertToDouble)");
227 return (0.0);
228 }
229}

◆ SDDS_ConvertToLong()

epicsShareFuncSDDS int32_t SDDS_ConvertToLong ( int32_t type,
void * data,
int64_t index )
extern

Converts a value to a 32-bit integer based on its type.

Parameters
typeThe SDDS data type of the value.
dataPointer to the data array.
indexIndex of the element to convert.
Returns
The converted 32-bit integer, or 0 on error.

Definition at line 279 of file SDDS_rpn.c.

279 {
280 if (!data) {
281 SDDS_SetError("NULL data pointer passed (SDDS_ConvertToLong)");
282 return (0.0);
283 }
284 switch (type) {
285 case SDDS_LONGDOUBLE:
286 return ((int32_t) * ((long double *)data + index));
287 case SDDS_DOUBLE:
288 return ((int32_t) * ((double *)data + index));
289 case SDDS_FLOAT:
290 return ((int32_t) * ((float *)data + index));
291 case SDDS_SHORT:
292 return ((int32_t) * ((short *)data + index));
293 case SDDS_USHORT:
294 return ((int32_t) * ((unsigned short *)data + index));
295 case SDDS_LONG:
296 return (*((int32_t *)data + index));
297 case SDDS_ULONG:
298 return ((int32_t) * ((uint32_t *)data + index));
299 case SDDS_LONG64:
300 return ((int32_t) * ((int64_t *)data + index));
301 case SDDS_ULONG64:
302 return ((int32_t) * ((uint64_t *)data + index));
303 case SDDS_CHARACTER:
304 return ((int32_t) * ((unsigned char *)data + index));
305 default:
306 SDDS_SetError("Invalid data type seen (SDDS_ConvertToLong)");
307 return (0.0);
308 }
309}

◆ SDDS_ConvertToLong64()

epicsShareFuncSDDS int64_t SDDS_ConvertToLong64 ( int32_t type,
void * data,
int64_t index )
extern

Converts a value to a 64-bit integer based on its type.

Parameters
typeThe SDDS data type of the value.
dataPointer to the data array.
indexIndex of the element to convert.
Returns
The converted 64-bit integer, or 0 on error.

Definition at line 239 of file SDDS_rpn.c.

239 {
240 if (!data) {
241 SDDS_SetError("NULL data pointer passed (SDDS_ConvertToLong64)");
242 return (0.0);
243 }
244 switch (type) {
245 case SDDS_LONGDOUBLE:
246 return ((int64_t) * ((long double *)data + index));
247 case SDDS_DOUBLE:
248 return ((int64_t) * ((double *)data + index));
249 case SDDS_FLOAT:
250 return ((int64_t) * ((float *)data + index));
251 case SDDS_SHORT:
252 return ((int64_t) * ((short *)data + index));
253 case SDDS_USHORT:
254 return ((int64_t) * ((unsigned short *)data + index));
255 case SDDS_LONG:
256 return ((int64_t) * ((int32_t *)data + index));
257 case SDDS_ULONG:
258 return ((int64_t) * ((uint32_t *)data + index));
259 case SDDS_LONG64:
260 return (*((int64_t *)data + index));
261 case SDDS_ULONG64:
262 return ((int64_t) * ((uint64_t *)data + index));
263 case SDDS_CHARACTER:
264 return ((int64_t) * ((unsigned char *)data + index));
265 default:
266 SDDS_SetError("Invalid data type seen (SDDS_ConvertToLong64)");
267 return (0.0);
268 }
269}

◆ SDDS_ConvertToLongDouble()

epicsShareFuncSDDS long double SDDS_ConvertToLongDouble ( int32_t type,
void * data,
int64_t index )
extern

Converts a value to long double based on its type.

Parameters
typeThe SDDS data type of the value.
dataPointer to the data array.
indexIndex of the element to convert.
Returns
The converted long double value, or 0.0 on error.

Definition at line 159 of file SDDS_rpn.c.

159 {
160 if (!data) {
161 SDDS_SetError("NULL data pointer passed (SDDS_ConvertToLongDouble)");
162 return (0.0);
163 }
164 switch (type) {
165 case SDDS_SHORT:
166 return ((long double)*((short *)data + index));
167 case SDDS_USHORT:
168 return ((long double)*((unsigned short *)data + index));
169 case SDDS_LONG:
170 return ((long double)*((int32_t *)data + index));
171 case SDDS_ULONG:
172 return ((long double)*((uint32_t *)data + index));
173 case SDDS_LONG64:
174 return ((long double)*((int64_t *)data + index));
175 case SDDS_ULONG64:
176 return ((long double)*((uint64_t *)data + index));
177 case SDDS_FLOAT:
178 return ((long double)*((float *)data + index));
179 case SDDS_DOUBLE:
180 return ((long double)*((double *)data + index));
181 case SDDS_LONGDOUBLE:
182 return (*((long double *)data + index));
183 case SDDS_CHARACTER:
184 return ((long double)*((unsigned char *)data + index));
185 default:
186 SDDS_SetError("Invalid data type seen (SDDS_ConvertToLongDouble)");
187 return (0.0);
188 }
189}

◆ SDDS_CopyAdditionalRows()

epicsShareFuncSDDS int32_t SDDS_CopyAdditionalRows ( SDDS_DATASET * SDDS_target,
SDDS_DATASET * SDDS_source )
extern

Copies additional rows from one SDDS_DATASET to another. The rows from SDDS_source are appended to the existing rows in SDDS_target.

Parameters
SDDS_targetPointer to the SDDS_DATASET structure where rows will be appended.
SDDS_sourcePointer to the SDDS_DATASET structure from which rows will be copied.
Returns
Returns 1 on success; 0 on failure, with an error message recorded.

Definition at line 519 of file SDDS_copy.c.

519 {
520 int64_t i, j, sum;
521 int32_t size, target_index;
522 char buffer[1024];
523
524 if (SDDS_target->n_rows_allocated < (sum = SDDS_target->n_rows + SDDS_source->n_rows) && !SDDS_LengthenTable(SDDS_target, sum - SDDS_target->n_rows_allocated)) {
525 SDDS_SetError("Unable to copy additional rows (SDDS_CopyAdditionalRows)");
526 return (0);
527 }
528 if (SDDS_target->layout.n_columns == 0)
529 return 1;
530 for (i = 0; i < SDDS_source->layout.n_columns; i++) {
531 if ((target_index = SDDS_GetColumnIndex(SDDS_target, SDDS_source->layout.column_definition[i].name)) < 0)
532 continue;
533 size = SDDS_GetTypeSize(SDDS_source->layout.column_definition[i].type);
534 if (SDDS_source->layout.column_definition[i].type != SDDS_STRING) {
535 if (SDDS_source->layout.column_definition[i].type == SDDS_target->layout.column_definition[target_index].type) {
536 memcpy((char *)SDDS_target->data[target_index] + size * SDDS_target->n_rows, SDDS_source->data[i], SDDS_type_size[SDDS_source->layout.column_definition[i].type - 1] * SDDS_source->n_rows);
537 } else {
538 for (j = 0; j < SDDS_source->n_rows; j++) {
539 if (!SDDS_CastValue(SDDS_source->data[i], j,
540 SDDS_source->layout.column_definition[i].type, SDDS_target->layout.column_definition[target_index].type, (char *)(SDDS_target->data[target_index]) + (j + SDDS_target->n_rows) * SDDS_type_size[SDDS_target->layout.column_definition[target_index].type - 1])) {
541 sprintf(buffer, "Problem with cast for column %s (SDDS_CopyAdditionalRows)", SDDS_source->layout.column_definition[i].name);
542 SDDS_SetError(buffer);
543 return 0;
544 }
545 }
546 }
547 } else {
548 if (SDDS_source->layout.column_definition[i].type != SDDS_target->layout.column_definition[target_index].type) {
549 sprintf(buffer, "Unable to copy columns---inconsistent data types for %s (SDDS_CopyAdditionalRows)", SDDS_source->layout.column_definition[i].name);
550 SDDS_SetError(buffer);
551 return (0);
552 }
553 if (!SDDS_CopyStringArray((char **)((char *)SDDS_target->data[target_index] + size * SDDS_target->n_rows), SDDS_source->data[i], SDDS_source->n_rows)) {
554 SDDS_SetError("Unable to copy columns (SDDS_CopyAdditionalRows)");
555 return (0);
556 }
557 }
558 SDDS_target->column_flag[target_index] = 1;
559 SDDS_target->column_order[target_index] = target_index;
560 }
561 SDDS_target->n_rows += SDDS_source->n_rows;
562 if (SDDS_target->row_flag)
563 for (i = 0; i < SDDS_target->n_rows; i++)
564 SDDS_target->row_flag[i] = 1;
565
566 return (1);
567}
int32_t SDDS_LengthenTable(SDDS_DATASET *SDDS_dataset, int64_t n_additional_rows)
void * SDDS_CastValue(void *data, int64_t index, int32_t data_type, int32_t desired_type, void *memory)
Casts a value from one SDDS data type to another.
int32_t SDDS_GetTypeSize(int32_t type)
Retrieves the size in bytes of a specified SDDS data type.

◆ SDDS_CopyArrayDefinition()

epicsShareFuncSDDS ARRAY_DEFINITION * SDDS_CopyArrayDefinition ( ARRAY_DEFINITION ** target,
ARRAY_DEFINITION * source )
extern

Creates a copy of an array definition.

This function allocates memory for a new ARRAY_DEFINITION structure and copies the contents from the source array definition to the target. All string fields are duplicated to ensure independent memory management.

Parameters
[out]targetPointer to a ARRAY_DEFINITION* where the copied definition will be stored.
[in]sourcePointer to the ARRAY_DEFINITION structure to be copied. If source is NULL, the target is set to NULL.
Returns
Returns a pointer to the copied ARRAY_DEFINITION structure on success. Returns NULL on failure (e.g., memory allocation failure).
Note
The caller is responsible for freeing the copied array definition using SDDS_FreeArrayDefinition.
See also
SDDS_FreeArrayDefinition
SDDS_Malloc
SDDS_CopyString

Definition at line 1274 of file SDDS_utils.c.

1274 {
1275 if (!target)
1276 return NULL;
1277 if (!source)
1278 return (*target = NULL);
1279 if (!(*target = (ARRAY_DEFINITION *)SDDS_Malloc(sizeof(**target))) ||
1280 !SDDS_CopyString(&(*target)->name, source->name) ||
1281 !SDDS_CopyString(&(*target)->symbol, source->symbol) ||
1282 !SDDS_CopyString(&(*target)->units, source->units) || !SDDS_CopyString(&(*target)->description, source->description) || !SDDS_CopyString(&(*target)->format_string, source->format_string) || !SDDS_CopyString(&(*target)->group_name, source->group_name))
1283 return (NULL);
1284 (*target)->type = source->type;
1285 (*target)->field_length = source->field_length;
1286 (*target)->dimensions = source->dimensions;
1287 return (*target);
1288}

◆ SDDS_CopyArrays()

epicsShareFuncSDDS int32_t SDDS_CopyArrays ( SDDS_DATASET * SDDS_target,
SDDS_DATASET * SDDS_source )
extern

Copies array data from one SDDS_DATASET structure into another for arrays with matching names.

Parameters
SDDS_targetAddress of the SDDS_DATASET structure into which array data will be copied.
SDDS_sourceAddress of the SDDS_DATASET structure from which array data will be copied.
Returns
Returns 1 on success; 0 on failure, with an error message recorded.

Definition at line 334 of file SDDS_copy.c.

334 {
335 int32_t i, j, target_index;
336 char messageBuffer[1024];
337
338 for (i = 0; i < SDDS_source->layout.n_arrays; i++) {
339 if ((target_index = SDDS_GetArrayIndex(SDDS_target, SDDS_source->layout.array_definition[i].name)) < 0)
340 continue;
341 SDDS_target->array[target_index].definition = SDDS_target->layout.array_definition + target_index;
342 SDDS_target->array[target_index].elements = SDDS_source->array[i].elements;
343 if (!(SDDS_target->array[target_index].dimension = (int32_t *)SDDS_Malloc(sizeof(*SDDS_target->array[i].dimension) * SDDS_target->array[target_index].definition->dimensions)) ||
344 !(SDDS_target->array[target_index].data = SDDS_Realloc(SDDS_target->array[target_index].data, SDDS_type_size[SDDS_target->array[target_index].definition->type - 1] * SDDS_target->array[target_index].elements))) {
345 SDDS_SetError("Unable to copy arrays--allocation failure (SDDS_CopyArrays)");
346 return (0);
347 }
348
349 for (j = 0; j < SDDS_target->array[target_index].definition->dimensions; j++)
350 SDDS_target->array[target_index].dimension[j] = SDDS_source->array[i].dimension[j];
351 if (!SDDS_source->array[i].data) {
352 SDDS_target->array[target_index].data = NULL;
353 continue;
354 }
355 if (SDDS_source->layout.array_definition[i].type != SDDS_target->layout.array_definition[target_index].type) {
356 if (!SDDS_NUMERIC_TYPE(SDDS_source->layout.array_definition[i].type) || !SDDS_NUMERIC_TYPE(SDDS_target->layout.array_definition[target_index].type)) {
357 sprintf(messageBuffer, "Can't cast between nonnumeric types for parameters %s and %s (SDDS_CopyArrays)", SDDS_source->layout.array_definition[i].name, SDDS_target->layout.array_definition[target_index].name);
358 SDDS_SetError(messageBuffer);
359 return 0;
360 }
361 for (j = 0; j < SDDS_source->array[i].elements; j++) {
362 if (!SDDS_CastValue(SDDS_source->array[i].data, j, SDDS_source->layout.array_definition[i].type, SDDS_target->layout.array_definition[target_index].type, (char *)(SDDS_target->array[target_index].data) + j * SDDS_type_size[SDDS_target->layout.array_definition[target_index].type - 1])) {
363 SDDS_SetError("Problem with cast (SDDS_CopyArrays)");
364 return 0;
365 }
366 }
367 } else {
368 if (SDDS_target->array[target_index].definition->type != SDDS_STRING)
369 memcpy(SDDS_target->array[target_index].data, SDDS_source->array[i].data, SDDS_type_size[SDDS_target->array[target_index].definition->type - 1] * SDDS_target->array[target_index].elements);
370 else if (!SDDS_CopyStringArray(SDDS_target->array[target_index].data, SDDS_source->array[i].data, SDDS_target->array[target_index].elements)) {
371 SDDS_SetError("Unable to copy arrays (SDDS_CopyArrays)");
372 return (0);
373 }
374 }
375 }
376 return (1);
377}

◆ SDDS_CopyAssociateDefinition()

epicsShareFuncSDDS ASSOCIATE_DEFINITION * SDDS_CopyAssociateDefinition ( ASSOCIATE_DEFINITION ** target,
ASSOCIATE_DEFINITION * source )
extern

Creates a copy of an associate definition.

This function allocates memory for a new ASSOCIATE_DEFINITION structure and copies the contents from the source associate definition to the target. All string fields are duplicated to ensure independent memory management.

Parameters
[out]targetPointer to a ASSOCIATE_DEFINITION* where the copied definition will be stored.
[in]sourcePointer to the ASSOCIATE_DEFINITION structure to be copied. If source is NULL, the target is set to NULL.
Returns
Returns a pointer to the copied ASSOCIATE_DEFINITION structure on success. Returns NULL on failure (e.g., memory allocation failure).
Note
The caller is responsible for freeing the copied associate definition using SDDS_FreeAssociateDefinition.
See also
SDDS_FreeAssociateDefinition
SDDS_Malloc
SDDS_CopyString

Definition at line 986 of file SDDS_utils.c.

986 {
987 if (!source)
988 return (*target = NULL);
989 if (!(*target = (ASSOCIATE_DEFINITION *)SDDS_Malloc(sizeof(**target))) ||
990 !SDDS_CopyString(&(*target)->name, source->name) || !SDDS_CopyString(&(*target)->filename, source->filename) || !SDDS_CopyString(&(*target)->path, source->path) || !SDDS_CopyString(&(*target)->description, source->description) || !SDDS_CopyString(&(*target)->contents, source->contents))
991 return (NULL);
992 (*target)->sdds = source->sdds;
993 return (*target);
994}

◆ SDDS_CopyColumnDefinition()

epicsShareFuncSDDS COLUMN_DEFINITION * SDDS_CopyColumnDefinition ( COLUMN_DEFINITION ** target,
COLUMN_DEFINITION * source )
extern

Creates a copy of a column definition.

This function allocates memory for a new COLUMN_DEFINITION structure and copies the contents from the source column definition to the target. All string fields are duplicated to ensure independent memory management.

Parameters
[out]targetPointer to a COLUMN_DEFINITION* where the copied definition will be stored.
[in]sourcePointer to the COLUMN_DEFINITION structure to be copied. If source is NULL, the target is set to NULL.
Returns
Returns a pointer to the copied COLUMN_DEFINITION structure on success. Returns NULL on failure (e.g., memory allocation failure).
Note
The caller is responsible for freeing the copied column definition using SDDS_FreeColumnDefinition.
See also
SDDS_FreeColumnDefinition
SDDS_Malloc
SDDS_CopyString

Definition at line 1078 of file SDDS_utils.c.

1078 {
1079 if (!target)
1080 return NULL;
1081 if (!source)
1082 return (*target = NULL);
1083 if (!(*target = (COLUMN_DEFINITION *)SDDS_Malloc(sizeof(**target))) ||
1084 !SDDS_CopyString(&(*target)->name, source->name) ||
1085 !SDDS_CopyString(&(*target)->symbol, source->symbol) || !SDDS_CopyString(&(*target)->units, source->units) || !SDDS_CopyString(&(*target)->description, source->description) || !SDDS_CopyString(&(*target)->format_string, source->format_string))
1086 return (NULL);
1087 (*target)->type = source->type;
1088 (*target)->field_length = source->field_length;
1089 (*target)->definition_mode = source->definition_mode;
1090 (*target)->memory_number = source->memory_number;
1091 return (*target);
1092}

◆ SDDS_CopyColumns()

epicsShareFuncSDDS int32_t SDDS_CopyColumns ( SDDS_DATASET * SDDS_target,
SDDS_DATASET * SDDS_source )
extern

Copies column data from one SDDS_DATASET structure into another for columns with matching names.

Parameters
SDDS_targetAddress of the SDDS_DATASET structure into which column data will be copied.
SDDS_sourceAddress of the SDDS_DATASET structure from which column data will be copied.
Returns
Returns 1 on success; 0 on failure, with an error message recorded.

Definition at line 387 of file SDDS_copy.c.

387 {
388 int64_t i, j;
389 int32_t target_index;
390 SDDS_target->n_rows = 0;
391 if (SDDS_target->layout.n_columns && SDDS_target->n_rows_allocated < SDDS_source->n_rows) {
392 SDDS_SetError("Unable to copy columns--insufficient memory allocated to target table");
393 return (0);
394 }
395 if (!SDDS_target->layout.n_columns)
396 return 1;
397 for (i = 0; i < SDDS_source->layout.n_columns; i++) {
398 if ((target_index = SDDS_GetColumnIndex(SDDS_target, SDDS_source->layout.column_definition[i].name)) < 0)
399 continue;
400 if (SDDS_source->layout.column_definition[i].type != SDDS_STRING) {
401 if (SDDS_source->layout.column_definition[i].type == SDDS_target->layout.column_definition[target_index].type)
402 memcpy(SDDS_target->data[target_index], SDDS_source->data[i], SDDS_type_size[SDDS_source->layout.column_definition[i].type - 1] * SDDS_source->n_rows);
403 else {
404 /* Do a cast between the source and target types, if they are both numeric */
405 if (!SDDS_NUMERIC_TYPE(SDDS_source->layout.column_definition[i].type) || !SDDS_NUMERIC_TYPE(SDDS_target->layout.column_definition[target_index].type)) {
406 SDDS_SetError("Can't cast between nonnumeric types (SDDS_CopyColumns)");
407 return 0;
408 }
409 for (j = 0; j < SDDS_source->n_rows; j++) {
410 if (!SDDS_CastValue(SDDS_source->data[i], j, SDDS_source->layout.column_definition[i].type, SDDS_target->layout.column_definition[target_index].type, (char *)(SDDS_target->data[target_index]) + j * SDDS_type_size[SDDS_target->layout.column_definition[target_index].type - 1])) {
411 SDDS_SetError("Problem with cast (SDDS_CopyColumns)");
412 return 0;
413 }
414 }
415 }
416 } else if (!SDDS_CopyStringArray(SDDS_target->data[target_index], SDDS_source->data[i], SDDS_source->n_rows)) {
417 SDDS_SetError("Unable to copy columns (SDDS_CopyColumns)");
418 return (0);
419 }
420 SDDS_target->column_flag[target_index] = 1;
421 SDDS_target->column_order[target_index] = target_index;
422 }
423 SDDS_target->n_rows = SDDS_source->n_rows;
424 if (SDDS_target->row_flag)
425 for (i = 0; i < SDDS_target->n_rows; i++)
426 SDDS_target->row_flag[i] = 1;
427 return (1);
428}

◆ SDDS_CopyLayout()

epicsShareFuncSDDS int32_t SDDS_CopyLayout ( SDDS_DATASET * SDDS_target,
SDDS_DATASET * SDDS_source )
extern

Copies the entire layout (including version, data mode, description, contents, columns, parameters, associates, and arrays) from one SDDS_DATASET to another. The target dataset's existing layout will be replaced.

Parameters
SDDS_targetAddress of the SDDS_DATASET structure into which the layout will be copied.
SDDS_sourceAddress of the SDDS_DATASET structure from which the layout will be copied.
Returns
Returns 1 on success; 0 on failure, with an error message recorded.

Definition at line 222 of file SDDS_copy.c.

222 {
223 SDDS_LAYOUT *target, *source;
224 int64_t i;
225
226 if (!SDDS_CheckDataset(SDDS_target, "SDDS_CopyLayout"))
227 return (0);
228 if (!SDDS_CheckDataset(SDDS_source, "SDDS_CopyLayout"))
229 return (0);
230 target = &SDDS_target->layout;
231 source = &SDDS_source->layout;
232 target->version = source->version;
233 target->data_mode = source->data_mode;
234 target->data_mode.no_row_counts = 0;
235 target->data_mode.fixed_row_count = 0;
236 target->data_mode.column_memory_mode = DEFAULT_COLUMN_MEMORY_MODE;
237 target->layout_written = 0;
238 target->byteOrderDeclared = 0;
239 if (source->description)
240 SDDS_CopyString(&target->description, source->description);
241 if (source->contents)
242 SDDS_CopyString(&target->contents, source->contents);
243 SDDS_DeferSavingLayout(SDDS_target, 1);
244 for (i = 0; i < source->n_columns; i++)
245 if (SDDS_DefineColumn(SDDS_target, source->column_definition[i].name, source->column_definition[i].symbol,
246 source->column_definition[i].units, source->column_definition[i].description, source->column_definition[i].format_string, source->column_definition[i].type, source->column_definition[i].field_length) < 0) {
247 SDDS_SetError("Unable to define column (SDDS_CopyLayout)");
248 return (0);
249 }
250 for (i = 0; i < source->n_parameters; i++)
251 if (SDDS_DefineParameter(SDDS_target, source->parameter_definition[i].name, source->parameter_definition[i].symbol,
252 source->parameter_definition[i].units, source->parameter_definition[i].description, source->parameter_definition[i].format_string, source->parameter_definition[i].type, source->parameter_definition[i].fixed_value) < 0) {
253 SDDS_SetError("Unable to define parameter (SDDS_CopyLayout)");
254 return (0);
255 }
256
257 for (i = 0; i < source->n_associates; i++)
258 if (SDDS_DefineAssociate(SDDS_target, source->associate_definition[i].name, source->associate_definition[i].filename, source->associate_definition[i].path, source->associate_definition[i].description, source->associate_definition[i].contents, source->associate_definition[i].sdds) < 0) {
259 SDDS_SetError("Unable to define associate (SDDS_CopyLayout)");
260 return (0);
261 }
262
263 for (i = 0; i < source->n_arrays; i++)
264 if (SDDS_DefineArray(SDDS_target, source->array_definition[i].name, source->array_definition[i].symbol,
265 source->array_definition[i].units, source->array_definition[i].description,
266 source->array_definition[i].format_string, source->array_definition[i].type, source->array_definition[i].field_length, source->array_definition[i].dimensions, source->array_definition[i].group_name) < 0) {
267 SDDS_SetError("Unable to define array (SDDS_CopyLayout)");
268 return (0);
269 }
270 SDDS_DeferSavingLayout(SDDS_target, 0);
271 if (!SDDS_SaveLayout(SDDS_target)) {
272 SDDS_SetError("Unable to save layout (SDDS_CopyLayout)");
273 return (0);
274 }
275 return (1);
276}

◆ SDDS_CopyPage()

epicsShareFuncSDDS int32_t SDDS_CopyPage ( SDDS_DATASET * SDDS_target,
SDDS_DATASET * SDDS_source )
extern

Copies the data from one SDDS_DATASET structure to another. This includes parameters, arrays, and columns.

Parameters
SDDS_targetPointer to the SDDS_DATASET structure where data will be copied to.
SDDS_sourcePointer to the SDDS_DATASET structure from which data will be copied.
Returns
Returns 1 on success; 0 on failure, with an error message recorded.

Definition at line 578 of file SDDS_copy.c.

578 {
579 if (!SDDS_CheckDataset(SDDS_target, "SDDS_CopyPage"))
580 return (0);
581 if (!SDDS_CheckDataset(SDDS_source, "SDDS_CopyPage"))
582 return (0);
583
584 if (!SDDS_StartPage(SDDS_target, SDDS_target->layout.n_columns ? SDDS_source->n_rows : 0)) {
585 SDDS_SetError("Unable to copy page (SDDS_CopyPage)");
586 return (0);
587 }
588 if (!SDDS_CopyParameters(SDDS_target, SDDS_source))
589 return (0);
590 if (!SDDS_CopyArrays(SDDS_target, SDDS_source))
591 return (0);
592 if (!SDDS_CopyColumns(SDDS_target, SDDS_source))
593 return (0);
594 return (1);
595}
int32_t SDDS_CopyColumns(SDDS_DATASET *SDDS_target, SDDS_DATASET *SDDS_source)
Definition SDDS_copy.c:387
int32_t SDDS_CopyParameters(SDDS_DATASET *SDDS_target, SDDS_DATASET *SDDS_source)
Definition SDDS_copy.c:286
int32_t SDDS_CopyArrays(SDDS_DATASET *SDDS_target, SDDS_DATASET *SDDS_source)
Definition SDDS_copy.c:334
int32_t SDDS_StartPage(SDDS_DATASET *SDDS_dataset, int64_t expected_n_rows)

◆ SDDS_CopyParameterDefinition()

epicsShareFuncSDDS PARAMETER_DEFINITION * SDDS_CopyParameterDefinition ( PARAMETER_DEFINITION ** target,
PARAMETER_DEFINITION * source )
extern

Creates a copy of a parameter definition.

This function allocates memory for a new PARAMETER_DEFINITION structure and copies the contents from the source parameter definition to the target. All string fields are duplicated to ensure independent memory management.

Parameters
[out]targetPointer to a PARAMETER_DEFINITION* where the copied definition will be stored.
[in]sourcePointer to the PARAMETER_DEFINITION structure to be copied. If source is NULL, the target is set to NULL.
Returns
Returns a pointer to the copied PARAMETER_DEFINITION structure on success. Returns NULL on failure (e.g., memory allocation failure).
Note
The caller is responsible for freeing the copied parameter definition using SDDS_FreeParameterDefinition.
See also
SDDS_FreeParameterDefinition
SDDS_Malloc
SDDS_CopyString

Definition at line 1175 of file SDDS_utils.c.

1175 {
1176 if (!target)
1177 return NULL;
1178 if (!source)
1179 return (*target = NULL);
1180 if (!(*target = (PARAMETER_DEFINITION *)SDDS_Malloc(sizeof(**target))) ||
1181 !SDDS_CopyString(&(*target)->name, source->name) ||
1182 !SDDS_CopyString(&(*target)->symbol, source->symbol) ||
1183 !SDDS_CopyString(&(*target)->units, source->units) || !SDDS_CopyString(&(*target)->description, source->description) || !SDDS_CopyString(&(*target)->format_string, source->format_string) || !SDDS_CopyString(&(*target)->fixed_value, source->fixed_value))
1184 return (NULL);
1185 (*target)->type = source->type;
1186 (*target)->definition_mode = source->definition_mode;
1187 (*target)->memory_number = source->memory_number;
1188 return (*target);
1189}

◆ SDDS_CopyParameters()

epicsShareFuncSDDS int32_t SDDS_CopyParameters ( SDDS_DATASET * SDDS_target,
SDDS_DATASET * SDDS_source )
extern

Copies parameter values from one SDDS_DATASET structure into another for parameters with matching names.

Parameters
SDDS_targetAddress of the SDDS_DATASET structure into which parameter values will be copied.
SDDS_sourceAddress of the SDDS_DATASET structure from which parameter values will be copied.
Returns
Returns 1 on success; 0 on failure, with an error message recorded.

Definition at line 286 of file SDDS_copy.c.

286 {
287 int32_t i, target_index;
288 char *buffer = NULL; /* will be sized to hold any SDDS data type with room to spare */
289 char messageBuffer[1024];
290
291 if (!buffer && !(buffer = SDDS_Malloc(sizeof(char) * 16))) {
292 SDDS_SetError("Allocation failure (SDDS_CopyParameters)");
293 return 0;
294 }
295
296 if (!SDDS_CheckDataset(SDDS_target, "SDDS_CopyParameters"))
297 return (0);
298 if (!SDDS_CheckDataset(SDDS_source, "SDDS_CopyParameters"))
299 return (0);
300
301 for (i = 0; i < SDDS_source->layout.n_parameters; i++) {
302 if ((target_index = SDDS_GetParameterIndex(SDDS_target, SDDS_source->layout.parameter_definition[i].name)) < 0)
303 continue;
304 if (SDDS_source->layout.parameter_definition[i].type != SDDS_target->layout.parameter_definition[target_index].type) {
305 if (!SDDS_NUMERIC_TYPE(SDDS_source->layout.parameter_definition[i].type) || !SDDS_NUMERIC_TYPE(SDDS_target->layout.parameter_definition[target_index].type)) {
306 sprintf(messageBuffer, "Can't cast between nonnumeric types for parameters %s and %s (SDDS_CopyParameters)", SDDS_source->layout.parameter_definition[i].name, SDDS_target->layout.parameter_definition[target_index].name);
307 SDDS_SetError(messageBuffer);
308 return 0;
309 }
310 if (!SDDS_SetParameters(SDDS_target, SDDS_SET_BY_INDEX | SDDS_PASS_BY_REFERENCE, target_index, SDDS_CastValue(SDDS_source->parameter[i], 0, SDDS_source->layout.parameter_definition[i].type, SDDS_target->layout.parameter_definition[target_index].type, buffer), -1)) {
311 sprintf(messageBuffer, "Error setting parameter with cast value for parameters %s and %s (SDDS_CopyParameters)", SDDS_source->layout.parameter_definition[i].name, SDDS_target->layout.parameter_definition[target_index].name);
312 SDDS_SetError(messageBuffer);
313 return 0;
314 }
315 } else if (!SDDS_SetParameters(SDDS_target, SDDS_SET_BY_INDEX | SDDS_PASS_BY_REFERENCE, target_index, SDDS_source->parameter[i], -1)) {
316 sprintf(messageBuffer, "Unable to copy parameters for parameters %s and %s (SDDS_CopyParameters)", SDDS_source->layout.parameter_definition[i].name, SDDS_target->layout.parameter_definition[target_index].name);
317 SDDS_SetError(messageBuffer);
318 return (0);
319 }
320 }
321 if (buffer)
322 free(buffer);
323 return (1);
324}
int32_t SDDS_SetParameters(SDDS_DATASET *SDDS_dataset, int32_t mode,...)

◆ SDDS_CopyRow()

epicsShareFuncSDDS int32_t SDDS_CopyRow ( SDDS_DATASET * SDDS_target,
int64_t target_row,
SDDS_DATASET * SDDS_source,
int64_t source_srow )
extern

Copies a row from the source SDDS_DATASET to the target SDDS_DATASET. Only columns that exist in both datasets are copied. The source row is determined by its position among the selected rows.

Parameters
SDDS_targetPointer to the SDDS_DATASET structure where the row will be copied to.
target_rowIndex of the row in the target dataset where data will be placed.
SDDS_sourcePointer to the SDDS_DATASET structure from which the row will be copied.
source_srowIndex of the selected row (among rows of interest) in the source dataset.
Returns
Returns 1 on success; 0 on failure, with an error message recorded.

Definition at line 778 of file SDDS_copy.c.

778 {
779 int64_t i, j, source_row;
780 int32_t size, type;
781
782 if (!SDDS_CheckDataset(SDDS_target, "SDDS_CopyRow"))
783 return (0);
784 if (!SDDS_CheckDataset(SDDS_source, "SDDS_CopyRow"))
785 return (0);
786
787 if (target_row >= SDDS_target->n_rows_allocated) {
788 SDDS_SetError("Unable to copy row--target page not large enough");
789 return (0);
790 }
791 if (SDDS_target->n_rows <= target_row)
792 SDDS_target->n_rows = target_row + 1;
793
794 source_row = -1;
795 for (i = j = 0; i < SDDS_source->n_rows; i++)
796 if (SDDS_source->row_flag[i] && j++ == source_srow) {
797 source_row = i;
798 break;
799 }
800
801 if (source_row == -1) {
802 SDDS_SetError("Unable to copy row--source selected-row does not exist");
803 return (0);
804 }
805
806 for (i = 0; i < SDDS_target->layout.n_columns; i++) {
807 if ((j = SDDS_GetColumnIndex(SDDS_source, SDDS_target->layout.column_definition[i].name)) < 0 || !SDDS_source->column_flag[j])
808 continue;
809 if ((type = SDDS_GetColumnType(SDDS_target, i)) == SDDS_STRING) {
810 if (!SDDS_CopyString(((char ***)SDDS_target->data)[i] + target_row, ((char ***)SDDS_source->data)[j][source_row])) {
811 SDDS_SetError("Unable to copy row--string copy failed (SDDS_CopyRow)");
812 return (0);
813 }
814 } else {
815 size = SDDS_type_size[type - 1];
816 memcpy((char *)SDDS_target->data[i] + size * target_row, (char *)SDDS_source->data[j] + size * source_row, size);
817 }
818 SDDS_target->row_flag[target_row] = 1;
819 }
820 return (1);
821}

◆ SDDS_CopyRowDirect()

epicsShareFuncSDDS int32_t SDDS_CopyRowDirect ( SDDS_DATASET * SDDS_target,
int64_t target_row,
SDDS_DATASET * SDDS_source,
int64_t source_row )
extern

Copies a specific row from the source SDDS_DATASET to the target SDDS_DATASET. Only columns that exist in both datasets are copied.

Parameters
SDDS_targetPointer to the SDDS_DATASET structure where the row will be copied to.
target_rowIndex of the row in the target dataset where data will be placed.
SDDS_sourcePointer to the SDDS_DATASET structure from which the row will be copied.
source_rowIndex of the row in the source dataset to be copied.
Returns
Returns 1 on success; 0 on failure, with an error message recorded.

Definition at line 834 of file SDDS_copy.c.

834 {
835 int64_t i, j;
836 int32_t size, type;
837
838 if (!SDDS_CheckDataset(SDDS_target, "SDDS_CopyRow"))
839 return (0);
840 if (!SDDS_CheckDataset(SDDS_source, "SDDS_CopyRow"))
841 return (0);
842
843 if (target_row >= SDDS_target->n_rows_allocated) {
844 SDDS_SetError("Unable to copy row--target page not large enough");
845 return (0);
846 }
847 if (SDDS_target->n_rows <= target_row)
848 SDDS_target->n_rows = target_row + 1;
849 if (source_row >= SDDS_source->n_rows_allocated) {
850 SDDS_SetError("Unable to copy row--source row non-existent");
851 return (0);
852 }
853
854 for (i = 0; i < SDDS_target->layout.n_columns; i++) {
855 if ((j = SDDS_GetColumnIndex(SDDS_source, SDDS_target->layout.column_definition[i].name)) < 0 || !SDDS_source->column_flag[j])
856 continue;
857 if ((type = SDDS_GetColumnType(SDDS_target, i)) == SDDS_STRING) {
858 if (!SDDS_CopyString(((char ***)SDDS_target->data)[i] + target_row, ((char ***)SDDS_source->data)[j][source_row])) {
859 SDDS_SetError("Unable to copy row--string copy failed (SDDS_CopyRow)");
860 return (0);
861 }
862 } else {
863 size = SDDS_type_size[type - 1];
864 memcpy((char *)SDDS_target->data[i] + size * target_row, (char *)SDDS_source->data[j] + size * source_row, size);
865 }
866 SDDS_target->row_flag[target_row] = 1;
867 }
868 return (1);
869}

◆ SDDS_CopyRows()

epicsShareFuncSDDS int32_t SDDS_CopyRows ( SDDS_DATASET * SDDS_target,
SDDS_DATASET * SDDS_source,
int64_t firstRow,
int64_t lastRow )
extern

Copies a range of rows from the source SDDS_DATASET to the target SDDS_DATASET. Only columns that exist in both datasets are copied.

Parameters
SDDS_targetPointer to the SDDS_DATASET structure where rows will be copied to.
SDDS_sourcePointer to the SDDS_DATASET structure from which rows will be copied.
firstRowIndex of the first row to copy from the source dataset.
lastRowIndex of the last row to copy from the source dataset.
Returns
Returns 1 on success; 0 on failure, with an error message recorded.

Definition at line 882 of file SDDS_copy.c.

882 {
883 int64_t i, j, k;
884 int32_t size, target_index;
885 char buffer[1024];
886 int64_t *rowList, roi;
887 k = 0;
888
889 if (!SDDS_target->layout.n_columns)
890 return 1;
891 roi = lastRow - firstRow + 1;
892 if (roi > SDDS_target->n_rows_allocated) {
893 SDDS_SetError("Unable to copy rows of interest--insufficient memory allocated to target page (SDDS_CopyRows)");
894 return 0;
895 }
896 rowList = malloc(sizeof(*rowList) * roi);
897 k = 0;
898
899 for (j = firstRow; j <= lastRow; j++) {
900 rowList[k] = j;
901 k++;
902 }
903
904 for (i = 0; i < SDDS_source->layout.n_columns; i++) {
905 if ((target_index = SDDS_GetColumnIndex(SDDS_target, SDDS_source->layout.column_definition[i].name)) < 0)
906 continue;
907 if (SDDS_source->layout.column_definition[i].type != SDDS_STRING) {
908 if (SDDS_source->layout.column_definition[i].type == SDDS_target->layout.column_definition[target_index].type) {
909 size = SDDS_type_size[SDDS_source->layout.column_definition[i].type - 1];
910 for (k = 0; k < roi; k++) {
911
912 memcpy((char *)SDDS_target->data[target_index] + k * size, (char *)SDDS_source->data[i] + rowList[k] * size, SDDS_type_size[SDDS_source->layout.column_definition[i].type - 1]);
913 }
914 } else {
915 for (k = 0; k < roi; k++) {
916 if (!SDDS_CastValue(SDDS_source->data[i], rowList[k],
917 SDDS_source->layout.column_definition[i].type, SDDS_target->layout.column_definition[target_index].type, (char *)(SDDS_target->data[target_index]) + k * SDDS_type_size[SDDS_target->layout.column_definition[target_index].type - 1])) {
918 sprintf(buffer, "Problem with cast for column %s (SDDS_CopyRows)", SDDS_source->layout.column_definition[i].name);
919 SDDS_SetError(buffer);
920 return 0;
921 }
922 }
923 }
924 } else {
925 if (SDDS_source->layout.column_definition[i].type != SDDS_target->layout.column_definition[target_index].type) {
926 sprintf(buffer, "Unable to copy columns---inconsistent data types for %s (SDDS_CopyRows)", SDDS_source->layout.column_definition[i].name);
927 SDDS_SetError(buffer);
928 return (0);
929 }
930 for (k = 0; k < roi; k++) {
931 if (((char **)SDDS_target->data[target_index])[k])
932 free(((char **)SDDS_target->data[target_index])[k]);
933 if (!SDDS_CopyString(&((char **)SDDS_target->data[target_index])[k], ((char **)SDDS_source->data[i])[rowList[k]])) {
934 SDDS_SetError("Unable to copy rows (SDDS_CopyRows)");
935 return (0);
936 }
937 }
938 }
939 SDDS_target->column_flag[target_index] = 1;
940 SDDS_target->column_order[target_index] = target_index;
941 }
942
943 free(rowList);
944
945 SDDS_target->n_rows = roi;
946 if (SDDS_target->row_flag) {
947 for (i = 0; i < roi; i++) {
948 SDDS_target->row_flag[i] = 1;
949 }
950 }
951
952 return (1);
953}

◆ SDDS_CopyRowsOfInterest()

epicsShareFuncSDDS int32_t SDDS_CopyRowsOfInterest ( SDDS_DATASET * SDDS_target,
SDDS_DATASET * SDDS_source )
extern

Copies rows of interest from the source SDDS_DATASET to the target SDDS_DATASET for columns with matching names. Rows of interest are those that have their row flags set in the source dataset.

Parameters
SDDS_targetAddress of the SDDS_DATASET structure into which rows will be copied.
SDDS_sourceAddress of the SDDS_DATASET structure from which rows will be copied.
Returns
Returns 1 on success; 0 on failure, with an error message recorded.

Definition at line 439 of file SDDS_copy.c.

439 {
440 int64_t i, j, k;
441 int32_t size, target_index;
442 /* int32_t rows; */
443 char buffer[1024];
444 int64_t *rowList, roi;
445 k = 0;
446
447 if (!SDDS_target->layout.n_columns)
448 return 1;
449 roi = SDDS_CountRowsOfInterest(SDDS_source);
450 if (roi > SDDS_target->n_rows_allocated) {
451 SDDS_SetError("Unable to copy rows of interest--insufficient memory allocated to target page (SDDS_CopyRowsOfInterest)");
452 return 0;
453 }
454
455 rowList = malloc(sizeof(*rowList) * roi);
456 k = 0;
457 for (j = 0; j < SDDS_source->n_rows; j++) {
458 if (SDDS_source->row_flag[j]) {
459 rowList[k] = j;
460 k++;
461 }
462 }
463
464 for (i = 0; i < SDDS_source->layout.n_columns; i++) {
465 if ((target_index = SDDS_GetColumnIndex(SDDS_target, SDDS_source->layout.column_definition[i].name)) < 0)
466 continue;
467 if (SDDS_source->layout.column_definition[i].type != SDDS_STRING) {
468 if (SDDS_source->layout.column_definition[i].type == SDDS_target->layout.column_definition[target_index].type) {
469 size = SDDS_type_size[SDDS_source->layout.column_definition[i].type - 1];
470 for (k = 0; k < roi; k++) {
471 memcpy((char *)SDDS_target->data[target_index] + k * size, (char *)SDDS_source->data[i] + rowList[k] * size, SDDS_type_size[SDDS_source->layout.column_definition[i].type - 1]);
472 }
473 } else {
474 for (k = 0; k < roi; k++) {
475 if (!SDDS_CastValue(SDDS_source->data[i], rowList[k],
476 SDDS_source->layout.column_definition[i].type, SDDS_target->layout.column_definition[target_index].type, (char *)(SDDS_target->data[target_index]) + k * SDDS_type_size[SDDS_target->layout.column_definition[target_index].type - 1])) {
477 sprintf(buffer, "Problem with cast for column %s (SDDS_CopyRowsOfInterest)", SDDS_source->layout.column_definition[i].name);
478 SDDS_SetError(buffer);
479 return 0;
480 }
481 }
482 }
483 } else {
484 if (SDDS_source->layout.column_definition[i].type != SDDS_target->layout.column_definition[target_index].type) {
485 sprintf(buffer, "Unable to copy columns---inconsistent data types for %s (SDDS_CopyRowsOfInterest)", SDDS_source->layout.column_definition[i].name);
486 SDDS_SetError(buffer);
487 return (0);
488 }
489 for (k = 0; k < roi; k++) {
490 if (((char **)SDDS_target->data[target_index])[k])
491 free(((char **)SDDS_target->data[target_index])[k]);
492 if (!SDDS_CopyString(&((char **)SDDS_target->data[target_index])[k], ((char **)SDDS_source->data[i])[rowList[k]])) {
493 SDDS_SetError("Unable to copy rows (SDDS_CopyRowsOfInterest)");
494 return (0);
495 }
496 }
497 }
498 SDDS_target->column_flag[target_index] = 1;
499 SDDS_target->column_order[target_index] = target_index;
500 }
501 free(rowList);
502 SDDS_target->n_rows = roi;
503 if (SDDS_target->row_flag)
504 for (i = 0; i < SDDS_target->n_rows; i++)
505 SDDS_target->row_flag[i] = 1;
506
507 return (1);
508}
int64_t SDDS_CountRowsOfInterest(SDDS_DATASET *SDDS_dataset)
Counts the number of rows marked as "of interest" in the current data table.

◆ SDDS_CopyString()

epicsShareFuncSDDS int32_t SDDS_CopyString ( char ** target,
const char * source )
extern

Copies a source string to a target string with memory allocation.

This function allocates memory for the target string and copies the contents of the source string into it. If the source string is NULL, the target string is set to NULL.

Parameters
[out]targetPointer to a char* variable where the copied string will be stored. Memory is allocated within this function and should be freed by the caller to avoid memory leaks.
[in]sourceThe source string to be copied. If NULL, the target is set to NULL.
Returns
Returns 1 on successful copy and memory allocation. Returns 0 on error (e.g., memory allocation failure).
Note
The caller is responsible for freeing the memory allocated for the target string.
See also
SDDS_Free
SDDS_Malloc

Definition at line 922 of file SDDS_utils.c.

922 {
923 if (!source)
924 *target = NULL;
925 else {
926 if (!(*target = SDDS_Malloc(sizeof(**target) * (strlen(source) + 1))))
927 return (0);
928 strcpy(*target, source);
929 }
930 return (1);
931}

◆ SDDS_CopyStringArray()

epicsShareFuncSDDS int32_t SDDS_CopyStringArray ( char ** target,
char ** source,
int64_t n_strings )
extern

Copies an array of strings from source to target.

This function duplicates each string from the source array into the target array. It handles memory allocation for each individual string using SDDS_CopyString.

Parameters
[in]targetPointer to the destination array of strings where the copied strings will be stored.
[in]sourcePointer to the source array of strings to be copied.
[in]n_stringsThe number of strings to copy from the source to the target.
Returns
  • Returns 1 on successful copying of all strings.
  • Returns 0 if either source or target is NULL, or if any string copy operation fails.
Note
  • The caller is responsible for ensuring that the target array has sufficient space allocated.
  • In case of failure, partially copied strings may remain in the target array.
See also
SDDS_CopyString
SDDS_Malloc

Definition at line 2903 of file SDDS_utils.c.

2903 {
2904 if (!source || !target)
2905 return (0);
2906 while (n_strings--) {
2907 if (!SDDS_CopyString(target + n_strings, source[n_strings]))
2908 return (0);
2909 }
2910 return (1);
2911}

◆ SDDS_CountColumnsOfInterest()

epicsShareFuncSDDS int32_t SDDS_CountColumnsOfInterest ( SDDS_DATASET * SDDS_dataset)
extern

Counts the number of columns marked as "of interest" in the current data table.

This function returns the total number of columns that have been flagged as "of interest" based on their acceptance flags.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the data set.
Returns
  • Non-negative integer representing the number of columns marked as "of interest".
  • -1 if the dataset is invalid.
See also
SDDS_CountRowsOfInterest, SDDS_SetColumnFlags, SDDS_GetColumnFlags

Definition at line 342 of file SDDS_extract.c.

342 {
343 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_CountRowsOfInterest"))
344 return (-1);
345 return (SDDS_dataset->n_of_interest);
346}

◆ SDDS_CountRowsOfInterest()

epicsShareFuncSDDS int64_t SDDS_CountRowsOfInterest ( SDDS_DATASET * SDDS_dataset)
extern

Counts the number of rows marked as "of interest" in the current data table.

This function iterates through the row acceptance flags and tallies the number of rows that are flagged as "of interest" (non-zero).

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the data set.
Returns
  • Number of rows with non-zero acceptance flags.
  • -1 on error (e.g., invalid dataset or tabular data).
Note
Ensure that the dataset contains tabular data before invoking this function.
See also
SDDS_SetRowFlags, SDDS_GetRowFlags, SDDS_GetRowFlag

Definition at line 364 of file SDDS_extract.c.

364 {
365 int64_t n_rows, i;
366 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_CountRowsOfInterest"))
367 return (-1);
368 if (!SDDS_CheckTabularData(SDDS_dataset, "SDDS_CountRowsOfInterest"))
369 return (-1);
370 if (!SDDS_dataset->layout.n_columns)
371 return 0;
372 for (i = n_rows = 0; i < SDDS_dataset->n_rows; i++) {
373 if (SDDS_dataset->row_flag[i])
374 n_rows += 1;
375 }
376 return (n_rows);
377}
int32_t SDDS_CheckTabularData(SDDS_DATASET *SDDS_dataset, const char *caller)
Validates the consistency of tabular data within an SDDS dataset.
Definition SDDS_utils.c:643

◆ SDDS_CreateEmptyDataset()

epicsShareFuncSDDS SDDS_DATASET * SDDS_CreateEmptyDataset ( void )
extern

Creates an empty SDDS dataset.

This function allocates and initializes an empty SDDS_DATASET structure. The returned dataset can then be configured and populated with columns, parameters, and arrays as needed.

Returns
  • Pointer to the newly created SDDS_DATASET structure.
  • NULL if memory allocation fails.
Note
  • The caller is responsible for initializing the dataset's layout and other necessary fields before use.
  • Ensure that the returned dataset is properly freed using appropriate memory deallocation functions to prevent memory leaks.
Warning
  • Failing to initialize the dataset after creation may lead to undefined behavior when performing operations on it.
  • Always check if the returned pointer is not NULL before using it.
See also
SDDS_FreeDataset, SDDS_InitLayout

Definition at line 5719 of file SDDS_utils.c.

5719 {
5720 SDDS_DATASET *dataset;
5721 dataset = malloc(sizeof(SDDS_DATASET));
5722 return dataset;
5723}

◆ SDDS_CreateRpnArray()

epicsShareFuncSDDS int64_t SDDS_CreateRpnArray ( char * name)
extern

Stub function for creating RPN arrays when RPN_SUPPORT is not enabled.

Parameters
nameName of the RPN array.
Returns
Always returns 1.

Definition at line 835 of file SDDS_rpn.c.

835 {
836 return (1);
837}

◆ SDDS_CreateRpnMemory()

epicsShareFuncSDDS int64_t SDDS_CreateRpnMemory ( const char * name,
short is_string )
extern

Stub function for creating RPN memory when RPN_SUPPORT is not enabled.

Parameters
nameName of the RPN memory.
is_stringFlag indicating if the memory is for string data.
Returns
Always returns 1.

Definition at line 825 of file SDDS_rpn.c.

825 {
826 return (1);
827}

◆ SDDS_CutOutComments()

epicsShareFuncSDDS void SDDS_CutOutComments ( SDDS_DATASET * SDDS_dataset,
char * s,
char cc )
extern

Removes comments from a string based on a specified comment character.

This function processes a string s, removing any content that follows the comment character cc. It also handles special comment lines that start with !# by parsing them using SDDS_ParseSpecialComments. The function ensures that quoted sections within the string are preserved and not mistakenly identified as comments.

Parameters
[in]SDDS_datasetPointer to the SDDS_DATASET structure used for processing special comments.
[in,out]sPointer to the character array containing the string to process. The string will be modified in place.
[in]ccThe comment character indicating the start of a comment.
Note
If the first character of the string is the comment character, the entire line is treated as a comment. Otherwise, only the portion of the string following the first unescaped comment character is removed.
See also
SDDS_ParseSpecialComments

Definition at line 1746 of file SDDS_utils.c.

1746 {
1747 int32_t length, hasNewline;
1748 char *s0;
1749
1750 if (!cc || !s)
1751 return;
1752
1753 hasNewline = 0;
1754 length = strlen(s);
1755 if (s[length - 1] == '\n')
1756 hasNewline = 1;
1757
1758 if (*s == cc) {
1759 /* check for special information */
1760 if (*(s + 1) == '#')
1761 SDDS_ParseSpecialComments(SDDS_dataset, s + 2);
1762 *s = 0;
1763 return;
1764 }
1765 s0 = s;
1766 while (*s) {
1767 if ((*s == '"') && (s == s0 || *(s - 1) != '\\')) {
1768 while (*++s && (*s != '"' || *(s - 1) == '\\'))
1769 ;
1770 if (!*s)
1771 return;
1772 s++;
1773 continue;
1774 }
1775 if (*s == cc) {
1776 if (s != s0 && *(s - 1) == '\\')
1777 strcpy_ss(s - 1, s);
1778 else {
1779 if (hasNewline) {
1780 *s = '\n';
1781 *(s + 1) = 0;
1782 } else
1783 *s = 0;
1784 return;
1785 }
1786 }
1787 s++;
1788 }
1789}
char * strcpy_ss(char *dest, const char *src)
Safely copies a string, handling memory overlap.
Definition str_copy.c:34

◆ SDDS_DeferSavingLayout()

epicsShareFuncSDDS void SDDS_DeferSavingLayout ( SDDS_DATASET * SDDS_dataset,
int32_t mode )
extern

Sets the flag to defer or resume saving the layout of an SDDS_DATASET.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure.
modeNon-zero value to defer saving the layout; zero to resume saving.

Definition at line 603 of file SDDS_copy.c.

603 {
604 SDDS_dataset->deferSavingLayout = mode;
605}

◆ SDDS_DefineArray()

epicsShareFuncSDDS int32_t SDDS_DefineArray ( SDDS_DATASET * SDDS_dataset,
const char * name,
const char * symbol,
const char * units,
const char * description,
const char * format_string,
int32_t type,
int32_t field_length,
int32_t dimensions,
const char * group_name )
extern

Defines a data array within the SDDS dataset.

This function processes the definition of a data array in the SDDS dataset. It allows the user to specify the array's name, symbol, units, description, format string, data type, field length, number of dimensions, and associated group name. The function ensures that the array name is valid and unique within the dataset before defining it.

Parameters
[in,out]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
[in]nameA NULL-terminated string specifying the name of the array. This name must be unique within the dataset.
[in]symbolA NULL-terminated string specifying the symbol for the array. Pass NULL if no symbol is desired.
[in]unitsA NULL-terminated string specifying the units of the array. Pass NULL if no units are desired.
[in]descriptionA NULL-terminated string providing a description of the array. Pass NULL if no description is desired.
[in]format_stringA NULL-terminated string specifying the printf-style format for ASCII output. If NULL is passed, a default format is selected based on the array type.
[in]typeAn integer representing the data type of the array. Must be one of the following:
  • SDDS_LONGDOUBLE
  • SDDS_DOUBLE
  • SDDS_FLOAT
  • SDDS_LONG
  • SDDS_ULONG
  • SDDS_SHORT
  • SDDS_USHORT
  • SDDS_CHARACTER
  • SDDS_STRING
[in]field_lengthAn integer specifying the length of the field allotted to the array for ASCII output. If set to 0, the field length is ignored. If negative, the field length is set to the absolute value, and leading and trailing white-space are eliminated for SDDS_STRING types upon reading.
[in]dimensionsAn integer specifying the number of dimensions of the array. Must be greater than 0.
[in]group_nameA NULL-terminated string specifying the name of the array group to which this array belongs. This allows related arrays to be grouped together (e.g., parallel arrays).
Returns
  • On success, returns the index of the newly defined array within the dataset.
  • Returns -1 on failure, with an error message set internally.
Precondition
  • The dataset must be initialized and configured for output.
  • The array name must be unique and valid.
  • The specified data type must be supported by the dataset.
Postcondition
  • The array is defined within the dataset with the specified attributes.
  • The dataset's internal structures are updated to include the new array.
Note
  • For string-type arrays, the fixed value is managed differently, and leading/trailing white-space is handled based on the field length parameter.
  • The function supports multi-dimensional arrays as specified by the dimensions parameter.
Warning
  • Defining an array with an invalid type, field length, or number of dimensions will result in an error.
  • Attempting to define an array with a name that already exists within the dataset will result in an error.

Definition at line 1599 of file SDDS_output.c.

1599 {
1600 SDDS_LAYOUT *layout;
1601 ARRAY_DEFINITION *definition;
1602 char s[SDDS_MAXLINE];
1603 SORTED_INDEX *new_indexed_array;
1604 int32_t index, duplicate;
1605
1606 if (!SDDS_IsValidName(name, "array"))
1607 return -1;
1608 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_DefineArray"))
1609 return (-1);
1610 if (!name) {
1611 SDDS_SetError("NULL name not allowed for array definition");
1612 return (-1);
1613 }
1614 layout = &SDDS_dataset->layout;
1615 if (!(layout->array_definition =
1616 SDDS_Realloc(layout->array_definition, sizeof(*layout->array_definition) * (layout->n_arrays + 1))) ||
1617 !(layout->array_index = SDDS_Realloc(layout->array_index, sizeof(*layout->array_index) * (layout->n_arrays + 1))) || !(new_indexed_array = (SORTED_INDEX *)SDDS_Malloc(sizeof(*new_indexed_array)))) {
1618 SDDS_SetError("Memory allocation failure (SDDS_DefineArray)");
1619 return (-1);
1620 }
1621
1622 if (!SDDS_CopyString(&new_indexed_array->name, name))
1623 return -1;
1624 index = binaryInsert((void **)layout->array_index, layout->n_arrays, new_indexed_array, SDDS_CompareIndexedNames, &duplicate);
1625 if (duplicate) {
1626 sprintf(s, "Array %s already exists (SDDS_DefineArray)", name);
1627 SDDS_SetError(s);
1628 return (-1);
1629 }
1630 layout->array_index[index]->index = layout->n_arrays;
1631
1632 if (!SDDS_ZeroMemory(definition = layout->array_definition + layout->n_arrays, sizeof(ARRAY_DEFINITION))) {
1633 SDDS_SetError("Unable to define array--can't zero memory for array definition (SDDS_DefineArray)");
1634 return (-1);
1635 }
1636 definition->name = new_indexed_array->name;
1637 if ((symbol && !SDDS_CopyString(&definition->symbol, symbol)) || (units && !SDDS_CopyString(&definition->units, units)) || (description && !SDDS_CopyString(&definition->description, description)) || (group_name && !SDDS_CopyString(&definition->group_name, group_name))) {
1638 SDDS_SetError("Memory allocation failure (SDDS_DefineArray)");
1639 return (-1);
1640 }
1641 if (type <= 0 || type > SDDS_NUM_TYPES) {
1642 SDDS_SetError("Unknown data type (SDDS_DefineArray)");
1643 return (-1);
1644 }
1645 definition->type = type;
1646 if (format_string) {
1647 if (!SDDS_VerifyPrintfFormat(format_string, type)) {
1648 SDDS_SetError("Invalid format string (SDDS_DefineArray)");
1649 return (-1);
1650 }
1651 if (!SDDS_CopyString(&definition->format_string, format_string)) {
1652 SDDS_SetError("Memory allocation failure (SDDS_DefineArray)");
1653 return (-1);
1654 }
1655 }
1656 if ((definition->field_length = field_length) < 0 && type != SDDS_STRING) {
1657 SDDS_SetError("Invalid field length (SDDS_DefineArray)");
1658 return (-1);
1659 }
1660 if ((definition->dimensions = dimensions) < 1) {
1661 SDDS_SetError("Invalid number of dimensions for array (SDDS_DefineArray)");
1662 return (-1);
1663 }
1664 layout->n_arrays += 1;
1665 return (layout->n_arrays - 1);
1666}
int32_t SDDS_IsValidName(const char *name, const char *class)
Checks if a given name is valid for a specified class within the SDDS dataset.
int SDDS_CompareIndexedNames(const void *s1, const void *s2)
Compares two SORTED_INDEX structures by their name fields.
int32_t SDDS_VerifyPrintfFormat(const char *string, int32_t type)
Verifies that a printf format string is compatible with a specified data type.
Definition SDDS_utils.c:816
#define SDDS_NUM_TYPES
Total number of defined SDDS data types.
Definition SDDStypes.h:97
long binaryInsert(void **array, long members, void *newMember, int(*compare)(const void *c1, const void *c2), int32_t *duplicate)
Inserts a new member into a sorted array using binary search.
Definition binsert.c:39

◆ SDDS_DefineAssociate()

epicsShareFuncSDDS int32_t SDDS_DefineAssociate ( SDDS_DATASET * SDDS_dataset,
const char * name,
const char * filename,
const char * path,
const char * description,
const char * contents,
int32_t sdds )
extern

Defines an associate for the SDDS dataset.

This function defines an associate for the SDDS dataset, allowing the association of additional files or data with the primary dataset. Associates can provide supplementary information or link related datasets together. The function sets up the necessary attributes such as name, filename, path, description, contents, and SDDS flag to describe the associate.

Note: This function is NOT USED in the current implementation and will always return 0 unless compiled with RW_ASSOCIATES defined.

Parameters
[in,out]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
[in]nameA NULL-terminated string specifying the name of the associate. This name must be unique within the dataset.
[in]filenameA NULL-terminated string specifying the filename of the associate. Must be a valid filename.
[in]pathA NULL-terminated string specifying the path to the associate. Pass NULL if no path is desired.
[in]descriptionA NULL-terminated string providing a description of the associate. Pass NULL if no description is desired.
[in]contentsA NULL-terminated string detailing the contents of the associate. Pass NULL if no contents are desired.
[in]sddsAn integer flag indicating the type of associate. Typically used to specify whether the associate is an SDDS file.
Returns
  • On success, returns the index of the newly defined associate within the dataset.
  • Returns a negative value on failure, with an error message set internally.
  • Returns 0 if RW_ASSOCIATES is not defined.
Precondition
  • The dataset must be initialized and configured for output.
  • RW_ASSOCIATES must be defined during compilation to use this feature.
  • The associate name and filename must be unique and valid.
Postcondition
  • The associate is defined within the dataset with the specified attributes.
  • The dataset's internal structures are updated to include the new associate.
Note
  • Associates provide a mechanism to link additional data or files to the primary SDDS dataset.
  • Properly defining associates can enhance data organization and accessibility.
Warning
  • Defining an associate with an invalid type, name, or filename will result in an error.
  • Attempting to define an associate with a name that already exists within the dataset will result in an error.
  • Ensure that the filename and path (if provided) are valid and accessible.

Definition at line 2173 of file SDDS_output.c.

2173 {
2174
2175#if RW_ASSOCIATES == 0
2176 return 0;
2177#else
2178 SDDS_LAYOUT *layout;
2179 ASSOCIATE_DEFINITION *definition;
2180 char s[SDDS_MAXLINE];
2181 if (!SDDS_IsValidName(name, "associate"))
2182 return -1;
2183 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_DefineAssociate"))
2184 return (-1);
2185 layout = &SDDS_dataset->layout;
2186 if (!(layout->associate_definition = SDDS_Realloc(layout->associate_definition, sizeof(*layout->associate_definition) * (layout->n_associates + 1)))) {
2187 SDDS_SetError("Memory allocation failure (SDDS_DefineAssociate)");
2188 return (-1);
2189 }
2190 if (!name) {
2191 SDDS_SetError("NULL name not allowed for associate file (SDDS_DefineAssociate)");
2192 return (-1);
2193 }
2194 if (!filename) {
2195 SDDS_SetError("NULL filename not allowed for associate file (SDDS_DefineAssociate)");
2196 return (-1);
2197 }
2198 if (SDDS_GetAssociateIndex(SDDS_dataset, name) >= 0) {
2199 sprintf(s, "Associate with name %s already exists (SDDS_DefineAssociate)", name);
2200 SDDS_SetError(s);
2201 return (-1);
2202 }
2203 if (!SDDS_ZeroMemory(definition = layout->associate_definition + layout->n_associates, sizeof(ASSOCIATE_DEFINITION))) {
2204 SDDS_SetError("Unable to define associate--can't zero memory for associate (SDDS_DefineAssociate)");
2205 return (-1);
2206 }
2207
2208 if (!SDDS_CopyString(&definition->name, name)) {
2209 SDDS_SetError("Memory allocation failure (SDDS_DefineAssociate)");
2210 return (-1);
2211 }
2212 if (!SDDS_CopyString(&definition->filename, filename)) {
2213 SDDS_SetError("Memory allocation failure (SDDS_DefineAssociate)");
2214 return (-1);
2215 }
2216 if (path && !SDDS_CopyString(&definition->path, path)) {
2217 SDDS_SetError("Memory allocation failure (SDDS_DefineAssociate)");
2218 return (-1);
2219 }
2220 if (contents && !SDDS_CopyString(&definition->contents, contents)) {
2221 SDDS_SetError("Memory allocation failure (SDDS_DefineAssociate)");
2222 return (-1);
2223 }
2224 if (description && !SDDS_CopyString(&definition->description, description)) {
2225 SDDS_SetError("Memory allocation failure (SDDS_DefineAssociate)");
2226 return (-1);
2227 }
2228 definition->sdds = sdds;
2229 layout->n_associates += 1;
2230 return (layout->n_associates - 1);
2231#endif
2232}

◆ SDDS_DefineColumn()

epicsShareFuncSDDS int32_t SDDS_DefineColumn ( SDDS_DATASET * SDDS_dataset,
const char * name,
const char * symbol,
const char * units,
const char * description,
const char * format_string,
int32_t type,
int32_t field_length )
extern

Defines a data column within the SDDS dataset.

This function processes the definition of a data column in the SDDS dataset. It allows the user to specify the column's name, symbol, units, description, format string, data type, and field length. The function ensures that the column name is valid and unique within the dataset before defining it.

Parameters
[in,out]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
[in]nameA NULL-terminated string specifying the name of the column. This name must be unique within the dataset.
[in]symbolA NULL-terminated string specifying the symbol for the column. Pass NULL if no symbol is desired.
[in]unitsA NULL-terminated string specifying the units of the column. Pass NULL if no units are desired.
[in]descriptionA NULL-terminated string providing a description of the column. Pass NULL if no description is desired.
[in]format_stringA NULL-terminated string specifying the printf-style format for ASCII output. If NULL is passed, a default format is selected based on the column type.
[in]typeAn integer representing the data type of the column. Must be one of the following:
  • SDDS_LONGDOUBLE
  • SDDS_DOUBLE
  • SDDS_FLOAT
  • SDDS_LONG
  • SDDS_ULONG
  • SDDS_SHORT
  • SDDS_USHORT
  • SDDS_CHARACTER
  • SDDS_STRING
[in]field_lengthAn integer specifying the length of the field allotted to the column for ASCII output. If set to 0, the field length is ignored. If negative, the field length is set to the absolute value, and leading and trailing white-space are eliminated for SDDS_STRING types upon reading.
Returns
  • On success, returns the index of the newly defined column within the dataset.
  • Returns -1 on failure, with an error message set internally.
Precondition
  • The dataset must be initialized and configured for output.
  • The column name must be unique and valid.
  • The specified data type must be supported by the dataset.
Postcondition
  • The column is defined within the dataset with the specified attributes.
  • The dataset's internal structures are updated to include the new column.
  • If rows have already been allocated, the data arrays are resized to accommodate the new column.
Note
  • For string-type columns, the fixed value is managed differently, and leading/trailing white-space is handled based on the field length parameter.
  • The function ensures that data arrays are appropriately resized if data has already been allocated.
Warning
  • Defining a column with an invalid type, field length, or name will result in an error.
  • Attempting to define a column with a name that already exists within the dataset will result in an error.
  • Memory allocation failures during the definition process will lead to an error.

Definition at line 1716 of file SDDS_output.c.

1716 {
1717 SDDS_LAYOUT *layout;
1718 COLUMN_DEFINITION *definition;
1719 char s[SDDS_MAXLINE];
1720 SORTED_INDEX *new_indexed_column;
1721 int32_t index;
1722 int32_t duplicate;
1723
1724 if (!SDDS_IsValidName(name, "column"))
1725 return -1;
1726 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_DefineColumn"))
1727 return (-1);
1728 if (!name) {
1729 SDDS_SetError("NULL name not allowed for column definition");
1730 return (-1);
1731 }
1732 layout = &SDDS_dataset->layout;
1733 if (!(layout->column_definition =
1734 SDDS_Realloc(layout->column_definition, sizeof(*layout->column_definition) * (layout->n_columns + 1))) ||
1735 !(layout->column_index = SDDS_Realloc(layout->column_index, sizeof(*layout->column_index) * (layout->n_columns + 1))) || !(new_indexed_column = (SORTED_INDEX *)SDDS_Malloc(sizeof(*new_indexed_column)))) {
1736 SDDS_SetError("Memory allocation failure (SDDS_DefineColumn)");
1737 return (-1);
1738 }
1739 if (!SDDS_CopyString(&new_indexed_column->name, name))
1740 return -1;
1741 index = binaryInsert((void **)layout->column_index, layout->n_columns, new_indexed_column, SDDS_CompareIndexedNames, &duplicate);
1742 if (duplicate) {
1743 sprintf(s, "Column %s already exists (SDDS_DefineColumn)", name);
1744 SDDS_SetError(s);
1745 return (-1);
1746 }
1747 layout->column_index[index]->index = layout->n_columns;
1748 if (!SDDS_ZeroMemory(definition = layout->column_definition + layout->n_columns, sizeof(COLUMN_DEFINITION))) {
1749 SDDS_SetError("Unable to define column--can't zero memory for column definition (SDDS_DefineColumn)");
1750 return (-1);
1751 }
1752 definition->name = new_indexed_column->name;
1753 if (symbol && !SDDS_CopyString(&definition->symbol, symbol)) {
1754 SDDS_SetError("Memory allocation failure (SDDS_DefineColumn)");
1755 return (-1);
1756 }
1757 if (units && !SDDS_CopyString(&definition->units, units)) {
1758 SDDS_SetError("Memory allocation failure (SDDS_DefineColumn)");
1759 return (-1);
1760 }
1761 if (description && !SDDS_CopyString(&definition->description, description)) {
1762 SDDS_SetError("Memory allocation failure (SDDS_DefineColumn)");
1763 return (-1);
1764 }
1765 if (type <= 0 || type > SDDS_NUM_TYPES) {
1766 SDDS_SetError("Unknown data type (SDDS_DefineColumn)");
1767 return (-1);
1768 }
1769 definition->type = type;
1770 if (format_string) {
1771 if (!SDDS_VerifyPrintfFormat(format_string, type)) {
1772 SDDS_SetError("Invalid format string (SDDS_DefineColumn)");
1773 return (-1);
1774 }
1775 if (!SDDS_CopyString(&definition->format_string, format_string)) {
1776 SDDS_SetError("Memory allocation failure (SDDS_DefineColumn)");
1777 return (-1);
1778 }
1779 }
1780 if ((definition->field_length = field_length) < 0 && type != SDDS_STRING) {
1781 SDDS_SetError("Invalid field length (SDDS_DefineColumn)");
1782 return (-1);
1783 }
1784
1785 if (SDDS_dataset->n_rows_allocated) {
1786 if (!SDDS_dataset->data) {
1787 SDDS_SetError("data array NULL but rows have been allocated! (SDDS_DefineColumn)");
1788 return (-1);
1789 }
1790 /* data already present--must resize data and parameter memory */
1791 if (!(SDDS_dataset->data = SDDS_Realloc(SDDS_dataset->data, sizeof(*SDDS_dataset->data) * (layout->n_columns + 1))) || !(SDDS_dataset->data[layout->n_columns] = calloc(SDDS_dataset->n_rows_allocated, SDDS_type_size[type - 1]))) {
1792 SDDS_SetError("Memory allocation failure (SDDS_DefineColumn)");
1793 return (-1);
1794 }
1795 }
1796
1797 /* not part of output: */
1798 definition->definition_mode = SDDS_NORMAL_DEFINITION;
1799 if (type == SDDS_STRING)
1800 definition->memory_number = SDDS_CreateRpnMemory(name, 1);
1801 else {
1802 definition->memory_number = SDDS_CreateRpnMemory(name, 0);
1803 }
1804 sprintf(s, "&%s", name);
1805 definition->pointer_number = SDDS_CreateRpnArray(s);
1806
1807 layout->n_columns += 1;
1808 return (layout->n_columns - 1);
1809}
int64_t SDDS_CreateRpnMemory(const char *name, short is_string)
Stub function for creating RPN memory when RPN_SUPPORT is not enabled.
Definition SDDS_rpn.c:825
int64_t SDDS_CreateRpnArray(char *name)
Stub function for creating RPN arrays when RPN_SUPPORT is not enabled.
Definition SDDS_rpn.c:835

◆ SDDS_DefineColumnLikeArray()

epicsShareFuncSDDS int32_t SDDS_DefineColumnLikeArray ( SDDS_DATASET * target,
SDDS_DATASET * source,
char * name,
char * newName )
extern

Defines a column in the target dataset based on an array definition from the source dataset.

This function creates a column in the target SDDS dataset with properties matching those of a specified array in the source dataset.

Parameters
targetPointer to the SDDS_DATASET structure representing the target dataset.
sourcePointer to the SDDS_DATASET structure representing the source dataset.
nameThe name of the array in the source dataset whose definition is to be used.
newNameThe name of the column in the target dataset. If NULL, the original name is used.
Returns
1 on success; 0 on failure. On failure, an error message is recorded.

Definition at line 302 of file SDDS_transfer.c.

302 {
303 ARRAY_DEFINITION *arrayDef;
304
305 if (!name || SDDS_StringIsBlank(name)) {
306 SDDS_SetError("Unable to define column--NULL or blank name passed (SDDS_DefineColumnLikeArray)");
307 return 0;
308 }
309 if (!newName)
310 newName = name;
311 if (!(arrayDef = SDDS_GetArrayDefinition(source, name))) {
312 SDDS_SetError("Unable to define column--unknown array named (SDDS_DefineColumnLikeArray)");
313 return 0;
314 }
315 if (SDDS_GetColumnIndex(target, newName) >= 0) {
316 SDDS_SetError("Unable to define column--already exists (SDDS_DefineColumnLikeArray)");
317 return 0;
318 }
319 if (SDDS_DefineColumn(target, newName, arrayDef->symbol, arrayDef->units, arrayDef->description, arrayDef->format_string, arrayDef->type, 0) < 0) {
320 SDDS_FreeArrayDefinition(arrayDef);
321 SDDS_SetError("Unable to define column--call to define column failed (SDDS_DefineColumnLikeArray)");
322 return 0;
323 }
324 SDDS_FreeArrayDefinition(arrayDef);
325 return 1;
326}
ARRAY_DEFINITION * SDDS_GetArrayDefinition(SDDS_DATASET *SDDS_dataset, char *name)
Retrieves the definition of a specified array from the SDDS dataset.
int32_t SDDS_FreeArrayDefinition(ARRAY_DEFINITION *source)
Frees memory allocated for an array definition.

◆ SDDS_DefineColumnLikeParameter()

epicsShareFuncSDDS int32_t SDDS_DefineColumnLikeParameter ( SDDS_DATASET * target,
SDDS_DATASET * source,
char * name,
char * newName )
extern

Defines a column in the target dataset based on a parameter definition from the source dataset.

This function creates a column in the target SDDS dataset with properties matching those of a specified parameter in the source dataset.

Parameters
targetPointer to the SDDS_DATASET structure representing the target dataset.
sourcePointer to the SDDS_DATASET structure representing the source dataset.
nameThe name of the parameter in the source dataset whose definition is to be used.
newNameThe name of the column in the target dataset. If NULL, the original name is used.
Returns
1 on success; 0 on failure. On failure, an error message is recorded.

Definition at line 264 of file SDDS_transfer.c.

264 {
265 PARAMETER_DEFINITION *pardef;
266
267 if (!name || SDDS_StringIsBlank(name)) {
268 SDDS_SetError("Unable to define column--NULL or blank name passed (SDDS_DefineColumnLikeParameter)");
269 return 0;
270 }
271 if (!newName)
272 newName = name;
273 if (!(pardef = SDDS_GetParameterDefinition(source, name))) {
274 SDDS_SetError("Unable to define column--unknown parameter named (SDDS_DefineColumnLikeParameter)");
275 return 0;
276 }
277 if (SDDS_GetColumnIndex(target, newName) >= 0) {
278 SDDS_SetError("Unable to define column--already exists (SDDS_DefineColumnLikeParameter)");
279 return 0;
280 }
281 if (SDDS_DefineColumn(target, newName, pardef->symbol, pardef->units, pardef->description, pardef->format_string, pardef->type, 0) < 0) {
283 SDDS_SetError("Unable to define column--call to define column failed (SDDS_DefineColumnLikeParameter)");
284 return 0;
285 }
287 return 1;
288}
PARAMETER_DEFINITION * SDDS_GetParameterDefinition(SDDS_DATASET *SDDS_dataset, char *name)
Retrieves the definition of a specified parameter from the SDDS dataset.
int32_t SDDS_FreeParameterDefinition(PARAMETER_DEFINITION *source)
Frees memory allocated for a parameter definition.

◆ SDDS_DefineParameter()

epicsShareFuncSDDS int32_t SDDS_DefineParameter ( SDDS_DATASET * SDDS_dataset,
const char * name,
const char * symbol,
const char * units,
const char * description,
const char * format_string,
int32_t type,
char * fixed_value )
extern

Defines a data parameter with a fixed string value.

This function processes the definition of a data parameter within the SDDS dataset. It allows the specification of a fixed string value for the parameter, which remains constant across all data entries. The function validates the parameter name, type, and format string before defining the parameter in the dataset.

Parameters
[in,out]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
[in]nameA NULL-terminated string specifying the name of the parameter. This name must be unique within the dataset.
[in]symbolA NULL-terminated string specifying the symbol for the parameter. Pass NULL if no symbol is desired.
[in]unitsA NULL-terminated string specifying the units of the parameter. Pass NULL if no units are desired.
[in]descriptionA NULL-terminated string providing a description of the parameter. Pass NULL if no description is desired.
[in]format_stringA NULL-terminated string specifying the printf-style format for ASCII output. If NULL is passed, a default format is selected based on the parameter type.
[in]typeAn integer representing the data type of the parameter. Must be one of the following:
  • SDDS_LONGDOUBLE
  • SDDS_DOUBLE
  • SDDS_FLOAT
  • SDDS_LONG
  • SDDS_ULONG
  • SDDS_SHORT
  • SDDS_USHORT
  • SDDS_CHARACTER
  • SDDS_STRING
[in]fixed_valueA NULL-terminated string specifying the fixed value of the parameter. For non-string types, this string should be formatted appropriately using functions like sprintf.
Returns
  • On success, returns the index of the newly defined parameter within the dataset.
  • Returns -1 on failure, with an error message set internally.
Precondition
  • The dataset must be initialized and configured for output.
  • The parameter name must be unique and valid.
  • The fixed value must be a valid string representation for the specified parameter type.
Postcondition
  • The parameter is defined within the dataset with the specified attributes and fixed value.
  • The dataset's internal structures are updated to include the new parameter.
Note
  • For numerical parameter types, the fixed value string should represent the numerical value correctly.
  • The function internally handles the conversion of the fixed value string to the appropriate type based on the parameter's data type.
Warning
  • Defining a parameter with an invalid type or format string will result in an error.
  • Passing an improperly formatted fixed value string for the specified type may lead to unexpected behavior.

Definition at line 1473 of file SDDS_output.c.

1473 {
1474 SDDS_LAYOUT *layout;
1475 PARAMETER_DEFINITION *definition;
1476 char s[SDDS_MAXLINE];
1477 SORTED_INDEX *new_indexed_parameter;
1478 int32_t index, duplicate;
1479
1480 if (!SDDS_IsValidName(name, "parameter"))
1481 return -1;
1482 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_DefineParameter"))
1483 return (-1);
1484 if (!name) {
1485 SDDS_SetError("NULL name not allowed for parameter definition");
1486 return (-1);
1487 }
1488 layout = &SDDS_dataset->layout;
1489 if (!(layout->parameter_definition =
1490 SDDS_Realloc(layout->parameter_definition, sizeof(*layout->parameter_definition) * (layout->n_parameters + 1))) ||
1491 !(layout->parameter_index = SDDS_Realloc(layout->parameter_index, sizeof(*layout->parameter_index) * (layout->n_parameters + 1))) || !(new_indexed_parameter = (SORTED_INDEX *)SDDS_Malloc(sizeof(*new_indexed_parameter)))) {
1492 SDDS_SetError("Memory allocation failure (SDDS_DefineParameter)");
1493 return (-1);
1494 }
1495 if (!SDDS_CopyString(&new_indexed_parameter->name, name))
1496 return -1;
1497 index = binaryInsert((void **)layout->parameter_index, layout->n_parameters, new_indexed_parameter, SDDS_CompareIndexedNames, &duplicate);
1498 if (duplicate) {
1499 sprintf(s, "Parameter %s already exists (SDDS_DefineParameter)", name);
1500 SDDS_SetError(s);
1501 return (-1);
1502 }
1503 layout->parameter_index[index]->index = layout->n_parameters;
1504
1505 if (!SDDS_ZeroMemory(definition = layout->parameter_definition + layout->n_parameters, sizeof(PARAMETER_DEFINITION))) {
1506 SDDS_SetError("Unable to define parameter--can't zero memory for parameter definition (SDDS_DefineParameter)");
1507 return (-1);
1508 }
1509 definition->name = new_indexed_parameter->name;
1510 if (symbol && !SDDS_CopyString(&definition->symbol, symbol)) {
1511 SDDS_SetError("Memory allocation failure (SDDS_DefineParameter)");
1512 return (-1);
1513 }
1514 if (units && !SDDS_CopyString(&definition->units, units)) {
1515 SDDS_SetError("Memory allocation failure (SDDS_DefineParameter)");
1516 return (-1);
1517 }
1518 if (description && !SDDS_CopyString(&definition->description, description)) {
1519 SDDS_SetError("Memory allocation failure (SDDS_DefineParameter)");
1520 return (-1);
1521 }
1522 if (type <= 0 || type > SDDS_NUM_TYPES) {
1523 SDDS_SetError("Unknown data type (SDDS_DefineParameter)");
1524 return (-1);
1525 }
1526 definition->type = type;
1527 if (format_string) {
1528 if (!SDDS_VerifyPrintfFormat(format_string, type)) {
1529 SDDS_SetError("Invalid format string (SDDS_DefineParameter)");
1530 return (-1);
1531 }
1532 if (!SDDS_CopyString(&definition->format_string, format_string)) {
1533 SDDS_SetError("Memory allocation failure (SDDS_DefineParameter)");
1534 return (-1);
1535 }
1536 }
1537 if (fixed_value && !SDDS_CopyString(&(definition->fixed_value), fixed_value)) {
1538 SDDS_SetError("Couldn't copy fixed_value string (SDDS_DefineParameter)");
1539 return (-1);
1540 }
1541 definition->definition_mode = SDDS_NORMAL_DEFINITION;
1542 if (type == SDDS_STRING)
1543 definition->memory_number = SDDS_CreateRpnMemory(name, 1);
1544 else
1545 definition->memory_number = SDDS_CreateRpnMemory(name, 0);
1546 layout->n_parameters += 1;
1547 return (layout->n_parameters - 1);
1548}

◆ SDDS_DefineParameter1()

epicsShareFuncSDDS int32_t SDDS_DefineParameter1 ( SDDS_DATASET * SDDS_dataset,
const char * name,
const char * symbol,
const char * units,
const char * description,
const char * format_string,
int32_t type,
void * fixed_value )
extern

Defines a data parameter with a fixed numerical value.

This function processes the definition of a data parameter within the SDDS dataset. It allows the specification of a fixed numerical value for the parameter, which remains constant across all data entries. The function validates the parameter name, type, and format string before defining the parameter in the dataset.

Parameters
[in,out]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
[in]nameA NULL-terminated string specifying the name of the parameter. This name must be unique within the dataset.
[in]symbolA NULL-terminated string specifying the symbol for the parameter. Pass NULL if no symbol is desired.
[in]unitsA NULL-terminated string specifying the units of the parameter. Pass NULL if no units are desired.
[in]descriptionA NULL-terminated string providing a description of the parameter. Pass NULL if no description is desired.
[in]format_stringA NULL-terminated string specifying the printf-style format for ASCII output. If NULL is passed, a default format is selected based on the parameter type.
[in]typeAn integer representing the data type of the parameter. Must be one of the following:
  • SDDS_LONGDOUBLE
  • SDDS_DOUBLE
  • SDDS_FLOAT
  • SDDS_LONG
  • SDDS_ULONG
  • SDDS_SHORT
  • SDDS_USHORT
  • SDDS_CHARACTER
  • SDDS_STRING
[in]fixed_valueA pointer to the numerical value that remains constant for this parameter across all data entries. This value is used to initialize the parameter's fixed value.
Returns
  • On success, returns the index of the newly defined parameter within the dataset.
  • Returns -1 on failure, with an error message set internally.
Precondition
  • The dataset must be initialized and configured for output.
  • The parameter name must be unique and valid.
  • The fixed value must be non-NULL for numerical types and should be prepared appropriately.
Postcondition
  • The parameter is defined within the dataset with the specified attributes and fixed value.
  • The dataset's internal structures are updated to include the new parameter.
Note
  • For string-type parameters, the fixed value should be a NULL-terminated string.
  • The function internally converts the fixed numerical value to a string representation if the parameter type is not SDDS_STRING.
Warning
  • Defining a parameter with an invalid type or format string will result in an error.
  • Passing a NULL fixed value for non-string types will result in an error.

Definition at line 1408 of file SDDS_output.c.

1408 {
1409 char buffer[SDDS_MAXLINE];
1410 if (!SDDS_IsValidName(name, "parameter"))
1411 return -1;
1412 if (!fixed_value || type == SDDS_STRING)
1413 return SDDS_DefineParameter(SDDS_dataset, name, symbol, units, description, format_string, type, fixed_value);
1414 if (type <= 0 || type > SDDS_NUM_TYPES) {
1415 SDDS_SetError("Unknown data type (SDDS_DefineParameter1)");
1416 return (-1);
1417 }
1418 buffer[SDDS_MAXLINE - 1] = 0;
1419 if (!SDDS_SprintTypedValue(fixed_value, 0, type, format_string, buffer, 0) || buffer[SDDS_MAXLINE - 1] != 0) {
1420 SDDS_SetError("Unable to define fixed value for parameter (SDDS_DefineParameter1)");
1421 return (-1);
1422 }
1423 return SDDS_DefineParameter(SDDS_dataset, name, symbol, units, description, format_string, type, buffer);
1424}
int32_t SDDS_SprintTypedValue(void *data, int64_t index, int32_t type, const char *format, char *buffer, uint32_t mode)
Formats a data value of a specified type into a string buffer using an optional printf format string.
Definition SDDS_utils.c:161

◆ SDDS_DefineParameterLikeArray()

epicsShareFuncSDDS int32_t SDDS_DefineParameterLikeArray ( SDDS_DATASET * target,
SDDS_DATASET * source,
char * name,
char * newName )
extern

Defines a parameter in the target dataset based on an array definition from the source dataset.

This function creates a parameter in the target SDDS dataset with properties matching those of a specified array in the source dataset.

Parameters
targetPointer to the SDDS_DATASET structure representing the target dataset.
sourcePointer to the SDDS_DATASET structure representing the source dataset.
nameThe name of the array in the source dataset whose definition is to be used.
newNameThe name of the parameter in the target dataset. If NULL, the original name is used.
Returns
1 on success; 0 on failure. On failure, an error message is recorded.

Definition at line 226 of file SDDS_transfer.c.

226 {
227 ARRAY_DEFINITION *arrayDef;
228
229 if (!name || SDDS_StringIsBlank(name)) {
230 SDDS_SetError("Unable to define parameter--NULL or blank name passed (SDDS_DefineParameterLikeArray)");
231 return 0;
232 }
233 if (!newName)
234 newName = name;
235 if (!(arrayDef = SDDS_GetArrayDefinition(source, name))) {
236 SDDS_SetError("Unable to define parameter--unknown array named (SDDS_DefineParameterLikeArray)");
237 return 0;
238 }
239 if (SDDS_GetParameterIndex(target, newName) >= 0) {
240 SDDS_SetError("Unable to define parameter--already exists (SDDS_DefineParameterLikeArray)");
241 return 0;
242 }
243 if (SDDS_DefineParameter(target, newName, arrayDef->symbol, arrayDef->units, arrayDef->description, arrayDef->format_string, arrayDef->type, NULL) < 0) {
244 SDDS_FreeArrayDefinition(arrayDef);
245 SDDS_SetError("Unable to define parameter--call to define parameter failed (SDDS_DefineParameterLikeArray)");
246 return 0;
247 }
248 SDDS_FreeArrayDefinition(arrayDef);
249 return 1;
250}

◆ SDDS_DefineParameterLikeColumn()

epicsShareFuncSDDS int32_t SDDS_DefineParameterLikeColumn ( SDDS_DATASET * target,
SDDS_DATASET * source,
char * name,
char * newName )
extern

Defines a parameter in the target dataset based on a column definition from the source dataset.

This function creates a parameter in the target SDDS dataset with properties matching those of a specified column in the source dataset.

Parameters
targetPointer to the SDDS_DATASET structure representing the target dataset.
sourcePointer to the SDDS_DATASET structure representing the source dataset.
nameThe name of the column in the source dataset whose definition is to be used.
newNameThe name of the parameter in the target dataset. If NULL, the original name is used.
Returns
1 on success; 0 on failure. On failure, an error message is recorded.

Definition at line 188 of file SDDS_transfer.c.

188 {
189 COLUMN_DEFINITION *coldef;
190
191 if (!name || SDDS_StringIsBlank(name)) {
192 SDDS_SetError("Unable to define parameter--NULL or blank name passed (SDDS_DefineParameterLikeColumn)");
193 return 0;
194 }
195 if (!newName)
196 newName = name;
197 if (!(coldef = SDDS_GetColumnDefinition(source, name))) {
198 SDDS_SetError("Unable to define parameter--unknown column named (SDDS_DefineParameterLikeColumn)");
199 return 0;
200 }
201 if (SDDS_GetParameterIndex(target, newName) >= 0) {
202 SDDS_SetError("Unable to define parameter--already exists (SDDS_DefineParameterLikeColumn)");
203 return 0;
204 }
205 if (SDDS_DefineParameter(target, newName, coldef->symbol, coldef->units, coldef->description, coldef->format_string, coldef->type, NULL) < 0) {
207 SDDS_SetError("Unable to define parameter--call to define parameter failed (SDDS_DefineParameterLikeColumn)");
208 return 0;
209 }
211 return 1;
212}
int32_t SDDS_FreeColumnDefinition(COLUMN_DEFINITION *source)
Frees memory allocated for a column definition.
COLUMN_DEFINITION * SDDS_GetColumnDefinition(SDDS_DATASET *SDDS_dataset, char *name)
Retrieves the definition of a specified column from the SDDS dataset.

◆ SDDS_DefineSimpleColumn()

epicsShareFuncSDDS int32_t SDDS_DefineSimpleColumn ( SDDS_DATASET * SDDS_dataset,
const char * name,
const char * unit,
int32_t type )
extern

Defines a simple data column within the SDDS dataset.

This function provides a simplified interface for defining a data column in the SDDS dataset. It allows the user to specify only the column's name, units, and data type, while omitting optional parameters such as symbol, description, format string, and field length. Internally, it calls SDDS_DefineColumn with default values for the omitted parameters.

Parameters
[in,out]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
[in]nameA NULL-terminated string specifying the name of the column. This name must be unique within the dataset.
[in]unitA NULL-terminated string specifying the units of the column. Pass NULL if no units are desired.
[in]typeAn integer representing the data type of the column. Must be one of the following:
  • SDDS_LONGDOUBLE
  • SDDS_DOUBLE
  • SDDS_FLOAT
  • SDDS_LONG
  • SDDS_ULONG
  • SDDS_SHORT
  • SDDS_USHORT
  • SDDS_CHARACTER
  • SDDS_STRING
Returns
  • 1 on successful definition of the column.
  • 0 on failure, with an error message set internally.
Precondition
  • The dataset must be initialized and configured for output.
  • The column name must be unique and valid.
Postcondition
  • The column is defined within the dataset with the specified name, units, and type.
  • The dataset's internal structures are updated to include the new column.
Note
  • This function is intended for scenarios where only basic column attributes are needed.
  • Optional parameters such as symbol, description, format string, and field length are set to default values.
Warning
  • Defining a column with an invalid type or name will result in an error.
  • Attempting to define a column with a name that already exists within the dataset will result in an error.

Definition at line 1853 of file SDDS_output.c.

1853 {
1854 if (SDDS_DefineColumn(SDDS_dataset, name, NULL, unit, NULL, NULL, type, 0) < 0)
1855 return 0;
1856 return (1);
1857}

◆ SDDS_DefineSimpleColumns()

epicsShareFuncSDDS int32_t SDDS_DefineSimpleColumns ( SDDS_DATASET * SDDS_dataset,
int32_t number,
char ** name,
char ** unit,
int32_t type )
extern

Defines multiple simple data columns of the same data type within the SDDS dataset.

This function provides a streamlined way to define multiple data columns in the SDDS dataset that share the same data type. It allows the user to specify the names and units of the columns, while omitting optional attributes such as symbol, description, format string, and field length. Internally, it calls SDDS_DefineColumn for each column with default values for the omitted parameters.

Parameters
[in,out]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
[in]numberThe number of columns to define. Must be greater than or equal to 0.
[in]nameAn array of NULL-terminated strings specifying the names of the columns. Each name must be unique within the dataset.
[in]unitAn array of NULL-terminated strings specifying the units of the columns. Pass NULL for elements where no units are desired.
[in]typeAn integer representing the data type for all the columns. Must be one of the following:
  • SDDS_LONGDOUBLE
  • SDDS_DOUBLE
  • SDDS_FLOAT
  • SDDS_LONG
  • SDDS_ULONG
  • SDDS_SHORT
  • SDDS_USHORT
  • SDDS_CHARACTER
  • SDDS_STRING
Returns
  • 1 on successful definition of all specified columns.
  • 0 on failure to define any of the columns, with an error message set internally.
Precondition
  • The dataset must be initialized and configured for output.
  • The name array must contain unique and valid names for each column.
  • The type must be a supported data type.
Postcondition
  • All specified columns are defined within the dataset with the provided names and units.
  • The dataset's internal structures are updated to include the new columns.
Note
  • Passing number as 0 results in no action and returns success.
  • This function is optimized for defining multiple columns of the same type, enhancing code readability and efficiency.
Warning
  • Defining a column with an invalid type or name will result in an error.
  • Attempting to define a column with a name that already exists within the dataset will result in an error.
  • Ensure that the name and unit arrays are properly allocated and contain valid strings.

Definition at line 1952 of file SDDS_output.c.

1952 {
1953 int32_t i;
1954 if (!number)
1955 return (1);
1956 if (!name)
1957 return 0;
1958 for (i = 0; i < number; i++)
1959 if (SDDS_DefineColumn(SDDS_dataset, name[i], NULL, unit ? unit[i] : NULL, NULL, NULL, type, 0) < 0)
1960 return 0;
1961 return (1);
1962}

◆ SDDS_DefineSimpleParameter()

epicsShareFuncSDDS int32_t SDDS_DefineSimpleParameter ( SDDS_DATASET * SDDS_dataset,
const char * name,
const char * unit,
int32_t type )
extern

Defines a simple data parameter within the SDDS dataset.

This function provides a simplified interface for defining a data parameter in the SDDS dataset. It allows the user to specify only the parameter's name, units, and data type, while omitting optional attributes such as symbol, description, format string, and fixed value. Internally, it calls SDDS_DefineParameter with default values for the omitted parameters.

Parameters
[in,out]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
[in]nameA NULL-terminated string specifying the name of the parameter. This name must be unique within the dataset.
[in]unitA NULL-terminated string specifying the units of the parameter. Pass NULL if no units are desired.
[in]typeAn integer representing the data type of the parameter. Must be one of the following:
  • SDDS_LONGDOUBLE
  • SDDS_DOUBLE
  • SDDS_FLOAT
  • SDDS_LONG
  • SDDS_ULONG
  • SDDS_SHORT
  • SDDS_USHORT
  • SDDS_CHARACTER
  • SDDS_STRING
Returns
  • 1 on successful definition of the parameter.
  • 0 on failure, with an error message set internally.
Precondition
  • The dataset must be initialized and configured for output.
  • The parameter name must be unique and valid.
Postcondition
  • The parameter is defined within the dataset with the specified name, units, and type.
  • The dataset's internal structures are updated to include the new parameter.
Note
  • This function is intended for scenarios where only basic parameter attributes are needed.
  • Optional parameters such as symbol, description, format string, and fixed value are set to default values.
Warning
  • Defining a parameter with an invalid type or name will result in an error.
  • Attempting to define a parameter with a name that already exists within the dataset will result in an error.

Definition at line 1901 of file SDDS_output.c.

1901 {
1902 if (SDDS_DefineParameter(SDDS_dataset, name, NULL, unit, NULL, NULL, type, NULL) < 0)
1903 return 0;
1904 return (1);
1905}

◆ SDDS_DefineSimpleParameters()

epicsShareFuncSDDS int32_t SDDS_DefineSimpleParameters ( SDDS_DATASET * SDDS_dataset,
int32_t number,
char ** name,
char ** unit,
int32_t type )
extern

Defines multiple simple data parameters of the same data type within the SDDS dataset.

This function provides a streamlined way to define multiple data parameters in the SDDS dataset that share the same data type. It allows the user to specify the names and units of the parameters, while omitting optional attributes such as symbol, description, format string, and fixed value. Internally, it calls SDDS_DefineParameter for each parameter with default values for the omitted parameters.

Parameters
[in,out]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
[in]numberThe number of parameters to define. Must be greater than or equal to 0.
[in]nameAn array of NULL-terminated strings specifying the names of the parameters. Each name must be unique within the dataset.
[in]unitAn array of NULL-terminated strings specifying the units of the parameters. Pass NULL for elements where no units are desired.
[in]typeAn integer representing the data type for all the parameters. Must be one of the following:
  • SDDS_LONGDOUBLE
  • SDDS_DOUBLE
  • SDDS_FLOAT
  • SDDS_LONG
  • SDDS_ULONG
  • SDDS_SHORT
  • SDDS_USHORT
  • SDDS_CHARACTER
  • SDDS_STRING
Returns
  • 1 on successful definition of all specified parameters.
  • 0 on failure to define any of the parameters, with an error message set internally.
Precondition
  • The dataset must be initialized and configured for output.
  • The name array must contain unique and valid names for each parameter.
  • The type must be a supported data type.
Postcondition
  • All specified parameters are defined within the dataset with the provided names and units.
  • The dataset's internal structures are updated to include the new parameters.
Note
  • Passing number as 0 results in no action and returns success.
  • This function is optimized for defining multiple parameters of the same type, enhancing code readability and efficiency.
Warning
  • Defining a parameter with an invalid type or name will result in an error.
  • Attempting to define a parameter with a name that already exists within the dataset will result in an error.
  • Ensure that the name and unit arrays are properly allocated and contain valid strings.

Definition at line 2009 of file SDDS_output.c.

2009 {
2010 int32_t i;
2011 if (!number)
2012 return (1);
2013 if (!name)
2014 return 0;
2015 for (i = 0; i < number; i++)
2016 if (SDDS_DefineParameter(SDDS_dataset, name[i], NULL, unit ? unit[i] : NULL, NULL, NULL, type, NULL) < 0)
2017 return 0;
2018 return (1);
2019}

◆ SDDS_DeleteColumn()

epicsShareFuncSDDS int32_t SDDS_DeleteColumn ( SDDS_DATASET * SDDS_dataset,
char * column_name )
extern

Deletes a specified column from an SDDS dataset.

Note: This function is currently non-functional and will abort execution if called.

This function is intended to remove a column identified by column_name from the provided SDDS dataset. It handles the reordering of remaining columns and updates the dataset's layout accordingly. However, as indicated by the current implementation, the function is not operational and will terminate the program when invoked.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
column_nameA null-terminated string specifying the name of the column to be deleted.
Returns
This function does not return as it aborts execution. If it were functional, it would return 1 on success and 0 on failure.
Warning
  • Currently Non-Functional: The function will terminate the program with an error message when called.
Todo
  • Implement the functionality to delete a column without aborting.
See also
SDDS_DeleteUnsetColumns, SDDS_CopyColumn

Definition at line 3846 of file SDDS_extract.c.

3846 {
3847 int32_t index;
3848 int64_t i, j;
3849
3850 SDDS_Bomb("SDDS_DeleteColumn is presently not functional.");
3851
3852 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_DeleteColumn"))
3853 return (0);
3854 if ((index = SDDS_GetColumnIndex(SDDS_dataset, column_name)) < 0) {
3855 SDDS_SetError("Unable to delete column--unrecognized column name (SDDS_DeleteColumn)");
3856 return (0);
3857 }
3858 for (i = index + 1; i < SDDS_dataset->layout.n_columns; i++) {
3859 if (!SDDS_CopyColumn(SDDS_dataset, i - 1, i)) {
3860 SDDS_SetError("Unable to delete column--error copying column (SDDS_DeleteColumn)");
3861 return (0);
3862 }
3863 for (j = 0; j < SDDS_dataset->n_of_interest; j++)
3864 if (SDDS_dataset->column_order[j] == index) {
3865 memcpy((char *)(SDDS_dataset->column_order + j), (char *)(SDDS_dataset->column_order + j + 1), sizeof(*SDDS_dataset->column_order) * (SDDS_dataset->n_of_interest - j - 1));
3866 SDDS_dataset->n_of_interest--;
3867 } else if (SDDS_dataset->column_order[j] > index)
3868 SDDS_dataset->column_order[j] -= 1;
3869 }
3870 if ((SDDS_dataset->layout.n_columns -= 1) == 0)
3871 SDDS_dataset->n_rows = 0;
3872 return (1);
3873}
int32_t SDDS_CopyColumn(SDDS_DATASET *SDDS_dataset, int32_t target, int32_t source)
Copies data from a source column to a target column within an SDDS dataset.

◆ SDDS_DeleteParameter()

epicsShareFuncSDDS int32_t SDDS_DeleteParameter ( SDDS_DATASET * SDDS_dataset,
char * parameter_name )
extern

Deletes a specified parameter from an SDDS dataset.

This function removes a parameter identified by parameter_name from the provided SDDS dataset. It shifts all subsequent parameters up to fill the gap left by the deleted parameter and updates the dataset's parameter count accordingly.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
parameter_nameA null-terminated string specifying the name of the parameter to be deleted.
Returns
On success, returns 1. On failure, returns 0 and sets an appropriate error message.
Return values
1Indicates that the parameter was successfully deleted.
0Indicates that an error occurred (e.g., invalid dataset, unrecognized parameter name, error copying parameters).
Note
  • This operation modifies the dataset by removing the specified parameter.
  • It is recommended to ensure that the parameter to be deleted is not essential for further operations.
See also
SDDS_CopyParameter, SDDS_DeleteUnsetParameters

Definition at line 3979 of file SDDS_extract.c.

3979 {
3980 int32_t i, index;
3981 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_DeleteParameter"))
3982 return (0);
3983 if ((index = SDDS_GetParameterIndex(SDDS_dataset, parameter_name)) < 0) {
3984 SDDS_SetError("Unable to delete parameter--unrecognized parameter name (SDDS_DeleteParameter)");
3985 return (0);
3986 }
3987 for (i = index + 1; i < SDDS_dataset->layout.n_parameters; i++) {
3988 if (!SDDS_CopyParameter(SDDS_dataset, i - 1, i)) {
3989 SDDS_SetError("Unable to delete parameter--error copying parameter (SDDS_DeleteParameter)");
3990 return (0);
3991 }
3992 }
3993 SDDS_dataset->layout.n_parameters -= 1;
3994 return (1);
3995}
int32_t SDDS_CopyParameter(SDDS_DATASET *SDDS_dataset, int32_t target, int32_t source)
Copies a parameter from a source index to a target index within an SDDS dataset.

◆ SDDS_DeleteParameterFixedValues()

epicsShareFuncSDDS int32_t SDDS_DeleteParameterFixedValues ( SDDS_DATASET * SDDS_dataset)
extern

Deletes fixed values from all parameters in the SDDS dataset.

This function iterates through all parameters in the provided SDDS dataset and removes any fixed values associated with them. It ensures that both the current layout and the original layout of the dataset have their fixed values cleared.

Parameters
[in]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset from which fixed values will be deleted.
Returns
  • 1 on successful deletion of all fixed values.
  • 0 if the dataset check fails or if saving the layout fails.
Note
  • The function requires that the SDDS dataset is properly initialized and that it contains parameters with fixed values.
  • Both the current layout and the original layout are updated to remove fixed values.
Warning
  • This operation cannot be undone. Ensure that fixed values are no longer needed before calling this function.
  • Improper handling of memory allocations related to fixed values may lead to memory leaks or undefined behavior.
See also
SDDS_CheckDataset, SDDS_SaveLayout

Definition at line 4974 of file SDDS_utils.c.

4974 {
4975 int32_t i;
4976 SDDS_LAYOUT *layout, *orig_layout;
4977
4978 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_DeleteFixedValueParameters"))
4979 return 0;
4980 if (!SDDS_SaveLayout(SDDS_dataset))
4981 return 0;
4982 layout = &SDDS_dataset->layout;
4983 orig_layout = &SDDS_dataset->original_layout;
4984 for (i = 0; i < layout->n_parameters; i++) {
4985 if (layout->parameter_definition[i].fixed_value)
4986 free(layout->parameter_definition[i].fixed_value);
4987 if (orig_layout->parameter_definition[i].fixed_value && (!layout->parameter_definition[i].fixed_value || orig_layout->parameter_definition[i].fixed_value != layout->parameter_definition[i].fixed_value))
4988 free(orig_layout->parameter_definition[i].fixed_value);
4989 orig_layout->parameter_definition[i].fixed_value = NULL;
4990 layout->parameter_definition[i].fixed_value = NULL;
4991 }
4992 return 1;
4993}

◆ SDDS_DeleteUnsetColumns()

epicsShareFuncSDDS int32_t SDDS_DeleteUnsetColumns ( SDDS_DATASET * SDDS_dataset)
extern

Deletes all columns from an SDDS dataset that are not marked as "of interest".

This function iterates through all columns in the provided SDDS dataset and removes those that have not been flagged as "of interest". It ensures that only desired columns are retained, updating the dataset's layout and column order accordingly.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
Returns
On success, returns 1. On failure, returns 0 and sets an appropriate error message.
Return values
1Indicates that columns were successfully deleted.
0Indicates that an error occurred (e.g., invalid dataset, failure to delete a column).
Note
  • This operation modifies the dataset in place by removing unset columns.
  • It is recommended to perform column selection before calling this function to ensure that only desired columns are retained.
See also
SDDS_SetColumnsOfInterest, SDDS_DeleteColumn, SDDS_CopyColumn

Definition at line 3894 of file SDDS_extract.c.

3894 {
3895 int64_t i;
3896 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_DeleteUnsetColumns"))
3897 return (0);
3898 for (i = 0; i < SDDS_dataset->layout.n_columns; i++)
3899 if (!SDDS_dataset->column_flag[i]) {
3900 if (!SDDS_DeleteColumn(SDDS_dataset, SDDS_dataset->layout.column_definition[i].name))
3901 return (0);
3902 else
3903 i--;
3904 }
3905 return (1);
3906}
int32_t SDDS_DeleteColumn(SDDS_DATASET *SDDS_dataset, char *column_name)
Deletes a specified column from an SDDS dataset.

◆ SDDS_DeleteUnsetRows()

epicsShareFuncSDDS int32_t SDDS_DeleteUnsetRows ( SDDS_DATASET * SDDS_dataset)
extern

Deletes rows from an SDDS dataset that are not marked as "of interest".

This function removes all rows in the provided SDDS dataset that have not been flagged as "of interest" using prior selection functions. It effectively compacts the dataset by retaining only the desired rows and updating the row count accordingly.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
Returns
On success, returns 1. On failure, returns 0 and sets an appropriate error message.
Return values
1Indicates that rows were successfully deleted.
0Indicates that an error occurred (e.g., invalid dataset, problem copying rows).
Note
  • This operation modifies the dataset in place by removing unset rows.
  • It is recommended to perform row selection before calling this function to ensure that only desired rows are retained.
See also
SDDS_SetRowsOfInterest, SDDS_MatchRowsOfInterest, SDDS_FilterRowsOfInterest

Definition at line 3761 of file SDDS_extract.c.

3761 {
3762 int64_t i, j;
3763 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_DeleteUnsetRows"))
3764 return (0);
3765
3766 for (i = j = 0; i < SDDS_dataset->n_rows; i++) {
3767 if (SDDS_dataset->row_flag[i]) {
3768 if (i != j) {
3769 SDDS_dataset->row_flag[j] = SDDS_dataset->row_flag[i];
3770 if (!SDDS_TransferRow(SDDS_dataset, j, i)) {
3771 SDDS_SetError("Unable to delete unset rows--problem copying row (SDDS_DeleteUnsetRows)");
3772 return (0);
3773 }
3774 }
3775 j++;
3776 }
3777 }
3778 SDDS_dataset->n_rows = j;
3779 return (1);
3780}
int32_t SDDS_TransferRow(SDDS_DATASET *SDDS_dataset, int64_t target, int64_t source)
Transfers data from a source row to a target row within an SDDS dataset.

◆ SDDS_DisableFSync()

epicsShareFuncSDDS void SDDS_DisableFSync ( SDDS_DATASET * SDDS_dataset)
extern

Disables file synchronization for the SDDS dataset.

This function disables the file synchronization feature for the specified SDDS dataset. File synchronization ensures that all buffered data is immediately written to disk, enhancing data integrity. By disabling this feature, the dataset will no longer perform synchronous writes, which can improve performance but may risk data loss in the event of a system failure.

Parameters
[in,out]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
Postcondition
  • File synchronization is disabled, meaning that SDDS_SyncDataSet will not call fsync.
Note
  • Disabling file synchronization can lead to improved performance, especially when writing large datasets.
  • It is recommended to use this function only when performance is a higher priority than immediate data integrity.
Warning
  • Without file synchronization, there is a risk of data loss if the system crashes before buffered data is written to disk.
  • Ensure that data integrity is managed through other means if synchronization is disabled.

Definition at line 2394 of file SDDS_output.c.

2394 {
2395 SDDS_dataset->layout.data_mode.fsync_data = 0;
2396}

◆ SDDS_DisconnectFile()

epicsShareFuncSDDS int32_t SDDS_DisconnectFile ( SDDS_DATASET * SDDS_dataset)
extern

Disconnects the SDDS dataset from its associated file.

This function terminates the connection between the SDDS dataset and the file it is currently linked to. It ensures that all pending data is flushed to the file, closes the file handle, and updates the dataset's internal state to reflect that it is no longer connected to any file.

Parameters
[in,out]SDDS_datasetPointer to the SDDS_DATASET structure to be disconnected.
Returns
  • 1 on successful disconnection.
  • 0 if an error occurred during disconnection. In this case, an error message is set internally.
Note
  • If the dataset is already disconnected, this function will return an error.
  • This function is not thread-safe if the dataset is being accessed concurrently.
Warning
  • Ensure that no further operations are performed on the dataset after disconnection unless it is reconnected.

Definition at line 71 of file SDDS_output.c.

71 {
72#if SDDS_MPI_IO
73 if (SDDS_dataset->parallel_io)
74 return SDDS_MPI_DisconnectFile(SDDS_dataset);
75#endif
76 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_DisconnectFile"))
77 return 0;
78 if (!SDDS_dataset->layout.filename) {
79 SDDS_SetError("Can't disconnect file. No filename given. (SDDS_DisconnectFile)");
80 return 0;
81 }
82 if (SDDS_dataset->layout.gzipFile) {
83 SDDS_SetError("Can't disconnect file because it is a gzip file. (SDDS_DisconnectFile)");
84 return 0;
85 }
86 if (SDDS_dataset->layout.lzmaFile) {
87 SDDS_SetError("Can't disconnect file because it is a lzma or xz file. (SDDS_DisconnectFile)");
88 return 0;
89 }
90 if (SDDS_dataset->layout.disconnected) {
91 SDDS_SetError("Can't disconnect file. Already disconnected. (SDDS_DisconnectFile)");
92 return 0;
93 }
94 if (SDDS_dataset->page_started && !SDDS_UpdatePage(SDDS_dataset, FLUSH_TABLE)) {
95 SDDS_SetError("Can't disconnect file. Problem updating page. (SDDS_DisconnectFile)");
96 return 0;
97 }
98 if (fclose(SDDS_dataset->layout.fp)) {
99 SDDS_SetError("Can't disconnect file. Problem closing file. (SDDS_DisconnectFile)");
100 return 0;
101 }
102 SDDS_dataset->layout.disconnected = 1;
103 return 1;
104}
int32_t SDDS_UpdatePage(SDDS_DATASET *SDDS_dataset, uint32_t mode)
Updates the current page of the SDDS dataset.
int32_t SDDS_MPI_DisconnectFile(SDDS_DATASET *SDDS_dataset)
Disconnects the MPI file associated with the SDDS dataset.

◆ SDDS_DisconnectInputFile()

epicsShareFuncSDDS long SDDS_DisconnectInputFile ( SDDS_DATASET * SDDS_dataset)
extern

Disconnects the input file from the SDDS dataset.

This function severs the connection between the SDDS dataset and its input file. It closes the file handle, updates the dataset's internal state to indicate disconnection, and returns the current file position before closing. After disconnection, the dataset cannot read further data from the input file until it is reconnected.

Parameters
[in,out]SDDS_datasetPointer to the SDDS_DATASET structure whose input file is to be disconnected.
Returns
  • On success, returns the current file position (as obtained by ftell) before disconnection.
  • On failure, returns -1 and sets an internal error message.
Note
  • This function cannot disconnect compressed input files (gzip, lzma, xz).
  • Attempting to disconnect an already disconnected dataset will result in an error.
Warning
  • Ensure that no further read operations are performed on the dataset after disconnection unless it is reconnected.

Definition at line 171 of file SDDS_output.c.

171 {
172 long position;
173#if SDDS_MPI_IO
174 if (SDDS_dataset->parallel_io) {
175 SDDS_SetError("Error: MPI mode not supported yet in SDDS_DisconnectInputFile");
176 return -1;
177 }
178#endif
179 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_DisconnectInputFile"))
180 return -1;
181 if (!SDDS_dataset->layout.filename) {
182 SDDS_SetError("Can't disconnect file. No filename given. (SDDS_DisconnectInputFile)");
183 return -1;
184 }
185 if (SDDS_dataset->layout.gzipFile) {
186 SDDS_SetError("Can't disconnect file because it is a gzip file. (SDDS_DisconnectInputFile)");
187 return -1;
188 }
189 if (SDDS_dataset->layout.lzmaFile) {
190 SDDS_SetError("Can't disconnect file because it is a lzma or xz file. (SDDS_DisconnectInputFile)");
191 return -1;
192 }
193 if (SDDS_dataset->layout.disconnected) {
194 SDDS_SetError("Can't disconnect file. Already disconnected. (SDDS_DisconnectInputFile)");
195 return -1;
196 }
197 position = ftell(SDDS_dataset->layout.fp);
198 if (fclose(SDDS_dataset->layout.fp)) {
199 SDDS_SetError("Can't disconnect file. Problem closing file. (SDDS_DisconnectInputFile)");
200 return -1;
201 }
202 SDDS_dataset->layout.disconnected = 1;
203 return position;
204}

◆ SDDS_DoFSync()

epicsShareFuncSDDS int32_t SDDS_DoFSync ( SDDS_DATASET * SDDS_dataset)
extern

Synchronizes the SDDS dataset's file to disk.

Performs a file synchronization operation on the specified SDDS dataset to ensure that all buffered data is flushed to the storage medium. This is crucial for maintaining data integrity, especially in scenarios where unexpected shutdowns or crashes may occur.

Platform-Specific Behavior

  • vxWorks, Windows (_WIN32), macOS (APPLE):
    • The function assumes that synchronization is always successful and returns 1.
  • Other Platforms:
    • Attempts to flush the dataset's file buffer to disk using the fsync system call.
    • Returns 1 if fsync succeeds, indicating successful synchronization.
    • Returns 0 if fsync fails or if the dataset/file pointer is invalid.
Parameters
[in]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset to be synchronized.
Returns
int32_t
  • 1 on successful synchronization.
  • 0 on failure.

Definition at line 2443 of file SDDS_output.c.

2443 {
2444#if defined(vxWorks) || defined(_WIN32) || defined(__APPLE__)
2445 return 1;
2446#else
2447 if (SDDS_dataset && SDDS_dataset->layout.fp)
2448 return fsync(fileno(SDDS_dataset->layout.fp)) == 0;
2449 return 0;
2450#endif
2451}

◆ SDDS_EnableFSync()

epicsShareFuncSDDS void SDDS_EnableFSync ( SDDS_DATASET * SDDS_dataset)
extern

Enables file synchronization for the SDDS dataset.

This function enables the file synchronization feature for the specified SDDS dataset. File synchronization ensures that all buffered data is immediately written to disk, enhancing data integrity. Enabling this feature can be crucial for applications where data consistency and reliability are paramount.

Parameters
[in,out]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
Postcondition
  • File synchronization is enabled, meaning that SDDS_SyncDataSet will call fsync to flush buffers to disk.
Note
  • Enabling file synchronization may impact performance due to the increased number of disk write operations.
  • It is recommended to enable synchronization when data integrity is critical, such as in transactional systems.
Warning
  • Frequent synchronization can lead to reduced performance, especially when writing large amounts of data.
  • Balance the need for data integrity with performance requirements based on the specific use case.

Definition at line 2418 of file SDDS_output.c.

2418 {
2419 SDDS_dataset->layout.data_mode.fsync_data = 1;
2420}

◆ SDDS_EraseData()

epicsShareFuncSDDS int32_t SDDS_EraseData ( SDDS_DATASET * SDDS_dataset)
extern

Erases all data entries in the SDDS dataset.

This function removes all data from the specified SDDS dataset, effectively resetting it to an empty state. It frees any allocated memory associated with data columns, parameters, and arrays, ensuring that all dynamic data is properly cleared. This is useful for reusing the dataset for new data without retaining previous entries.

Parameters
[in,out]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
Returns
  • 1 on successful erasure of all data.
  • 0 on failure, with an error message set internally.
Precondition
  • The dataset must be initialized and configured.
Postcondition
  • All data rows are removed from the dataset.
  • Memory allocated for data columns, parameters, and arrays is freed.
  • The dataset is ready to accept new data entries.
Note
  • This function does not alter the dataset's layout definitions; only the data entries are cleared.
  • After erasing data, the dataset can be reused to write new data tables without redefining the layout.
Warning
  • Erasing data is irreversible; ensure that any necessary data is backed up before calling this function.
  • Concurrent access to the dataset while erasing data may lead to undefined behavior.

Definition at line 2264 of file SDDS_output.c.

2264 {
2265 SDDS_LAYOUT *layout;
2266 int64_t i, j;
2267 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_EraseData"))
2268 return 0;
2269 layout = &SDDS_dataset->layout;
2270 if (SDDS_dataset->data) {
2271 for (i = 0; i < layout->n_columns; i++) {
2272 if (!SDDS_dataset->data[i])
2273 continue;
2274 if (layout->column_definition[i].type == SDDS_STRING) {
2275 for (j = 0; j < SDDS_dataset->n_rows; j++) {
2276 if (((char **)SDDS_dataset->data[i])[j]) {
2277 free(((char **)SDDS_dataset->data[i])[j]);
2278 ((char **)SDDS_dataset->data[i])[j] = NULL;
2279 }
2280 }
2281 }
2282 }
2283 }
2284 SDDS_dataset->n_rows = 0;
2285
2286 if (SDDS_dataset->parameter) {
2287 for (i = 0; i < layout->n_parameters; i++) {
2288 if (!SDDS_dataset->parameter[i])
2289 continue;
2290 if (layout->parameter_definition[i].type == SDDS_STRING && *(char **)(SDDS_dataset->parameter[i])) {
2291 free(*(char **)(SDDS_dataset->parameter[i]));
2292 *(char **)SDDS_dataset->parameter[i] = NULL;
2293 }
2294 }
2295 }
2296
2297 if (SDDS_dataset->array) {
2298 for (i = 0; i < layout->n_arrays; i++) {
2299 if (SDDS_dataset->array[i].definition->type == SDDS_STRING) {
2300 for (j = 0; j < SDDS_dataset->array[i].elements; j++) {
2301 if (((char **)SDDS_dataset->array[i].data)[j]) {
2302 free(((char **)SDDS_dataset->array[i].data)[j]);
2303 ((char **)SDDS_dataset->array[i].data)[j] = NULL;
2304 }
2305 }
2306 }
2307 }
2308 }
2309
2310 return (1);
2311}

◆ SDDS_EscapeCommentCharacters()

epicsShareFuncSDDS void SDDS_EscapeCommentCharacters ( char * string,
char cc )
extern

Escapes comment characters within a string by inserting backslashes.

This function scans the input string string and inserts a backslash (\) before each occurrence of the specified comment character cc, provided it is not already escaped. This is useful for preparing strings to include comment characters without them being interpreted as actual comments.

Parameters
[in,out]stringPointer to the string in which comment characters will be escaped. The string will be modified in place.
[in]ccThe comment character to escape (e.g., #).
Note
The function dynamically allocates a temporary buffer to perform the escaping process and ensures that the original string string is updated correctly. The caller must ensure that string has sufficient space to accommodate the additional backslashes.
See also
SDDS_CutOutComments

Definition at line 2021 of file SDDS_utils.c.

2021 {
2022 char *ptr, *s0;
2023 s0 = string;
2024 while (*string) {
2025 if (*string == cc && (string == s0 || *(string - 1) != '\\')) {
2026 ptr = string + strlen(string) + 1;
2027 while (ptr != string) {
2028 *ptr = *(ptr - 1);
2029 ptr--;
2030 }
2031 *string++ = '\\';
2032 }
2033 string++;
2034 }
2035}

◆ SDDS_EscapeNewlines()

epicsShareFuncSDDS void SDDS_EscapeNewlines ( char * s)
extern

Escapes newline characters in a string by replacing them with "\\n".

This function modifies the input string s in place by replacing each newline character (‘’
') with the two-character sequence'\'and'n'`. It shifts the subsequent characters in the string to accommodate the additional character introduced by the escape sequence.

Parameters
[in,out]sPointer to the null-terminated string to be modified. Important: The buffer pointed to by s must have sufficient space to accommodate the additional characters resulting from the escape sequences. Failure to ensure adequate space may lead to buffer overflows.
Warning
This function does not perform bounds checking on the buffer size. Ensure that the buffer is large enough to handle the increased length after escaping newlines.
See also
SDDS_UnescapeNewlines

Definition at line 3264 of file SDDS_utils.c.

3264 {
3265 char *ptr;
3266 while (*s) {
3267 if (*s == '\n') {
3268 ptr = s + strlen(s);
3269 *(ptr + 1) = 0;
3270 while (ptr != s) {
3271 *ptr = *(ptr - 1);
3272 ptr--;
3273 }
3274 *s++ = '\\';
3275 *s++ = 'n';
3276 } else
3277 s++;
3278 }
3279}

◆ SDDS_EscapeQuotes()

epicsShareFuncSDDS void SDDS_EscapeQuotes ( char * s,
char quote_char )
extern

Escapes quote characters within a string by inserting backslashes.

This function scans the input string s and inserts a backslash (\) before each occurrence of the specified quote_char, provided it is not already escaped. This is useful for preparing strings for formats that require escaped quotes.

Parameters
[in,out]sPointer to the string in which quotes will be escaped. The string will be modified in place.
[in]quote_charThe quote character to escape (e.g., ").
Note
The function dynamically allocates a temporary buffer to perform the escaping process and ensures that the original string s is updated correctly. The caller must ensure that s has sufficient space to accommodate the additional backslashes.
See also
SDDS_UnescapeQuotes

Definition at line 1967 of file SDDS_utils.c.

1967 {
1968 char *ptr, *bptr;
1969 char *buffer = NULL;
1970
1971 ptr = s;
1972 buffer = trealloc(buffer, sizeof(*buffer) * (4 * (strlen(s) + 1)));
1973 bptr = buffer;
1974
1975 while (*ptr) {
1976 if (*ptr == quote_char && (ptr == s || *(ptr - 1) != '\\'))
1977 *bptr++ = '\\';
1978 *bptr++ = *ptr++;
1979 }
1980 *bptr = 0;
1981 strcpy(s, buffer);
1982 if (buffer)
1983 free(buffer);
1984}
void * trealloc(void *old_ptr, uint64_t size_of_block)
Reallocates a memory block to a new size.
Definition array.c:190

◆ SDDS_FileIsLocked()

epicsShareFuncSDDS int32_t SDDS_FileIsLocked ( const char * filename)
extern

Determines if a specified file is locked.

This function checks whether the given file is currently locked. If file locking is enabled through the F_TEST and ALLOW_FILE_LOCKING macros, it attempts to open the file and apply a test lock using lockf. The function returns 1 if the file is locked and 0 otherwise.

If file locking is not enabled (i.e., the F_TEST and ALLOW_FILE_LOCKING macros are not defined), the function always returns 0, indicating that the file is not locked.

Parameters
[in]filenameThe path to the file to be checked for a lock.
Returns
  • 1 if the file is locked.
  • 0 if the file is not locked or if file locking is not enabled.
Note
The effectiveness of this function depends on the platform and the implementation of file locking mechanisms.
Warning
Ensure that the F_TEST and ALLOW_FILE_LOCKING macros are appropriately defined to enable file locking functionality.
See also
SDDS_LockFile

Definition at line 3357 of file SDDS_utils.c.

3357 {
3358#if defined(F_TEST) && ALLOW_FILE_LOCKING
3359 FILE *fp;
3360 if (!(fp = fopen(filename, "rb")))
3361 return 0;
3362 if (lockf(fileno(fp), F_TEST, 0) == -1) {
3363 fclose(fp);
3364 return 1;
3365 }
3366 fclose(fp);
3367 return 0;
3368#else
3369 return 0;
3370#endif
3371}

◆ SDDS_FilterRowsByNumScan()

epicsShareFuncSDDS int64_t SDDS_FilterRowsByNumScan ( SDDS_DATASET * SDDS_dataset,
char * filter_column,
uint32_t mode )
extern

Filters rows of interest in an SDDS dataset based on numeric scanning of a specified column.

This function marks rows in the provided SDDS dataset as "of interest" based on whether the entries in the specified filter column can be interpreted as valid numbers. It supports inversion of the filtering criterion through the mode parameter.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
filter_columnA null-terminated string specifying the name of the column used for numeric scanning. This column must not be of string type.
modeAn unsigned integer representing mode flags. Supported flags include:
  • NUMSCANFILTER_INVERT: Invert the filtering criterion (select rows where the entry is not a number).
Returns
On success, returns the number of rows marked as "of interest" after filtering. On failure, returns -1 and sets an appropriate error message.
Return values
-1Indicates that an error occurred (e.g., invalid dataset, unrecognized filter column, filter column is of string type).
Non-negativeInteger representing the count of rows marked as "of interest".
Note
  • The filter column must exist and must not be of string type.
  • The function uses tokenIsNumber to determine if an entry is a valid number.
See also
SDDS_SetRowsOfInterest, SDDS_MatchRowsOfInterest, SDDS_DeleteUnsetRows

Definition at line 3698 of file SDDS_extract.c.

3698 {
3699 int32_t accept, index;
3700 int64_t i, count;
3701 short invert;
3702 char *ptr;
3703
3704 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_FilterRowsByNumScan"))
3705 return (-1);
3706 if (!filter_column) {
3707 SDDS_SetError("Unable to filter rows--filter column name not given (SDDS_FilterRowsByNumScan)");
3708 return (-1);
3709 }
3710 if ((index = SDDS_GetColumnIndex(SDDS_dataset, filter_column)) < 0) {
3711 SDDS_SetError("Unable to filter rows--column name is unrecognized (SDDS_FilterRowsByNumScan)");
3712 return (-1);
3713 }
3714 switch (SDDS_GetColumnType(SDDS_dataset, index)) {
3715 case SDDS_SHORT:
3716 case SDDS_USHORT:
3717 case SDDS_LONG:
3718 case SDDS_ULONG:
3719 case SDDS_LONG64:
3720 case SDDS_ULONG64:
3721 case SDDS_FLOAT:
3722 case SDDS_DOUBLE:
3723 case SDDS_LONGDOUBLE:
3724 case SDDS_CHARACTER:
3725 SDDS_SetError("Unable to filter rows--filter column is not string type (SDDS_FilterRowsByNumScan)");
3726 return (-1);
3727 default:
3728 break;
3729 }
3730 invert = mode & NUMSCANFILTER_INVERT ? 1 : 0;
3731 for (i = count = 0; i < SDDS_dataset->n_rows; i++) {
3732 ptr = ((char **)(SDDS_dataset->data[index]))[i];
3733 accept = !invert;
3734 if (!tokenIsNumber(ptr))
3735 accept = invert;
3736 if ((SDDS_dataset->row_flag[i] = accept))
3737 count++;
3738 }
3739 return (count);
3740}
long tokenIsNumber(char *token)
Checks if the given token represents a valid number.
Definition data_scan.c:530

◆ SDDS_FilterRowsOfInterest()

epicsShareFuncSDDS int64_t SDDS_FilterRowsOfInterest ( SDDS_DATASET * SDDS_dataset,
char * filter_column,
double lower_limit,
double upper_limit,
int32_t logic )
extern

Filters rows of interest in an SDDS dataset based on numeric ranges in a specified column.

This function marks rows in the provided SDDS dataset as "of interest" if the values in the specified filter column fall within the defined numeric range (lower_limit to upper_limit). Logical operations specified by the logic parameter determine how the filtering interacts with existing row flags.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
filter_columnA null-terminated string specifying the name of the column used for numeric filtering. This column must be of a numeric type.
lower_limitThe lower bound of the numeric range. Rows with values below this limit are excluded.
upper_limitThe upper bound of the numeric range. Rows with values above this limit are excluded.
logicAn integer representing logical operation flags. Supported flags include:
  • SDDS_NEGATE_PREVIOUS: Invert the previous row flag.
  • SDDS_NEGATE_MATCH: Invert the match result.
  • SDDS_AND: Combine with existing row flags using logical AND.
  • SDDS_OR: Combine with existing row flags using logical OR.
  • SDDS_NEGATE_EXPRESSION: Invert the entire logical expression.
Returns
On success, returns the number of rows marked as "of interest" after filtering. On failure, returns -1 and sets an appropriate error message.
Return values
-1Indicates that an error occurred (e.g., invalid dataset, unrecognized filter column, non-numeric filter column).
Non-negativeInteger representing the count of rows marked as "of interest".
Note
  • The filter column must exist and be of a numeric type (e.g., SDDS_SHORT, SDDS_USHORT, SDDS_LONG, SDDS_ULONG, SDDS_LONG64, SDDS_ULONG64, SDDS_FLOAT, SDDS_DOUBLE, SDDS_LONGDOUBLE).
  • Logical flags determine how the filtering interacts with existing row flags. Multiple flags can be combined using bitwise OR.
See also
SDDS_SetRowsOfInterest, SDDS_MatchRowsOfInterest, SDDS_DeleteUnsetRows

Definition at line 3629 of file SDDS_extract.c.

3629 {
3630 int32_t accept, type, index;
3631 int64_t i, count;
3632 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_FilterRowsOfInterest"))
3633 return (-1);
3634 if (!filter_column) {
3635 SDDS_SetError("Unable to filter rows--filter column name not given (SDDS_FilterRowsOfInterest)");
3636 return (-1);
3637 }
3638 if ((index = SDDS_GetColumnIndex(SDDS_dataset, filter_column)) < 0) {
3639 SDDS_SetError("Unable to filter rows--column name is unrecognized (SDDS_FilterRowsOfInterest)");
3640 return (-1);
3641 }
3642 switch (type = SDDS_GetColumnType(SDDS_dataset, index)) {
3643 case SDDS_SHORT:
3644 case SDDS_USHORT:
3645 case SDDS_LONG:
3646 case SDDS_ULONG:
3647 case SDDS_LONG64:
3648 case SDDS_ULONG64:
3649 case SDDS_FLOAT:
3650 case SDDS_DOUBLE:
3651 case SDDS_LONGDOUBLE:
3652 break;
3653 default:
3654 SDDS_SetError("Unable to filter rows--filter column is not a numeric type (SDDS_FilterRowsOfInterest)");
3655 return (-1);
3656 }
3657 for (i = count = 0; i < SDDS_dataset->n_rows; i++) {
3658 if (logic & SDDS_NEGATE_PREVIOUS)
3659 SDDS_dataset->row_flag[i] = !SDDS_dataset->row_flag[i];
3660 accept = SDDS_ItemInsideWindow(SDDS_dataset->data[index], i, type, lower_limit, upper_limit);
3661 if (logic & SDDS_NEGATE_MATCH)
3662 accept = !accept;
3663 if (logic & SDDS_AND)
3664 accept = accept && SDDS_dataset->row_flag[i];
3665 else if (logic & SDDS_OR)
3666 accept = accept || SDDS_dataset->row_flag[i];
3667 if (logic & SDDS_NEGATE_EXPRESSION)
3668 accept = !accept;
3669 if ((SDDS_dataset->row_flag[i] = accept))
3670 count++;
3671 }
3672 return (count);
3673}
int32_t SDDS_ItemInsideWindow(void *data, int64_t index, int32_t type, double lower_limit, double upper_limit)
Checks whether a data item is within a specified numeric window.

◆ SDDS_FindArray()

epicsShareFuncSDDS char * SDDS_FindArray ( SDDS_DATASET * SDDS_dataset,
int32_t mode,
... )
extern

Finds the first array in the SDDS dataset that matches the specified criteria.

This function searches through the arrays of the provided SDDS dataset and returns the name of the first array that matches the given criteria based on the specified mode.

The function supports the following modes:

  • FIND_SPECIFIED_TYPE:
    • Parameters: int32_t type, char *name1, char *name2, ..., NULL
    • Description: Finds the first array with a specified type among the provided array names.
  • FIND_ANY_TYPE:
    • Parameters: char *name1, char *name2, ..., NULL
    • Description: Finds the first array with any type among the provided array names.
  • FIND_NUMERIC_TYPE:
    • Parameters: char *name1, char *name2, ..., NULL
    • Description: Finds the first array with a numeric type among the provided array names.
  • FIND_FLOATING_TYPE:
    • Parameters: char *name1, char *name2, ..., NULL
    • Description: Finds the first array with a floating type among the provided array names.
  • FIND_INTEGER_TYPE:
    • Parameters: char *name1, char *name2, ..., NULL
    • Description: Finds the first array with an integer type among the provided array names.
Parameters
[in]SDDS_datasetPointer to the SDDS_DATASET structure containing the dataset.
[in]modeSpecifies the mode for matching arrays. Valid modes are:
  • FIND_SPECIFIED_TYPE
  • FIND_ANY_TYPE
  • FIND_NUMERIC_TYPE
  • FIND_FLOATING_TYPE
  • FIND_INTEGER_TYPE
[in]...Variable arguments depending on mode:
  • FIND_SPECIFIED_TYPE: int32_t type, followed by a list of array names (char *name1, char *name2, ..., NULL)
  • Other Modes: A list of array names (char *name1, char *name2, ..., NULL)
Returns
  • On success, returns a dynamically allocated string containing the name of the first matched array.
  • Returns NULL if no matching array is found or if an error occurs (e.g., memory allocation failure).
Note
  • The caller is responsible for freeing the memory allocated for the returned string using free() or an appropriate memory deallocation function.
  • Ensure that the SDDS dataset is properly initialized and contains arrays before calling this function.
Warning
  • Ensure that the variable arguments match the expected parameters for the specified mode.
  • Failure to free the returned string may lead to memory leaks.
See also
SDDS_FindColumn, SDDS_FindParameter, SDDS_MatchArrays, SDDS_SetError

Definition at line 4575 of file SDDS_utils.c.

4575 {
4576 int32_t index, error, type, thisType;
4577 va_list argptr;
4578 char *name, *buffer;
4579
4580 va_start(argptr, mode);
4581 buffer = NULL;
4582 error = type = 0;
4583
4584 if (mode == FIND_SPECIFIED_TYPE)
4585 type = va_arg(argptr, int32_t);
4586 while ((name = va_arg(argptr, char *))) {
4587 if ((index = SDDS_GetArrayIndex(SDDS_dataset, name)) >= 0) {
4588 thisType = SDDS_GetArrayType(SDDS_dataset, index);
4589 if (mode == FIND_ANY_TYPE || (mode == FIND_SPECIFIED_TYPE && thisType == type) || (mode == FIND_NUMERIC_TYPE && SDDS_NUMERIC_TYPE(thisType)) || (mode == FIND_FLOATING_TYPE && SDDS_FLOATING_TYPE(thisType)) || (mode == FIND_INTEGER_TYPE && SDDS_INTEGER_TYPE(thisType))) {
4590 if (!SDDS_CopyString(&buffer, name)) {
4591 SDDS_SetError("unable to return string from SDDS_FindArray");
4592 error = 1;
4593 break;
4594 }
4595 error = 0;
4596 break;
4597 }
4598 }
4599 }
4600 va_end(argptr);
4601 if (error)
4602 return NULL;
4603 return buffer;
4604}

◆ SDDS_FindColumn()

epicsShareFuncSDDS char * SDDS_FindColumn ( SDDS_DATASET * SDDS_dataset,
int32_t mode,
... )
extern

Finds the first column in the SDDS dataset that matches the specified criteria.

This function searches through the columns of the provided SDDS dataset and returns the name of the first column that matches the given criteria based on the specified mode.

The function supports the following modes:

  • FIND_SPECIFIED_TYPE:
    • Parameters: int32_t type, char *name1, char *name2, ..., NULL
    • Description: Finds the first column with a specified type among the provided column names.
  • FIND_ANY_TYPE:
    • Parameters: char *name1, char *name2, ..., NULL
    • Description: Finds the first column with any type among the provided column names.
  • FIND_NUMERIC_TYPE:
    • Parameters: char *name1, char *name2, ..., NULL
    • Description: Finds the first column with a numeric type among the provided column names.
  • FIND_FLOATING_TYPE:
    • Parameters: char *name1, char *name2, ..., NULL
    • Description: Finds the first column with a floating type among the provided column names.
  • FIND_INTEGER_TYPE:
    • Parameters: char *name1, char *name2, ..., NULL
    • Description: Finds the first column with an integer type among the provided column names.
Parameters
[in]SDDS_datasetPointer to the SDDS_DATASET structure containing the dataset.
[in]modeSpecifies the mode for matching columns. Valid modes are:
  • FIND_SPECIFIED_TYPE
  • FIND_ANY_TYPE
  • FIND_NUMERIC_TYPE
  • FIND_FLOATING_TYPE
  • FIND_INTEGER_TYPE
[in]...Variable arguments depending on mode:
  • FIND_SPECIFIED_TYPE: int32_t type, followed by a list of column names (char *name1, char *name2, ..., NULL)
  • Other Modes: A list of column names (char *name1, char *name2, ..., NULL)
Returns
  • On success, returns a dynamically allocated string containing the name of the first matched column.
  • Returns NULL if no matching column is found or if an error occurs (e.g., memory allocation failure).
Note
  • The caller is responsible for freeing the memory allocated for the returned string using free() or an appropriate memory deallocation function.
  • Ensure that the SDDS dataset is properly initialized and contains columns before calling this function.
Warning
  • Ensure that the variable arguments match the expected parameters for the specified mode.
  • Failure to free the returned string may lead to memory leaks.
See also
SDDS_FindParameter, SDDS_FindArray, SDDS_MatchColumns, SDDS_SetError

Definition at line 4396 of file SDDS_utils.c.

4396 {
4397 /*
4398 SDDS_DATASET *SDDS_dataset, FIND_SPECIFIED_TYPE, int32_t type, char*, ..., NULL)
4399 SDDS_DATASET *SDDS_dataset, FIND_ANY_TYPE, char*, ..., NULL)
4400 */
4401 int32_t index;
4402 int32_t error, type, thisType;
4403 va_list argptr;
4404 char *name, *buffer;
4405
4406 va_start(argptr, mode);
4407 buffer = NULL;
4408 error = type = 0;
4409
4410 if (mode == FIND_SPECIFIED_TYPE)
4411 type = va_arg(argptr, int32_t);
4412 while ((name = va_arg(argptr, char *))) {
4413 if ((index = SDDS_GetColumnIndex(SDDS_dataset, name)) >= 0) {
4414 thisType = SDDS_GetColumnType(SDDS_dataset, index);
4415 if (mode == FIND_ANY_TYPE || (mode == FIND_SPECIFIED_TYPE && thisType == type) || (mode == FIND_NUMERIC_TYPE && SDDS_NUMERIC_TYPE(thisType)) || (mode == FIND_FLOATING_TYPE && SDDS_FLOATING_TYPE(thisType)) || (mode == FIND_INTEGER_TYPE && SDDS_INTEGER_TYPE(thisType))) {
4416 if (!SDDS_CopyString(&buffer, name)) {
4417 SDDS_SetError("unable to return string from SDDS_FindColumn");
4418 error = 1;
4419 break;
4420 }
4421 error = 0;
4422 break;
4423 }
4424 }
4425 }
4426 va_end(argptr);
4427 if (error)
4428 return NULL;
4429 return buffer;
4430}

◆ SDDS_FindParameter()

epicsShareFuncSDDS char * SDDS_FindParameter ( SDDS_DATASET * SDDS_dataset,
int32_t mode,
... )
extern

Finds the first parameter in the SDDS dataset that matches the specified criteria.

This function searches through the parameters of the provided SDDS dataset and returns the name of the first parameter that matches the given criteria based on the specified mode.

The function supports the following modes:

  • FIND_SPECIFIED_TYPE:
    • Parameters: int32_t type, char *name1, char *name2, ..., NULL
    • Description: Finds the first parameter with a specified type among the provided parameter names.
  • FIND_ANY_TYPE:
    • Parameters: char *name1, char *name2, ..., NULL
    • Description: Finds the first parameter with any type among the provided parameter names.
  • FIND_NUMERIC_TYPE:
    • Parameters: char *name1, char *name2, ..., NULL
    • Description: Finds the first parameter with a numeric type among the provided parameter names.
  • FIND_FLOATING_TYPE:
    • Parameters: char *name1, char *name2, ..., NULL
    • Description: Finds the first parameter with a floating type among the provided parameter names.
  • FIND_INTEGER_TYPE:
    • Parameters: char *name1, char *name2, ..., NULL
    • Description: Finds the first parameter with an integer type among the provided parameter names.
Parameters
[in]SDDS_datasetPointer to the SDDS_DATASET structure containing the dataset.
[in]modeSpecifies the mode for matching parameters. Valid modes are:
  • FIND_SPECIFIED_TYPE
  • FIND_ANY_TYPE
  • FIND_NUMERIC_TYPE
  • FIND_FLOATING_TYPE
  • FIND_INTEGER_TYPE
[in]...Variable arguments depending on mode:
  • FIND_SPECIFIED_TYPE: int32_t type, followed by a list of parameter names (char *name1, char *name2, ..., NULL)
  • Other Modes: A list of parameter names (char *name1, char *name2, ..., NULL)
Returns
  • On success, returns a dynamically allocated string containing the name of the first matched parameter.
  • Returns NULL if no matching parameter is found or if an error occurs (e.g., memory allocation failure).
Note
  • The caller is responsible for freeing the memory allocated for the returned string using free() or an appropriate memory deallocation function.
  • Ensure that the SDDS dataset is properly initialized and contains parameters before calling this function.
Warning
  • Ensure that the variable arguments match the expected parameters for the specified mode.
  • Failure to free the returned string may lead to memory leaks.
See also
SDDS_FindColumn, SDDS_FindArray, SDDS_MatchParameters, SDDS_SetError

Definition at line 4488 of file SDDS_utils.c.

4488 {
4489 int32_t index, error, type, thisType;
4490 va_list argptr;
4491 char *name, *buffer;
4492
4493 va_start(argptr, mode);
4494 buffer = NULL;
4495 error = type = 0;
4496
4497 if (mode == FIND_SPECIFIED_TYPE)
4498 type = va_arg(argptr, int32_t);
4499 while ((name = va_arg(argptr, char *))) {
4500 if ((index = SDDS_GetParameterIndex(SDDS_dataset, name)) >= 0) {
4501 thisType = SDDS_GetParameterType(SDDS_dataset, index);
4502 if (mode == FIND_ANY_TYPE || (mode == FIND_SPECIFIED_TYPE && thisType == type) || (mode == FIND_NUMERIC_TYPE && SDDS_NUMERIC_TYPE(thisType)) || (mode == FIND_FLOATING_TYPE && SDDS_FLOATING_TYPE(thisType)) || (mode == FIND_INTEGER_TYPE && SDDS_INTEGER_TYPE(thisType))) {
4503 if (!SDDS_CopyString(&buffer, name)) {
4504 SDDS_SetError("unable to return string from SDDS_FindParameter");
4505 error = 1;
4506 break;
4507 }
4508 error = 0;
4509 break;
4510 }
4511 }
4512 }
4513 va_end(argptr);
4514 if (error)
4515 return NULL;
4516 return buffer;
4517}

◆ SDDS_FlushBuffer()

epicsShareFuncSDDS int32_t SDDS_FlushBuffer ( FILE * fp,
SDDS_FILEBUFFER * fBuffer )
extern

Flushes the buffered data to a file to ensure all data is written.

This function writes any remaining data in the buffer (fBuffer) to the file pointed to by fp. If the buffer contains data, it writes the data to the file, resets the buffer, and flushes the file's output buffer using fflush. This ensures that all buffered data is physically written to the file.

Parameters
fpThe file pointer to which buffered data will be written.
fBufferPointer to an SDDS_FILEBUFFER structure containing the buffered data.
Returns
Returns 1 on success; returns 0 on error.
Note
If fBuffer->bufferSize is zero, the function will only call fflush(fp).
Warning
If fp or fBuffer is NULL, the function sets an error message and returns 0.

Definition at line 650 of file SDDS_binary.c.

650 {
651 int64_t writeBytes;
652 if (!fp) {
653 SDDS_SetError("Unable to flush buffer: file pointer is NULL. (SDDS_FlushBuffer)");
654 return 0;
655 }
656 if (!fBuffer) {
657 SDDS_SetError("Unable to flush buffer: buffer pointer is NULL. (SDDS_FlushBuffer)");
658 return 0;
659 }
660 if (!fBuffer->bufferSize) {
661 if (fflush(fp)) {
662 SDDS_SetError("Problem flushing file (SDDS_FlushBuffer.1)");
663 SDDS_SetError(strerror(errno));
664 return 0;
665 }
666 return 1;
667 }
668 if ((writeBytes = fBuffer->bufferSize - fBuffer->bytesLeft)) {
669 if (writeBytes < 0) {
670 SDDS_SetError("Unable to flush buffer: negative byte count (SDDS_FlushBuffer).");
671 return 0;
672 }
673#ifdef DEBUG
674 fprintf(stderr, "Writing %" PRId64 " bytes to disk\n", writeBytes);
675#endif
676 if (fwrite(fBuffer->buffer, 1, writeBytes, fp) != writeBytes) {
677 SDDS_SetError("Unable to flush buffer: write operation failed (SDDS_FlushBuffer).");
678 return 0;
679 }
680 fBuffer->bytesLeft = fBuffer->bufferSize;
681 fBuffer->data = fBuffer->buffer;
682 }
683 if (fflush(fp)) {
684 SDDS_SetError("Problem flushing file (SDDS_FlushBuffer.2)");
685 SDDS_SetError(strerror(errno));
686 return 0;
687 }
688 return 1;
689}

◆ SDDS_ForceInactive()

epicsShareFuncSDDS int32_t SDDS_ForceInactive ( SDDS_DATASET * SDDS_dataset)
extern

Marks an SDDS dataset as inactive.

This function forces the provided SDDS dataset to become inactive by setting its file pointer to NULL. An inactive dataset is typically not associated with any open file operations.

Parameters
[in]SDDS_datasetPointer to the SDDS_DATASET structure to be marked as inactive.
Returns
  • 1 on successful operation.
  • -1 if a NULL pointer is passed, indicating an error.
Note
After calling this function, the dataset will be considered inactive, and any subsequent operations that require an active dataset may fail.
See also
SDDS_IsActive, SDDS_SetError

Definition at line 3298 of file SDDS_utils.c.

3298 {
3299 if (!SDDS_dataset) {
3300 SDDS_SetError("NULL SDDS_DATASET passed (SDDS_ForceInactive)");
3301 return (-1);
3302 }
3303 SDDS_dataset->layout.fp = NULL;
3304 return (1);
3305}

◆ SDDS_Free()

epicsShareFuncSDDS void SDDS_Free ( void * mem)
extern

Free memory previously allocated by SDDS_Malloc.

This function frees memory that wsa previously allocated by SDDS_Malloc.

Parameters
[in]memPointer to the memory block.
See also
SDDS_Malloc
SDDS_Calloc

Definition at line 721 of file SDDS_utils.c.

721 {
722 /* this is required so the free will be consistent with the malloc.
723 On WIN32 the release (optimized) version of malloc is different
724 from the debug (unoptimized) version, so debug programs freeing
725 memory that was allocated by release, library routines encounter
726 problems. */
727 free(mem);
728}

◆ SDDS_FreeArray()

epicsShareFuncSDDS void SDDS_FreeArray ( SDDS_ARRAY * array)
extern

Frees memory allocated for an SDDS array structure.

This function deallocates all memory associated with an SDDS_ARRAY structure, including its data and definition. It handles the freeing of string elements if the array type is SDDS_STRING and ensures that all pointers are set to NULL after deallocation to prevent dangling references.

Parameters
[in]arrayPointer to the SDDS_ARRAY structure to be freed.
Note
  • The function assumes that the array's data and definitions were allocated using SDDS memory management functions.
  • After calling this function, the array pointer becomes invalid and should not be used.
See also
SDDS_FreePointerArray
SDDS_FreeArrayDefinition
SDDS_Free

Definition at line 2832 of file SDDS_utils.c.

2832 {
2833 int i;
2834 if (!array)
2835 return;
2836 if (array->definition) {
2837 if ((array->definition->type == SDDS_STRING) && (array->data)) {
2838 char **str = (char **)array->data;
2839 for (i = 0; i < array->elements; i++) {
2840 if (str[i])
2841 free(str[i]);
2842 str[i] = NULL;
2843 }
2844 }
2845 }
2846 if (array->definition && array->pointer)
2847 SDDS_FreePointerArray(array->pointer, array->definition->dimensions, array->dimension);
2848 if (array->data)
2849 free(array->data);
2850 array->pointer = array->data = NULL;
2851 if (array->dimension)
2852 free(array->dimension);
2853 if (array->definition)
2854 SDDS_FreeArrayDefinition(array->definition);
2855 array->definition = NULL;
2856 free(array);
2857 array = NULL;
2858}
void SDDS_FreePointerArray(void **data, int32_t dimensions, int32_t *dimension)
Frees a multi-dimensional pointer array created by SDDS_MakePointerArray.

◆ SDDS_FreeArrayDefinition()

epicsShareFuncSDDS int32_t SDDS_FreeArrayDefinition ( ARRAY_DEFINITION * source)
extern

Frees memory allocated for an array definition.

This function deallocates all memory associated with an ARRAY_DEFINITION structure, including its string fields. After freeing, the structure is zeroed out to prevent dangling pointers.

Parameters
[in]sourcePointer to the ARRAY_DEFINITION structure to be freed.
Returns
Returns 1 on successful deallocation. Returns 0 if the source is NULL.
Note
After calling this function, the source pointer becomes invalid and should not be used.
See also
SDDS_CopyArrayDefinition
SDDS_Free

Definition at line 1304 of file SDDS_utils.c.

1304 {
1305 if (!source)
1306 return (0);
1307 if (source->name)
1308 free(source->name);
1309 if (source->symbol)
1310 free(source->symbol);
1311 if (source->units)
1312 free(source->units);
1313 if (source->description)
1314 free(source->description);
1315 if (source->format_string)
1316 free(source->format_string);
1317 if (source->group_name)
1318 free(source->group_name);
1319 SDDS_ZeroMemory(source, sizeof(*source));
1320 free(source);
1321 source = NULL;
1322 return (1);
1323}

◆ SDDS_FreeAssociateDefinition()

epicsShareFuncSDDS int32_t SDDS_FreeAssociateDefinition ( ASSOCIATE_DEFINITION * source)
extern

Frees memory allocated for an associate definition.

This function deallocates all memory associated with an ASSOCIATE_DEFINITION structure, including its string fields. After freeing, the structure is zeroed out to prevent dangling pointers.

Parameters
[in]sourcePointer to the ASSOCIATE_DEFINITION structure to be freed.
Returns
Returns 1 on successful deallocation. Returns 0 if the source is NULL or if required fields are missing.
Note
After calling this function, the source pointer becomes invalid and should not be used.
See also
SDDS_CopyAssociateDefinition
SDDS_Free

Definition at line 1010 of file SDDS_utils.c.

1010 {
1011 if (!source->name)
1012 return (0);
1013 free(source->name);
1014 if (!source->filename)
1015 return (0);
1016 free(source->filename);
1017 if (source->path)
1018 free(source->path);
1019 if (source->description)
1020 free(source->description);
1021 if (source->contents)
1022 free(source->contents);
1023 SDDS_ZeroMemory(source, sizeof(*source));
1024 free(source);
1025 return (1);
1026}

◆ SDDS_FreeColumnDefinition()

epicsShareFuncSDDS int32_t SDDS_FreeColumnDefinition ( COLUMN_DEFINITION * source)
extern

Frees memory allocated for a column definition.

This function deallocates all memory associated with a COLUMN_DEFINITION structure, including its string fields. After freeing, the structure is zeroed out to prevent dangling pointers.

Parameters
[in]sourcePointer to the COLUMN_DEFINITION structure to be freed.
Returns
Returns 1 on successful deallocation. Returns 0 if the source is NULL or if required fields are missing.
Note
After calling this function, the source pointer becomes invalid and should not be used.
See also
SDDS_CopyColumnDefinition
SDDS_Free

Definition at line 1108 of file SDDS_utils.c.

1108 {
1109 if (!source || !source->name)
1110 return (0);
1111 free(source->name);
1112 if (source->symbol)
1113 free(source->symbol);
1114 if (source->units)
1115 free(source->units);
1116 if (source->description)
1117 free(source->description);
1118 if (source->format_string)
1119 free(source->format_string);
1120 SDDS_ZeroMemory(source, sizeof(*source));
1121 free(source);
1122 return (1);
1123}

◆ SDDS_FreeMatrix()

epicsShareFuncSDDS void SDDS_FreeMatrix ( void ** ptr,
int64_t dim1 )
extern

Frees memory allocated for a two-dimensional matrix.

This function deallocates a two-dimensional matrix by freeing each row individually followed by the matrix pointer itself.

Parameters
[in]ptrPointer to the two-dimensional matrix to be freed.
[in]dim1The number of rows in the matrix.
Note
  • The function assumes that the matrix was allocated using SDDS_AllocateMatrix or similar memory allocation functions.
See also
SDDS_AllocateMatrix
free

Definition at line 2874 of file SDDS_utils.c.

2874 {
2875 int64_t i;
2876 if (!ptr)
2877 return;
2878 for (i = 0; i < dim1; i++)
2879 free(ptr[i]);
2880 free(ptr);
2881}

◆ SDDS_FreeParameterDefinition()

epicsShareFuncSDDS int32_t SDDS_FreeParameterDefinition ( PARAMETER_DEFINITION * source)
extern

Frees memory allocated for a parameter definition.

This function deallocates all memory associated with a PARAMETER_DEFINITION structure, including its string fields. After freeing, the structure is zeroed out to prevent dangling pointers.

Parameters
[in]sourcePointer to the PARAMETER_DEFINITION structure to be freed.
Returns
Returns 1 on successful deallocation. Returns 0 if the source is NULL or if required fields are missing.
Note
After calling this function, the source pointer becomes invalid and should not be used.
See also
SDDS_CopyParameterDefinition
SDDS_Free

Definition at line 1205 of file SDDS_utils.c.

1205 {
1206 if (!source || !source->name)
1207 return (0);
1208 free(source->name);
1209 if (source->symbol)
1210 free(source->symbol);
1211 if (source->units)
1212 free(source->units);
1213 if (source->description)
1214 free(source->description);
1215 if (source->format_string)
1216 free(source->format_string);
1217 if (source->fixed_value)
1218 free(source->fixed_value);
1219 SDDS_ZeroMemory(source, sizeof(*source));
1220 free(source);
1221 return (1);
1222}

◆ SDDS_FreeStringArray()

epicsShareFuncSDDS int32_t SDDS_FreeStringArray ( char ** string,
int64_t strings )
extern

Frees an array of strings by deallocating each individual string.

This function iterates through an array of strings, freeing each non-NULL string and setting its pointer to NULL to prevent dangling references.

Parameters
[in,out]stringArray of strings to be freed.
[in]stringsThe number of elements in the string array.
Returns
  • Returns 1 if the array is successfully freed.
  • Returns 0 if the string pointer is NULL.
Note
  • After calling this function, all string pointers within the array are set to NULL.
See also
SDDS_Free
free

Definition at line 2931 of file SDDS_utils.c.

2931 {
2932 int64_t i;
2933 if (!string)
2934 return 0;
2935 for (i = 0; i < strings; i++)
2936 if (string[i]) {
2937 free(string[i]);
2938 string[i] = NULL;
2939 }
2940 return 1;
2941}

◆ SDDS_FreeStringData()

epicsShareFuncSDDS int32_t SDDS_FreeStringData ( SDDS_DATASET * SDDS_dataset)
extern

Frees all allocated string data in the SDDS dataset.

This function frees any strings allocated for parameters, arrays, and columns within the SDDS dataset. It is typically called during termination to clean up allocated memory.

Parameters
SDDS_datasetThe SDDS dataset to free string data from.
Returns
Returns 1 on success, 0 on failure.

Definition at line 1397 of file SDDS_input.c.

1397 {
1398 SDDS_LAYOUT *layout;
1399 char **ptr;
1400 int64_t i, j;
1401 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_Terminate"))
1402 return (0);
1403 layout = &SDDS_dataset->original_layout;
1404
1405 if (SDDS_dataset->parameter) {
1406 for (i = 0; i < layout->n_parameters; i++) {
1407 if (layout->parameter_definition[i].type == SDDS_STRING) {
1408 free(*(char **)(SDDS_dataset->parameter[i]));
1409 *(char **)(SDDS_dataset->parameter[i]) = NULL;
1410 }
1411 }
1412 }
1413 if (SDDS_dataset->array) {
1414 for (i = 0; i < layout->n_arrays; i++) {
1415 if (layout->array_definition[i].type == SDDS_STRING) {
1416 for (j = 0; j < SDDS_dataset->array[i].elements; j++)
1417 if (((char **)SDDS_dataset->array[i].data)[j]) {
1418 free(((char **)SDDS_dataset->array[i].data)[j]);
1419 ((char **)SDDS_dataset->array[i].data)[j] = NULL;
1420 }
1421 }
1422 }
1423 }
1424 if (SDDS_dataset->data) {
1425 for (i = 0; i < layout->n_columns; i++)
1426 if (SDDS_dataset->data[i]) {
1427 if (layout->column_definition[i].type == SDDS_STRING) {
1428 ptr = (char **)SDDS_dataset->data[i];
1429 for (j = 0; j < SDDS_dataset->n_rows_allocated; j++, ptr++)
1430 if (*ptr) {
1431 free(*ptr);
1432 *ptr = NULL;
1433 }
1434 }
1435 }
1436 }
1437 return (1);
1438}

◆ SDDS_GetArray()

epicsShareFuncSDDS SDDS_ARRAY * SDDS_GetArray ( SDDS_DATASET * SDDS_dataset,
char * array_name,
SDDS_ARRAY * memory )
extern

Retrieves an array from the current data table of an SDDS dataset.

This function returns a pointer to a SDDS_ARRAY structure containing the data and other information about a specified array within the current data table of an SDDS dataset. The function can either populate a provided SDDS_ARRAY structure or allocate a new one if memory is NULL.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
array_nameA null-terminated string specifying the name of the SDDS array to retrieve.
memoryOptional pointer to an existing SDDS_ARRAY structure where the array information will be stored. If NULL, a new SDDS_ARRAY structure is allocated and returned.
Returns
On success, returns a pointer to a SDDS_ARRAY structure containing the array data and metadata. If memory is not NULL, the function populates the provided structure. On failure, returns NULL and sets an appropriate error message.
Return values
NULLIndicates that an error occurred (e.g., invalid dataset, unrecognized array name, memory allocation failure).
Non-NULLPointer to a SDDS_ARRAY structure containing the array data and metadata.
Note
  • The caller is responsible for freeing the allocated memory for the SDDS_ARRAY structure if memory is NULL.
  • The definition field in the returned structure points to the internal copy of the array definition.
See also
SDDS_GetArrayInDoubles, SDDS_GetArrayInString, SDDS_GetArrayInLong

Definition at line 4210 of file SDDS_extract.c.

4210 {
4211 int32_t index, type, size;
4212 SDDS_ARRAY *copy, *original;
4213
4214 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_GetArray"))
4215 return (NULL);
4216 if (!array_name) {
4217 SDDS_SetError("Unable to get array--array name pointer is NULL (SDDS_GetArray)");
4218 return (NULL);
4219 }
4220 if ((index = SDDS_GetArrayIndex(SDDS_dataset, array_name)) < 0) {
4221 SDDS_SetError("Unable to get array--array name is unrecognized (SDDS_GetArray)");
4222 return (NULL);
4223 }
4224 if (memory)
4225 copy = memory;
4226 else if (!(copy = (SDDS_ARRAY *)calloc(1, sizeof(*copy)))) {
4227 SDDS_SetError("Unable to get array--allocation failure (SDDS_GetArray)");
4228 return (NULL);
4229 }
4230 original = SDDS_dataset->array + index;
4231 if (copy->definition && !SDDS_FreeArrayDefinition(copy->definition)) {
4232 SDDS_SetError("Unable to get array--array definition corrupted (SDDS_GetArray)");
4233 return (NULL);
4234 }
4235 if (!SDDS_CopyArrayDefinition(&copy->definition, original->definition)) {
4236 SDDS_SetError("Unable to get array--array definition missing (SDDS_GetArray)");
4237 return (NULL);
4238 }
4239 type = copy->definition->type;
4240 size = SDDS_type_size[copy->definition->type - 1];
4241 if (!(copy->dimension = SDDS_Realloc(copy->dimension, sizeof(*copy->dimension) * copy->definition->dimensions))) {
4242 SDDS_SetError("Unable to get array--allocation failure (SDDS_GetArray)");
4243 return (NULL);
4244 }
4245 memcpy((void *)copy->dimension, (void *)original->dimension, sizeof(*copy->dimension) * copy->definition->dimensions);
4246 if (!(copy->elements = original->elements))
4247 return (copy);
4248 if (!(copy->data = SDDS_Realloc(copy->data, size * original->elements))) {
4249 SDDS_SetError("Unable to get array--allocation failure (SDDS_GetArray)");
4250 return (NULL);
4251 }
4252
4253 if (copy->definition->type != SDDS_STRING)
4254 memcpy(copy->data, original->data, size * copy->elements);
4255 else if (!SDDS_CopyStringArray((char **)copy->data, (char **)original->data, original->elements)) {
4256 SDDS_SetError("Unable to get array--string copy failure (SDDS_GetArray)");
4257 return (NULL);
4258 }
4259
4260 /* should free existing subpointers here, but probably not worth the trouble */
4261 if (copy->pointer && copy->definition->dimensions != 1)
4262 free(copy->pointer);
4263 if (!(copy->pointer = SDDS_MakePointerArray(copy->data, type, copy->definition->dimensions, copy->dimension))) {
4264 SDDS_SetError("Unable to get array--couldn't make pointer array (SDDS_GetArray)");
4265 return (NULL);
4266 }
4267 return (copy);
4268}
ARRAY_DEFINITION * SDDS_CopyArrayDefinition(ARRAY_DEFINITION **target, ARRAY_DEFINITION *source)
Creates a copy of an array definition.
void * SDDS_MakePointerArray(void *data, int32_t type, int32_t dimensions, int32_t *dimension)
Creates a multi-dimensional pointer array from a contiguous data block.

◆ SDDS_GetArrayDefinition()

epicsShareFuncSDDS ARRAY_DEFINITION * SDDS_GetArrayDefinition ( SDDS_DATASET * SDDS_dataset,
char * name )
extern

Retrieves the definition of a specified array from the SDDS dataset.

This function searches for an array by its name within the provided SDDS dataset. If found, it creates a copy of the array's definition and returns a pointer to it. The returned pointer should be freed by the caller using SDDS_FreeArrayDefinition to avoid memory leaks.

Parameters
[in]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
[in]nameA null-terminated string specifying the name of the array to retrieve.
Returns
On success, returns a pointer to a newly allocated ARRAY_DEFINITION structure containing the array's information. On failure (e.g., if the array is not found or a copy fails), returns NULL and records an error message.
Note
The caller is responsible for freeing the returned ARRAY_DEFINITION pointer using SDDS_FreeArrayDefinition.
See also
SDDS_CopyArrayDefinition
SDDS_FreeArrayDefinition
SDDS_SetError

Definition at line 1240 of file SDDS_utils.c.

1240 {
1241 int32_t i;
1242 ARRAY_DEFINITION *arraydef;
1243 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_GetArrayDefinition"))
1244 return (NULL);
1245 if (!name) {
1246 SDDS_SetError("Unable to get array definition--name is NULL (SDDS_GetArrayDefinition)");
1247 return (NULL);
1248 }
1249 if ((i = SDDS_GetArrayIndex(SDDS_dataset, name)) < 0)
1250 return NULL;
1251 if (!SDDS_CopyArrayDefinition(&arraydef, SDDS_dataset->layout.array_definition + i)) {
1252 SDDS_SetError("Unable to get array definition--copy failure (SDDS_GetArrayDefinition)");
1253 return (NULL);
1254 }
1255 return (arraydef);
1256}

◆ SDDS_GetArrayIndex()

epicsShareFuncSDDS int32_t SDDS_GetArrayIndex ( SDDS_DATASET * SDDS_dataset,
char * name )
extern

Retrieves the index of a named array in the SDDS dataset.

This function searches for an array by its name within the provided SDDS dataset and returns its index. The index can then be used with other routines for faster access to the array's data or metadata.

Parameters
[in]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
[in]nameA null-terminated string specifying the name of the array whose index is desired.
Returns
On success, returns a non-negative integer representing the index of the array. On failure (e.g., if the array is not found), returns -1 and records an error message.
See also
SDDS_GetArrayDefinition
SDDS_SetError

Definition at line 1433 of file SDDS_utils.c.

1433 {
1434 int32_t i;
1435 SORTED_INDEX key;
1436
1437 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_GetArrayIndex"))
1438 return (-1);
1439 if (!name) {
1440 SDDS_SetError("Unable to get array index--name is NULL (SDDS_GetArrayIndex)");
1441 return (-1);
1442 }
1443 key.name = name;
1444 if ((i = binaryIndexSearch((void **)SDDS_dataset->layout.array_index, SDDS_dataset->layout.n_arrays, &key, SDDS_CompareIndexedNames, 0)) < 0)
1445 return -1;
1446 return SDDS_dataset->layout.array_index[i]->index;
1447}
long binaryIndexSearch(void **array, long members, void *key, int(*compare)(const void *c1, const void *c2), long bracket)
Searches for a key in a sorted array of pointers using binary search.
Definition binsert.c:98

◆ SDDS_GetArrayInDoubles()

epicsShareFuncSDDS double * SDDS_GetArrayInDoubles ( SDDS_DATASET * SDDS_dataset,
char * array_name,
int32_t * values )
extern

Retrieves an array from the current data table of an SDDS dataset and converts its elements to doubles.

This function extracts the specified array from the provided SDDS dataset and converts each of its elements into a double value. It ensures that the array is of a compatible numeric type before performing the conversion.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
array_nameA null-terminated string specifying the name of the SDDS array to retrieve and convert.
valuesPointer to an integer where the number of elements in the array will be stored upon successful completion.
Returns
On success, returns a pointer to an array of double values representing the SDDS array elements. On failure, returns NULL and sets an appropriate error message.
Return values
NULLIndicates that an error occurred (e.g., invalid dataset, unrecognized array name, incompatible array type, memory allocation failure).
Non-NULLPointer to an array of double values representing the SDDS array elements.
Note
  • The caller is responsible for freeing the allocated memory for the returned double array.
  • The function does not handle string-type arrays; attempting to retrieve a string array will result in an error.
See also
SDDS_GetArray, SDDS_GetArrayInString, SDDS_GetArrayInLong

Definition at line 4414 of file SDDS_extract.c.

4414 {
4415 int32_t index, type, i, elements;
4416 SDDS_ARRAY *original;
4417 double *data;
4418 void *rawData;
4419
4420 *values = 0;
4421 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_GetArrayInDoubles"))
4422 return (NULL);
4423 if (!array_name) {
4424 SDDS_SetError("Unable to get array--array name pointer is NULL (SDDS_GetArrayInDoubles)");
4425 return (NULL);
4426 }
4427 if ((index = SDDS_GetArrayIndex(SDDS_dataset, array_name)) < 0) {
4428 SDDS_SetError("Unable to get array--array name is unrecognized (SDDS_GetArrayInDoubles)");
4429 return (NULL);
4430 }
4431 original = SDDS_dataset->array + index;
4432 if ((type = original->definition->type) == SDDS_STRING) {
4433 SDDS_SetError("Unable to get array--string type (SDDS_GetArrayInDoubles)");
4434 return (NULL);
4435 }
4436 elements = original->elements;
4437 if (!(data = SDDS_Malloc(sizeof(*data) * elements))) {
4438 SDDS_SetError("Unable to get array--allocation failure (SDDS_GetArrayInDoubles)");
4439 return (NULL);
4440 }
4441 rawData = original->data;
4442 switch (type) {
4443 case SDDS_LONGDOUBLE:
4444 for (i = 0; i < elements; i++) {
4445 data[i] = ((long double *)rawData)[i];
4446 }
4447 break;
4448 case SDDS_DOUBLE:
4449 for (i = 0; i < elements; i++) {
4450 data[i] = ((double *)rawData)[i];
4451 }
4452 break;
4453 case SDDS_FLOAT:
4454 for (i = 0; i < elements; i++) {
4455 data[i] = ((float *)rawData)[i];
4456 }
4457 break;
4458 case SDDS_LONG64:
4459 for (i = 0; i < elements; i++) {
4460 data[i] = ((int64_t *)rawData)[i];
4461 }
4462 break;
4463 case SDDS_ULONG64:
4464 for (i = 0; i < elements; i++) {
4465 data[i] = ((uint64_t *)rawData)[i];
4466 }
4467 break;
4468 case SDDS_LONG:
4469 for (i = 0; i < elements; i++) {
4470 data[i] = ((int32_t *)rawData)[i];
4471 }
4472 break;
4473 case SDDS_ULONG:
4474 for (i = 0; i < elements; i++) {
4475 data[i] = ((uint32_t *)rawData)[i];
4476 }
4477 break;
4478 case SDDS_SHORT:
4479 for (i = 0; i < elements; i++) {
4480 data[i] = ((short *)rawData)[i];
4481 }
4482 break;
4483 case SDDS_USHORT:
4484 for (i = 0; i < elements; i++) {
4485 data[i] = ((unsigned short *)rawData)[i];
4486 }
4487 break;
4488 case SDDS_CHARACTER:
4489 for (i = 0; i < elements; i++) {
4490 data[i] = ((char *)rawData)[i];
4491 }
4492 break;
4493 }
4494 *values = elements;
4495 return data;
4496}

◆ SDDS_GetArrayInformation()

epicsShareFuncSDDS int32_t SDDS_GetArrayInformation ( SDDS_DATASET * SDDS_dataset,
char * field_name,
void * memory,
int32_t mode,
... )
extern

Retrieves information about a specified array in the SDDS dataset.

This function is the preferred alternative to SDDS_GetArrayDefinition. It allows you to obtain information about a specific field of an array, either by the array's name or index.

Parameters
[in]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
[in]field_nameA null-terminated string specifying the name of the field for which information is requested.
[out]memoryPointer to a variable where the retrieved information will be stored. The variable should be of type data_type*, where data_type corresponds to the type of the requested information. For STRING information, use char*. If memory is NULL, the function will verify the existence and type of the information, returning the data type without storing any data.
[in]modeSpecifies how to identify the array. Valid values are:
  • SDDS_GET_BY_NAME: Identify the array by its name. Requires an additional argument of type char* (array name).
  • SDDS_GET_BY_INDEX: Identify the array by its index. Requires an additional argument of type int32_t (array index).
Returns
On success, returns the SDDS data type of the requested information. On failure, returns zero and records an error message.
Note
This function uses variable arguments to accept either the array name or index based on the mode parameter.
See also
SDDS_GetArrayDefinition

Definition at line 192 of file SDDS_info.c.

192 {
193 int32_t field_index, type, array_index;
194 ARRAY_DEFINITION *arraydef;
195 char *array_name;
196 va_list argptr;
197 int32_t retval;
198
199 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_GetArrayInformation"))
200 return (0);
201
202 if (!field_name) {
203 SDDS_SetError("NULL field name passed. (SDDS_GetArrayInformation)");
204 return (0);
205 }
206
207 va_start(argptr, mode);
208 retval = 1;
209 if (mode & SDDS_GET_BY_INDEX) {
210 if ((array_index = va_arg(argptr, int32_t)) < 0 || array_index >= SDDS_dataset->layout.n_arrays) {
211 SDDS_SetError("Invalid array index passed. (SDDS_GetArrayInformation)");
212 retval = 0;
213 }
214 } else {
215 if (!(array_name = va_arg(argptr, char *))) {
216 SDDS_SetError("NULL array name passed. (SDDS_GetArrayInformation)");
217 retval = 0;
218 }
219 if ((array_index = SDDS_GetArrayIndex(SDDS_dataset, array_name)) < 0) {
220 SDDS_SetError("Unknown array name given (SDDS_GetArrayInformation)");
221 retval = 0;
222 }
223 }
224 arraydef = SDDS_dataset->layout.array_definition + array_index;
225 va_end(argptr);
226 if (!retval)
227 return (0);
228
229 for (field_index = 0; field_index < SDDS_ARRAY_FIELDS; field_index++)
230 if (strcmp(field_name, SDDS_ArrayFieldInformation[field_index].name) == 0)
231 break;
232 if (field_index == SDDS_ARRAY_FIELDS) {
233 SDDS_SetError("Unknown field name given (SDDS_GetArrayInformation)");
234 return (0);
235 }
236 type = SDDS_ArrayFieldInformation[field_index].type;
237 if (!memory)
238 return (type);
239 if (type == SDDS_STRING) {
240 if (!SDDS_CopyString((char **)memory, *((char **)((char *)arraydef + SDDS_ArrayFieldInformation[field_index].offset)))) {
241 SDDS_SetError("Unable to copy field data (SDDS_GetArrayInformation)");
242 return (0);
243 }
244 } else
245 memcpy(memory, (char *)arraydef + SDDS_ArrayFieldInformation[field_index].offset, SDDS_type_size[type - 1]);
246 return (type);
247}

◆ SDDS_GetArrayInLong()

epicsShareFuncSDDS int32_t * SDDS_GetArrayInLong ( SDDS_DATASET * SDDS_dataset,
char * array_name,
int32_t * values )
extern

Retrieves an array from the current data table of an SDDS dataset and converts its elements to 32-bit integers.

This function extracts the specified array from the provided SDDS dataset and converts each of its elements into a 32-bit integer (int32_t). It ensures that the array is of a compatible numeric type before performing the conversion.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
array_nameA null-terminated string specifying the name of the SDDS array to retrieve and convert.
valuesPointer to an integer where the number of elements in the array will be stored upon successful completion.
Returns
On success, returns a pointer to an array of int32_t values representing the SDDS array elements. On failure, returns NULL and sets an appropriate error message.
Return values
NULLIndicates that an error occurred (e.g., invalid dataset, unrecognized array name, incompatible array type, memory allocation failure).
Non-NULLPointer to an array of int32_t values representing the SDDS array elements.
Note
  • The caller is responsible for freeing the allocated memory for the returned int32_t array.
  • The function does not handle string-type arrays; attempting to retrieve a string array will result in an error.
See also
SDDS_GetArray, SDDS_GetArrayInDoubles, SDDS_GetArrayInString

Definition at line 4519 of file SDDS_extract.c.

4519 {
4520 int32_t index, type, i, elements;
4521 SDDS_ARRAY *original;
4522 int32_t *data;
4523 void *rawData;
4524
4525 *values = 0;
4526 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_GetArrayInLong"))
4527 return (NULL);
4528 if (!array_name) {
4529 SDDS_SetError("Unable to get array--array name pointer is NULL (SDDS_GetArrayInLong)");
4530 return (NULL);
4531 }
4532 if ((index = SDDS_GetArrayIndex(SDDS_dataset, array_name)) < 0) {
4533 SDDS_SetError("Unable to get array--array name is unrecognized (SDDS_GetArrayInLong)");
4534 return (NULL);
4535 }
4536 original = SDDS_dataset->array + index;
4537 if ((type = original->definition->type) == SDDS_STRING) {
4538 SDDS_SetError("Unable to get array--string type (SDDS_GetArrayInLong)");
4539 return (NULL);
4540 }
4541 elements = original->elements;
4542 if (!(data = SDDS_Malloc(sizeof(*data) * elements))) {
4543 SDDS_SetError("Unable to get array--allocation failure (SDDS_GetArrayInLong)");
4544 return (NULL);
4545 }
4546 rawData = original->data;
4547 switch (type) {
4548 case SDDS_LONGDOUBLE:
4549 for (i = 0; i < elements; i++) {
4550 data[i] = ((long double *)rawData)[i];
4551 }
4552 break;
4553 case SDDS_DOUBLE:
4554 for (i = 0; i < elements; i++) {
4555 data[i] = ((double *)rawData)[i];
4556 }
4557 break;
4558 case SDDS_FLOAT:
4559 for (i = 0; i < elements; i++) {
4560 data[i] = ((float *)rawData)[i];
4561 }
4562 break;
4563 case SDDS_LONG64:
4564 for (i = 0; i < elements; i++) {
4565 data[i] = ((int64_t *)rawData)[i];
4566 }
4567 break;
4568 case SDDS_ULONG64:
4569 for (i = 0; i < elements; i++) {
4570 data[i] = ((uint64_t *)rawData)[i];
4571 }
4572 break;
4573 case SDDS_LONG:
4574 for (i = 0; i < elements; i++) {
4575 data[i] = ((int32_t *)rawData)[i];
4576 }
4577 break;
4578 case SDDS_ULONG:
4579 for (i = 0; i < elements; i++) {
4580 data[i] = ((uint32_t *)rawData)[i];
4581 }
4582 break;
4583 case SDDS_SHORT:
4584 for (i = 0; i < elements; i++) {
4585 data[i] = ((short *)rawData)[i];
4586 }
4587 break;
4588 case SDDS_USHORT:
4589 for (i = 0; i < elements; i++) {
4590 data[i] = ((unsigned short *)rawData)[i];
4591 }
4592 break;
4593 case SDDS_CHARACTER:
4594 for (i = 0; i < elements; i++) {
4595 data[i] = ((char *)rawData)[i];
4596 }
4597 break;
4598 }
4599 *values = elements;
4600 return data;
4601}

◆ SDDS_GetArrayInString()

epicsShareFuncSDDS char ** SDDS_GetArrayInString ( SDDS_DATASET * SDDS_dataset,
char * array_name,
int32_t * values )
extern

Retrieves an array from the current data table of an SDDS dataset and converts its elements to strings.

This function extracts the specified array from the provided SDDS dataset and converts each of its elements into a null-terminated string representation. The conversion respects the data type of the array elements, ensuring accurate string formatting.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
array_nameA null-terminated string specifying the name of the SDDS array to retrieve and convert.
valuesPointer to an integer where the number of elements in the array will be stored upon successful completion.
Returns
On success, returns a pointer to an array of null-terminated strings (char **). Each string represents an element of the original SDDS array. On failure, returns NULL and sets an appropriate error message.
Return values
NULLIndicates that an error occurred (e.g., invalid dataset, unrecognized array name, memory allocation failure).
Non-NULLPointer to an array of strings representing the SDDS array elements.
Note
  • The caller is responsible for freeing each string in the returned array as well as the array itself.
  • The function handles different data types, including numeric types and strings, ensuring proper formatting for each type.
See also
SDDS_GetArray, SDDS_GetArrayInDoubles, SDDS_GetArrayInLong

Definition at line 4292 of file SDDS_extract.c.

4292 {
4293 int32_t index, type, i, elements;
4294 SDDS_ARRAY *original;
4295 char **data;
4296 char buffer[SDDS_MAXLINE];
4297 void *rawData;
4298
4299 *values = 0;
4300 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_GetArrayInString"))
4301 return (NULL);
4302 if (!array_name) {
4303 SDDS_SetError("Unable to get array--array name pointer is NULL (SDDS_GetArrayInString)");
4304 return (NULL);
4305 }
4306 if ((index = SDDS_GetArrayIndex(SDDS_dataset, array_name)) < 0) {
4307 SDDS_SetError("Unable to get array--array name is unrecognized (SDDS_GetArrayInString)");
4308 return (NULL);
4309 }
4310 original = SDDS_dataset->array + index;
4311 type = original->definition->type;
4312 elements = original->elements;
4313 if (!(data = (char **)SDDS_Malloc(sizeof(*data) * elements))) {
4314 SDDS_SetError("Unable to get array--allocation failure (SDDS_GetArrayInString)");
4315 return (NULL);
4316 }
4317 rawData = original->data;
4318 switch (type) {
4319 case SDDS_LONGDOUBLE:
4320 for (i = 0; i < elements; i++) {
4321 if (LDBL_DIG == 18) {
4322 sprintf(buffer, "%22.18Le", ((long double *)rawData)[i]);
4323 } else {
4324 sprintf(buffer, "%22.15Le", ((long double *)rawData)[i]);
4325 }
4326 SDDS_CopyString(&data[i], buffer);
4327 }
4328 break;
4329 case SDDS_DOUBLE:
4330 for (i = 0; i < elements; i++) {
4331 sprintf(buffer, "%22.15le", ((double *)rawData)[i]);
4332 SDDS_CopyString(&data[i], buffer);
4333 }
4334 break;
4335 case SDDS_FLOAT:
4336 for (i = 0; i < elements; i++) {
4337 sprintf(buffer, "%15.8e", ((float *)rawData)[i]);
4338 SDDS_CopyString(&data[i], buffer);
4339 }
4340 break;
4341 case SDDS_LONG64:
4342 for (i = 0; i < elements; i++) {
4343 sprintf(buffer, "%" PRId64, ((int64_t *)rawData)[i]);
4344 SDDS_CopyString(&data[i], buffer);
4345 }
4346 break;
4347 case SDDS_ULONG64:
4348 for (i = 0; i < elements; i++) {
4349 sprintf(buffer, "%" PRIu64, ((uint64_t *)rawData)[i]);
4350 SDDS_CopyString(&data[i], buffer);
4351 }
4352 break;
4353 case SDDS_LONG:
4354 for (i = 0; i < elements; i++) {
4355 sprintf(buffer, "%" PRId32, ((int32_t *)rawData)[i]);
4356 SDDS_CopyString(&data[i], buffer);
4357 }
4358 break;
4359 case SDDS_ULONG:
4360 for (i = 0; i < elements; i++) {
4361 sprintf(buffer, "%" PRIu32, ((uint32_t *)rawData)[i]);
4362 SDDS_CopyString(&data[i], buffer);
4363 }
4364 break;
4365 case SDDS_SHORT:
4366 for (i = 0; i < elements; i++) {
4367 sprintf(buffer, "%hd", ((short *)rawData)[i]);
4368 SDDS_CopyString(&data[i], buffer);
4369 }
4370 break;
4371 case SDDS_USHORT:
4372 for (i = 0; i < elements; i++) {
4373 sprintf(buffer, "%hu", ((unsigned short *)rawData)[i]);
4374 SDDS_CopyString(&data[i], buffer);
4375 }
4376 break;
4377 case SDDS_CHARACTER:
4378 for (i = 0; i < elements; i++) {
4379 sprintf(buffer, "%c", ((char *)rawData)[i]);
4380 SDDS_CopyString(&data[i], buffer);
4381 }
4382 break;
4383 case SDDS_STRING:
4384 for (i = 0; i < elements; i++) {
4385 SDDS_CopyString(&data[i], ((char **)rawData)[i]);
4386 }
4387 break;
4388 }
4389 *values = elements;
4390 return data;
4391}

◆ SDDS_GetArrayNames()

epicsShareFuncSDDS char ** SDDS_GetArrayNames ( SDDS_DATASET * SDDS_dataset,
int32_t * number )
extern

Retrieves the names of all arrays in the SDDS dataset.

This function allocates and returns an array of NULL-terminated strings containing the names of the arrays in the provided SDDS_dataset.

Parameters
[in]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
[out]numberPointer to an int32_t variable where the number of retrieved array names will be stored.
Returns
  • Returns a pointer to an array of NULL-terminated strings containing the array names on success.
  • Returns NULL on failure (e.g., if the dataset is invalid or memory allocation fails) and records an error message.
Note
The caller is responsible for freeing the memory allocated for the returned array and its strings using SDDS_FreeStringArray or similar functions.
See also
SDDS_CheckDataset
SDDS_Malloc
SDDS_CopyString
SDDS_SetError

Definition at line 2605 of file SDDS_utils.c.

2605 {
2606 int32_t i;
2607 char **name;
2608 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_GetArrayNames"))
2609 return (NULL);
2610 *number = SDDS_dataset->layout.n_arrays;
2611 if (!(name = (char **)SDDS_Malloc(sizeof(*name) * SDDS_dataset->layout.n_arrays))) {
2612 SDDS_SetError("Unable to get array names--allocation failure (SDDS_GetArrayNames)");
2613 return (NULL);
2614 }
2615 for (i = 0; i < SDDS_dataset->layout.n_arrays; i++) {
2616 if (!SDDS_CopyString(name + i, SDDS_dataset->layout.array_definition[i].name)) {
2617 free(name);
2618 return (NULL);
2619 }
2620 }
2621 return (name);
2622}

◆ SDDS_GetArrayType()

epicsShareFuncSDDS int32_t SDDS_GetArrayType ( SDDS_DATASET * SDDS_dataset,
int32_t index )
extern

Retrieves the data type of an array in the SDDS dataset by its index.

This function returns the SDDS data type of the specified array within the dataset. The data type corresponds to one of the predefined SDDS type constants, such as SDDS_LONGDOUBLE, SDDS_DOUBLE, SDDS_FLOAT, etc.

Parameters
[in]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
[in]indexThe zero-based index of the array whose data type is to be retrieved. The index should be obtained from SDDS_DefineArray or SDDS_GetArrayIndex.
Returns
On success, returns the SDDS data type of the array as an int32_t. On failure (e.g., if the index is out of range or the dataset is invalid), returns 0 and records an error message.
Note
The function does not perform type validation beyond checking the index range. It assumes that the dataset's array definitions are correctly initialized.
See also
SDDS_GetArrayIndex
SDDS_SetError

Definition at line 2268 of file SDDS_utils.c.

2268 {
2269 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_GetArrayType"))
2270 return (0);
2271 if (index < 0 || index >= SDDS_dataset->layout.n_arrays) {
2272 SDDS_SetError("Unable to get array type--array index is out of range (SDDS_GetArrayType)");
2273 return (0);
2274 }
2275 return (SDDS_dataset->layout.array_definition[index].type);
2276}

◆ SDDS_GetAssociateDefinition()

epicsShareFuncSDDS ASSOCIATE_DEFINITION * SDDS_GetAssociateDefinition ( SDDS_DATASET * SDDS_dataset,
char * name )
extern

Retrieves the definition of a specified associate from the SDDS dataset.

This function searches for an associate by its name within the provided SDDS dataset. If found, it creates a copy of the associate's definition and returns a pointer to it. The returned pointer should be freed by the caller using SDDS_FreeAssociateDefinition to avoid memory leaks.

Parameters
[in]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
[in]nameA null-terminated string specifying the name of the associate to retrieve.
Returns
On success, returns a pointer to a newly allocated ASSOCIATE_DEFINITION structure containing the associate's information. On failure (e.g., if the associate is not found or a copy fails), returns NULL and records an error message.
Note
The caller is responsible for freeing the returned ASSOCIATE_DEFINITION pointer using SDDS_FreeAssociateDefinition.
See also
SDDS_CopyAssociateDefinition
SDDS_FreeAssociateDefinition
SDDS_SetError

Definition at line 949 of file SDDS_utils.c.

949 {
950 int32_t i;
951 ASSOCIATE_DEFINITION *assdef;
952 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_GetAssociateDefinition"))
953 return (NULL);
954 if (!name) {
955 SDDS_SetError("Unable to get associate definition--name is NULL (SDDS_GetAssociateDefinition)");
956 return (NULL);
957 }
958 for (i = 0; i < SDDS_dataset->layout.n_associates; i++) {
959 if (strcmp(SDDS_dataset->layout.associate_definition[i].name, name) == 0) {
960 if (!SDDS_CopyAssociateDefinition(&assdef, SDDS_dataset->layout.associate_definition + i)) {
961 SDDS_SetError("Unable to get associate definition--copy failure (SDDS_GetAssociateDefinition)");
962 return (NULL);
963 }
964 return (assdef);
965 }
966 }
967 return (NULL);
968}
ASSOCIATE_DEFINITION * SDDS_CopyAssociateDefinition(ASSOCIATE_DEFINITION **target, ASSOCIATE_DEFINITION *source)
Creates a copy of an associate definition.
Definition SDDS_utils.c:986

◆ SDDS_GetAssociateIndex()

epicsShareFuncSDDS int32_t SDDS_GetAssociateIndex ( SDDS_DATASET * SDDS_dataset,
char * name )
extern

Retrieves the index of a named associate in the SDDS dataset.

This function searches for an associate by its name within the provided SDDS dataset and returns its index. The index can then be used with other routines for faster access to the associate's data or metadata.

Parameters
[in]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
[in]nameA null-terminated string specifying the name of the associate whose index is desired.
Returns
On success, returns a non-negative integer representing the index of the associate. On failure (e.g., if the associate is not found), returns -1 and records an error message.
See also
SDDS_GetAssociateDefinition
SDDS_SetError

Definition at line 1462 of file SDDS_utils.c.

1462 {
1463 int32_t i;
1464 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_GetAssociateIndex"))
1465 return (-1);
1466 if (!name) {
1467 SDDS_SetError("Unable to get associate index--name is NULL (SDDS_GetAssociateIndex)");
1468 return (-1);
1469 }
1470 for (i = 0; i < SDDS_dataset->layout.n_associates; i++) {
1471 if (strcmp(SDDS_dataset->layout.associate_definition[i].name, name) == 0)
1472 return (i);
1473 }
1474 return (-1);
1475}

◆ SDDS_GetAssociateInformation()

epicsShareFuncSDDS int32_t SDDS_GetAssociateInformation ( SDDS_DATASET * SDDS_dataset,
char * field_name,
void * memory,
int32_t mode,
... )
extern

Retrieves information about a specified associate in the SDDS dataset.

This function allows you to obtain information about a specific field of an associate, either by the associate's name or index.

Parameters
[in]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
[in]field_nameA null-terminated string specifying the name of the field for which information is requested.
[out]memoryPointer to a variable where the retrieved information will be stored. The variable should be of type data_type*, where data_type corresponds to the type of the requested information. For STRING information, use char*. If memory is NULL, the function will verify the existence and type of the information, returning the data type without storing any data.
[in]modeSpecifies how to identify the associate. Valid values are:
  • SDDS_GET_BY_NAME: Identify the associate by its name. Requires an additional argument of type char* (associate name).
  • SDDS_GET_BY_INDEX: Identify the associate by its index. Requires an additional argument of type int32_t (associate index).
Returns
On success, returns the SDDS data type of the requested information. On failure, returns zero and records an error message.
Note
This function uses variable arguments to accept either the associate name or index based on the mode parameter.
See also
SDDS_GetAssociateDefinition

Definition at line 267 of file SDDS_info.c.

267 {
268 int32_t field_index, type, associate_index;
269 ASSOCIATE_DEFINITION *associatedef;
270 char *associate_name;
271 va_list argptr;
272 int32_t retval;
273
274 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_GetAssociateInformation"))
275 return (0);
276
277 if (!field_name) {
278 SDDS_SetError("NULL field name passed. (SDDS_GetAssociateInformation)");
279 return (0);
280 }
281
282 va_start(argptr, mode);
283 retval = 1;
284 if (mode & SDDS_GET_BY_INDEX) {
285 if ((associate_index = va_arg(argptr, int32_t)) < 0 || associate_index >= SDDS_dataset->layout.n_associates) {
286 SDDS_SetError("Invalid associate index passed. (SDDS_GetAssociateInformation)");
287 retval = 0;
288 }
289 } else {
290 if (!(associate_name = va_arg(argptr, char *))) {
291 SDDS_SetError("NULL associate name passed. (SDDS_GetAssociateInformation)");
292 retval = 0;
293 }
294 if ((associate_index = SDDS_GetAssociateIndex(SDDS_dataset, associate_name)) < 0) {
295 SDDS_SetError("Unknown associate name given (SDDS_GetAssociateInformation)");
296 retval = 0;
297 }
298 }
299 associatedef = SDDS_dataset->layout.associate_definition + associate_index;
300 va_end(argptr);
301 if (!retval)
302 return (0);
303
304 for (field_index = 0; field_index < SDDS_ASSOCIATE_FIELDS; field_index++)
305 if (strcmp(field_name, SDDS_AssociateFieldInformation[field_index].name) == 0)
306 break;
307 if (field_index == SDDS_ASSOCIATE_FIELDS) {
308 SDDS_SetError("Unknown field name given (SDDS_GetAssociateInformation)");
309 return (0);
310 }
311 type = SDDS_AssociateFieldInformation[field_index].type;
312 if (!memory)
313 return (type);
314 if (type == SDDS_STRING) {
315 if (!SDDS_CopyString((char **)memory, *((char **)((char *)associatedef + SDDS_AssociateFieldInformation[field_index].offset)))) {
316 SDDS_SetError("Unable to copy field data (SDDS_GetAssociateInformation)");
317 return (0);
318 }
319 } else
320 memcpy(memory, (char *)associatedef + SDDS_AssociateFieldInformation[field_index].offset, SDDS_type_size[type - 1]);
321 return (type);
322}
SDDS_FIELD_INFORMATION SDDS_AssociateFieldInformation[SDDS_ASSOCIATE_FIELDS]
Field information for associate definitions.
Definition SDDS_data.c:225

◆ SDDS_GetAssociateNames()

epicsShareFuncSDDS char ** SDDS_GetAssociateNames ( SDDS_DATASET * SDDS_dataset,
int32_t * number )
extern

Retrieves the names of all associates in the SDDS dataset.

This function allocates and returns an array of NULL-terminated strings containing the names of the associates in the provided SDDS_dataset.

Parameters
[in]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
[out]numberPointer to an int32_t variable where the number of retrieved associate names will be stored.
Returns
  • Returns a pointer to an array of NULL-terminated strings containing the associate names on success.
  • Returns NULL on failure (e.g., if the dataset is invalid or memory allocation fails) and records an error message.
Note
The caller is responsible for freeing the memory allocated for the returned array and its strings using SDDS_FreeStringArray or similar functions.
See also
SDDS_CheckDataset
SDDS_Malloc
SDDS_CopyString
SDDS_SetError

Definition at line 2643 of file SDDS_utils.c.

2643 {
2644 int32_t i;
2645 char **name;
2646 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_GetAssociateNames"))
2647 return (NULL);
2648 if (!(name = (char **)SDDS_Malloc(sizeof(*name) * SDDS_dataset->layout.n_associates))) {
2649 SDDS_SetError("Unable to get associate names--allocation failure (SDDS_GetAssociateNames)");
2650 return (NULL);
2651 }
2652 *number = SDDS_dataset->layout.n_associates;
2653 for (i = 0; i < SDDS_dataset->layout.n_associates; i++) {
2654 if (!SDDS_CopyString(name + i, SDDS_dataset->layout.associate_definition[i].name)) {
2655 free(name);
2656 return (NULL);
2657 }
2658 }
2659 return (name);
2660}

◆ SDDS_GetCastMatrixOfRows()

epicsShareFuncSDDS void * SDDS_GetCastMatrixOfRows ( SDDS_DATASET * SDDS_dataset,
int64_t * n_rows,
int32_t sddsType )
extern

Retrieves all rows marked as "of interest" as a matrix, casting each value to a specified numerical type.

This function extracts all rows that are flagged as "of interest" within the current data table of a dataset and casts each value to a specified numerical type. It processes only those columns that are flagged as "of interest" and returns the data as a matrix, where each row is an array of casted values corresponding to the selected columns.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the data set.
n_rowsPointer to an int64_t variable where the number of rows retrieved will be stored.
sddsTypeInteger constant representing the desired data type for casting (e.g., SDDS_DOUBLE, SDDS_FLOAT, etc.). Must be a valid numerical type as defined by SDDS.
Returns
  • Pointer to an array of pointers, where each pointer references a row's data array cast to the specified type.
  • NULL if an error occurs (e.g., invalid dataset, no columns selected, inconsistent data types among selected columns, non-numeric sddsType, memory allocation failure). In this case, an error message is recorded internally.
Warning
  • The caller is responsible for freeing the allocated memory to prevent memory leaks. This includes freeing each individual row array followed by the array of pointers itself.
  • All selected columns must have numerical data types. If any selected column is non-numeric, the function will fail.
  • Ensure that sddsType is a valid numerical type supported by SDDS.
Note
  • The number of rows retrieved is stored in the variable pointed to by n_rows.
  • This function performs type casting using SDDS_CastValue. If casting fails for any value, the function will terminate and return NULL.
  • If the dataset's memory mode for the columns is set to DONT_TRACK_COLUMN_MEMORY_AFTER_ACCESS, the internal data for the columns may be freed after access.
See also

Definition at line 2344 of file SDDS_extract.c.

2344 {
2345 void **data;
2346 int32_t size;
2347 int64_t i, j, k;
2348
2349 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_GetCastMatrixOfRows"))
2350 return (NULL);
2351 if (!SDDS_NUMERIC_TYPE(sddsType)) {
2352 SDDS_SetError("Unable to get matrix of rows--no columns selected (SDDS_GetCastMatrixOfRows)");
2353 return NULL;
2354 }
2355 if (SDDS_dataset->n_of_interest <= 0) {
2356 SDDS_SetError("Unable to get matrix of rows--no columns selected (SDDS_GetCastMatrixOfRows)");
2357 return (NULL);
2358 }
2359 if (!SDDS_CheckTabularData(SDDS_dataset, "SDDS_GetCastMatrixOfRows"))
2360 return (NULL);
2361 size = SDDS_type_size[sddsType - 1];
2362 if ((*n_rows = SDDS_CountRowsOfInterest(SDDS_dataset)) <= 0) {
2363 SDDS_SetError("Unable to get matrix of rows--no rows of interest (SDDS_GetCastMatrixOfRows)");
2364 return (NULL);
2365 }
2366 if (!(data = (void **)SDDS_Malloc(sizeof(*data) * (*n_rows)))) {
2367 SDDS_SetError("Unable to get matrix of rows--memory allocation failure (SDDS_GetCastMatrixOfRows)");
2368 return (NULL);
2369 }
2370 for (i = 0; i < SDDS_dataset->n_of_interest; i++) {
2371 if (!SDDS_NUMERIC_TYPE(SDDS_dataset->layout.column_definition[SDDS_dataset->column_order[i]].type)) {
2372 SDDS_SetError("Unable to get matrix of rows--not all columns are numeric (SDDS_GetCastMatrixOfRows)");
2373 return NULL;
2374 }
2375 }
2376 for (j = k = 0; j < SDDS_dataset->n_rows; j++) {
2377 if (SDDS_dataset->row_flag[j]) {
2378 if (!(data[k] = SDDS_Malloc(size * SDDS_dataset->n_of_interest))) {
2379 SDDS_SetError("Unable to get matrix of rows--memory allocation failure (SDDS_GetCastMatrixOfRows)");
2380 return (NULL);
2381 }
2382 for (i = 0; i < SDDS_dataset->n_of_interest; i++)
2383 SDDS_CastValue(SDDS_dataset->data[SDDS_dataset->column_order[i]], j, SDDS_dataset->layout.column_definition[SDDS_dataset->column_order[i]].type, sddsType, (char *)data[k] + i * sizeof(double));
2384 k++;
2385 }
2386 }
2387 return (data);
2388}

◆ SDDS_GetColumn()

epicsShareFuncSDDS void * SDDS_GetColumn ( SDDS_DATASET * SDDS_dataset,
char * column_name )
extern

Retrieves a copy of the data for a specified column, including only rows marked as "of interest".

This function returns a newly allocated array containing data from the specified column for all rows that are flagged as "of interest". The data type of the returned array matches the column's data type.

For columns of type SDDS_STRING, the returned array is of type char**, with each element being a dynamically allocated string.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the data set.
column_nameNULL-terminated string specifying the name of the column to retrieve.
Returns
  • Pointer to the data array on success. The type of the array corresponds to the column's data type.
  • NULL on failure, with an error message recorded (e.g., unrecognized column name, memory allocation failure, no rows of interest).
Warning
The caller is responsible for freeing the allocated memory to avoid memory leaks. For SDDS_STRING types, each string within the array should be freed individually, followed by the array itself.
Note
  • The number of rows in the returned array can be obtained using SDDS_CountRowsOfInterest.
  • If the column's memory mode is set to DONT_TRACK_COLUMN_MEMORY_AFTER_ACCESS, the internal data may be freed after access.
See also
SDDS_GetInternalColumn, SDDS_CountRowsOfInterest, SDDS_SetRowFlags

Definition at line 611 of file SDDS_extract.c.

611 {
612 int32_t size, type, index;
613 int64_t i, j, n_rows;
614 void *data;
615 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_GetColumn"))
616 return (NULL);
617 if ((index = SDDS_GetColumnIndex(SDDS_dataset, column_name)) < 0) {
618 SDDS_SetError("Unable to get column--name is not recognized (SDDS_GetColumn)");
619 return (NULL);
620 }
621 if ((n_rows = SDDS_CountRowsOfInterest(SDDS_dataset)) <= 0) {
622 SDDS_SetError("Unable to get column--no rows left (SDDS_GetColumn)");
623 return (NULL);
624 }
625 if (!(type = SDDS_GetColumnType(SDDS_dataset, index))) {
626 SDDS_SetError("Unable to get column--data type undefined (SDDS_GetColumn)");
627 return (NULL);
628 }
629 size = SDDS_type_size[type - 1];
630 if (!(data = SDDS_Malloc(size * n_rows))) {
631 SDDS_SetError("Unable to get column--memory allocation failure (SDDS_GetColumn)");
632 return (NULL);
633 }
634 for (i = j = 0; i < SDDS_dataset->n_rows; i++) {
635 if (SDDS_dataset->row_flag[i]) {
636 if (type != SDDS_STRING)
637 memcpy((char *)data + size * j++, (char *)SDDS_dataset->data[index] + size * i, size);
638 else if (!SDDS_CopyString((char **)data + j++, ((char ***)SDDS_dataset->data)[index][i]))
639 return (NULL);
640 }
641 }
642 if (j != n_rows) {
643 SDDS_SetError("Unable to get column--row number mismatch (SDDS_GetColumn)");
644 return (NULL);
645 }
646 if (SDDS_GetColumnMemoryMode(SDDS_dataset) == DONT_TRACK_COLUMN_MEMORY_AFTER_ACCESS) {
647 SDDS_dataset->column_track_memory[index] = 0;
648 //Free internal copy now under the assumption that the program will not ask for it again.
649 if (type == SDDS_STRING) {
650 if (0) {
651 //FIX this. It currently causes a memory error in SDDS_ScanData2 with multipage files
652 char **ptr = (char **)SDDS_dataset->data[index];
653 for (i = 0; i < SDDS_dataset->n_rows_allocated; i++, ptr++)
654 if (*ptr)
655 free(*ptr);
656 free(SDDS_dataset->data[index]);
657 SDDS_dataset->data[index] = NULL;
658 }
659 } else {
660 free(SDDS_dataset->data[index]);
661 SDDS_dataset->data[index] = NULL;
662 }
663 }
664 return (data);
665}
int32_t SDDS_GetColumnMemoryMode(SDDS_DATASET *SDDS_dataset)

◆ SDDS_GetColumnDefinition()

epicsShareFuncSDDS COLUMN_DEFINITION * SDDS_GetColumnDefinition ( SDDS_DATASET * SDDS_dataset,
char * name )
extern

Retrieves the definition of a specified column from the SDDS dataset.

This function searches for a column by its name within the provided SDDS dataset. If found, it creates a copy of the column's definition and returns a pointer to it. The returned pointer should be freed by the caller using SDDS_FreeColumnDefinition to avoid memory leaks.

Parameters
[in]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
[in]nameA null-terminated string specifying the name of the column to retrieve.
Returns
On success, returns a pointer to a newly allocated COLUMN_DEFINITION structure containing the column's information. On failure (e.g., if the column is not found or a copy fails), returns NULL and records an error message.
Note
The caller is responsible for freeing the returned COLUMN_DEFINITION pointer using SDDS_FreeColumnDefinition.
See also
SDDS_CopyColumnDefinition
SDDS_FreeColumnDefinition
SDDS_SetError

Definition at line 1044 of file SDDS_utils.c.

1044 {
1045 int64_t i;
1046 COLUMN_DEFINITION *coldef;
1047 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_GetColumnDefinition"))
1048 return (NULL);
1049 if (!name) {
1050 SDDS_SetError("Unable to get column definition--name is NULL (SDDS_GetColumnDefinition)");
1051 return (NULL);
1052 }
1053 if ((i = SDDS_GetColumnIndex(SDDS_dataset, name)) < 0)
1054 return NULL;
1055 if (!SDDS_CopyColumnDefinition(&coldef, SDDS_dataset->layout.column_definition + i)) {
1056 SDDS_SetError("Unable to get column definition--copy failure (SDDS_GetColumnDefinition)");
1057 return (NULL);
1058 }
1059 return (coldef);
1060}
COLUMN_DEFINITION * SDDS_CopyColumnDefinition(COLUMN_DEFINITION **target, COLUMN_DEFINITION *source)
Creates a copy of a column definition.

◆ SDDS_GetColumnIndex()

epicsShareFuncSDDS int32_t SDDS_GetColumnIndex ( SDDS_DATASET * SDDS_dataset,
char * name )
extern

Retrieves the index of a named column in the SDDS dataset.

This function searches for a column by its name within the provided SDDS dataset and returns its index. The index can then be used with other routines for faster access to the column's data or metadata.

Parameters
[in]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
[in]nameA null-terminated string specifying the name of the column whose index is desired.
Returns
On success, returns a non-negative integer representing the index of the column. On failure (e.g., if the column is not found), returns -1 and records an error message.
See also
SDDS_GetColumnDefinition
SDDS_SetError

Definition at line 1375 of file SDDS_utils.c.

1375 {
1376 int64_t i;
1377 SORTED_INDEX key;
1378
1379 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_GetColumnIndex"))
1380 return (-1);
1381 if (!name) {
1382 SDDS_SetError("Unable to get column index--name is NULL (SDDS_GetColumnIndex)");
1383 return (-1);
1384 }
1385 key.name = name;
1386 if ((i = binaryIndexSearch((void **)SDDS_dataset->layout.column_index, SDDS_dataset->layout.n_columns, &key, SDDS_CompareIndexedNames, 0)) < 0)
1387 return -1;
1388 return SDDS_dataset->layout.column_index[i]->index;
1389}

◆ SDDS_GetColumnInDoubles()

epicsShareFuncSDDS double * SDDS_GetColumnInDoubles ( SDDS_DATASET * SDDS_dataset,
char * column_name )
extern

Retrieves the data of a specified numerical column as an array of doubles, considering only rows marked as "of interest".

This function extracts data from a specified column within the current data table of a dataset. It processes only those rows that are flagged as "of interest" (i.e., have a non-zero acceptance flag). The extracted data is returned as a newly allocated array of double values.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the data set.
column_nameNULL-terminated string specifying the name of the column from which data is to be retrieved.
Returns
  • Pointer to an array of double containing the data from the specified column for all rows marked as "of interest".
  • NULL if an error occurs (e.g., invalid dataset, unrecognized column name, non-numeric column type, memory allocation failure). In this case, an error message is recorded internally.
Warning
  • The caller is responsible for freeing the allocated memory to prevent memory leaks.
  • This function assumes that the specified column contains numerical data. Attempting to retrieve data from a non-numeric column (excluding SDDS_CHARACTER) will result in an error.
Note
  • The number of elements in the returned array corresponds to the number of rows marked as "of interest", which can be obtained using SDDS_CountRowsOfInterest.
  • If the dataset's memory mode for the column is set to DONT_TRACK_COLUMN_MEMORY_AFTER_ACCESS, the internal data for the column may be freed after access.
See also

Definition at line 872 of file SDDS_extract.c.

872 {
873 int32_t size, type, index;
874 int64_t i, j, n_rows;
875 double *data;
876 void *rawData;
877
878 j = 0;
879
880 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_GetColumnInDoubles"))
881 return (NULL);
882 if ((index = SDDS_GetColumnIndex(SDDS_dataset, column_name)) < 0) {
883 SDDS_SetError("Unable to get column--name is not recognized (SDDS_GetColumnInDoubles)");
884 return (NULL);
885 }
886 if ((n_rows = SDDS_CountRowsOfInterest(SDDS_dataset)) <= 0) {
887 SDDS_SetError("Unable to get column--no rows left (SDDS_GetColumnInDoubles)");
888 return (NULL);
889 }
890 if ((type = SDDS_GetColumnType(SDDS_dataset, index)) <= 0 || (size = SDDS_GetTypeSize(type)) <= 0 || (!SDDS_NUMERIC_TYPE(type) && type != SDDS_CHARACTER)) {
891 SDDS_SetError("Unable to get column--data size or type undefined or non-numeric (SDDS_GetColumnInDoubles)");
892 return (NULL);
893 }
894 if (!(data = (double *)SDDS_Malloc(sizeof(double) * n_rows))) {
895 SDDS_SetError("Unable to get column--memory allocation failure (SDDS_GetColumnInDoubles)");
896 return (NULL);
897 }
898 rawData = SDDS_dataset->data[index];
899 switch (type) {
900 case SDDS_LONGDOUBLE:
901 for (i = j = 0; i < SDDS_dataset->n_rows; i++) {
902 if (SDDS_dataset->row_flag[i])
903 data[j++] = ((long double *)rawData)[i];
904 }
905 break;
906 case SDDS_DOUBLE:
907 for (i = j = 0; i < SDDS_dataset->n_rows; i++) {
908 if (SDDS_dataset->row_flag[i])
909 data[j++] = ((double *)rawData)[i];
910 }
911 break;
912 case SDDS_FLOAT:
913 for (i = j = 0; i < SDDS_dataset->n_rows; i++) {
914 if (SDDS_dataset->row_flag[i])
915 data[j++] = ((float *)rawData)[i];
916 }
917 break;
918 case SDDS_LONG:
919 for (i = j = 0; i < SDDS_dataset->n_rows; i++) {
920 if (SDDS_dataset->row_flag[i])
921 data[j++] = ((int32_t *)rawData)[i];
922 }
923 break;
924 case SDDS_ULONG:
925 for (i = j = 0; i < SDDS_dataset->n_rows; i++) {
926 if (SDDS_dataset->row_flag[i])
927 data[j++] = ((uint32_t *)rawData)[i];
928 }
929 break;
930 case SDDS_LONG64:
931 for (i = j = 0; i < SDDS_dataset->n_rows; i++) {
932 if (SDDS_dataset->row_flag[i])
933 data[j++] = ((int64_t *)rawData)[i];
934 }
935 break;
936 case SDDS_ULONG64:
937 for (i = j = 0; i < SDDS_dataset->n_rows; i++) {
938 if (SDDS_dataset->row_flag[i])
939 data[j++] = ((uint64_t *)rawData)[i];
940 }
941 break;
942 case SDDS_SHORT:
943 for (i = j = 0; i < SDDS_dataset->n_rows; i++) {
944 if (SDDS_dataset->row_flag[i])
945 data[j++] = ((short *)rawData)[i];
946 }
947 break;
948 case SDDS_USHORT:
949 for (i = j = 0; i < SDDS_dataset->n_rows; i++) {
950 if (SDDS_dataset->row_flag[i])
951 data[j++] = ((unsigned short *)rawData)[i];
952 }
953 break;
954 case SDDS_CHARACTER:
955 for (i = j = 0; i < SDDS_dataset->n_rows; i++) {
956 if (SDDS_dataset->row_flag[i])
957 data[j++] = ((char *)rawData)[i];
958 }
959 break;
960 }
961 if (j != n_rows) {
962 SDDS_SetError("Unable to get column--row number mismatch (SDDS_GetColumnInDoubles)");
963 return (NULL);
964 }
965 if (SDDS_GetColumnMemoryMode(SDDS_dataset) == DONT_TRACK_COLUMN_MEMORY_AFTER_ACCESS) {
966 SDDS_dataset->column_track_memory[index] = 0;
967 //Free internal copy now under the assumption that the program will not ask for it again.
968 if (type == SDDS_STRING) {
969 if (0) {
970 //FIX this. It currently causes a memory error in SDDS_ScanData2 with multipage files
971 char **ptr = (char **)SDDS_dataset->data[index];
972 for (i = 0; i < SDDS_dataset->n_rows_allocated; i++, ptr++)
973 if (*ptr)
974 free(*ptr);
975 free(SDDS_dataset->data[index]);
976 SDDS_dataset->data[index] = NULL;
977 }
978 } else {
979 free(SDDS_dataset->data[index]);
980 SDDS_dataset->data[index] = NULL;
981 }
982 }
983 return (data);
984}

◆ SDDS_GetColumnInFloats()

epicsShareFuncSDDS float * SDDS_GetColumnInFloats ( SDDS_DATASET * SDDS_dataset,
char * column_name )
extern

Retrieves the data of a specified numerical column as an array of floats, considering only rows marked as "of interest".

This function extracts data from a specified column within the current data table of a dataset. It processes only those rows that are flagged as "of interest" (i.e., have a non-zero acceptance flag). The extracted data is returned as a newly allocated array of float values.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the data set.
column_nameNULL-terminated string specifying the name of the column from which data is to be retrieved.
Returns
  • Pointer to an array of float containing the data from the specified column for all rows marked as "of interest".
  • NULL if an error occurs (e.g., invalid dataset, unrecognized column name, non-numeric column type, memory allocation failure). In this case, an error message is recorded internally.
Warning
  • The caller is responsible for freeing the allocated memory to prevent memory leaks.
  • This function assumes that the specified column contains numerical data. Attempting to retrieve data from a non-numeric column (excluding SDDS_CHARACTER) will result in an error.
Note
  • The number of elements in the returned array corresponds to the number of rows marked as "of interest", which can be obtained using SDDS_CountRowsOfInterest.
  • If the dataset's memory mode for the column is set to DONT_TRACK_COLUMN_MEMORY_AFTER_ACCESS, the internal data for the column may be freed after access.
See also

Definition at line 1014 of file SDDS_extract.c.

1014 {
1015 int32_t size, type, index;
1016 int64_t i, j, n_rows;
1017 float *data;
1018 void *rawData;
1019
1020 j = 0;
1021
1022 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_GetColumnInFloats"))
1023 return (NULL);
1024 if ((index = SDDS_GetColumnIndex(SDDS_dataset, column_name)) < 0) {
1025 SDDS_SetError("Unable to get column--name is not recognized (SDDS_GetColumnInFloats)");
1026 return (NULL);
1027 }
1028 if ((n_rows = SDDS_CountRowsOfInterest(SDDS_dataset)) <= 0) {
1029 SDDS_SetError("Unable to get column--no rows left (SDDS_GetColumnInFloats)");
1030 return (NULL);
1031 }
1032 if ((type = SDDS_GetColumnType(SDDS_dataset, index)) <= 0 || (size = SDDS_GetTypeSize(type)) <= 0 || (!SDDS_NUMERIC_TYPE(type) && type != SDDS_CHARACTER)) {
1033 SDDS_SetError("Unable to get column--data size or type undefined or non-numeric (SDDS_GetColumnInFloats)");
1034 return (NULL);
1035 }
1036 if (!(data = (float *)SDDS_Malloc(sizeof(float) * n_rows))) {
1037 SDDS_SetError("Unable to get column--memory allocation failure (SDDS_GetColumnInFloats)");
1038 return (NULL);
1039 }
1040 rawData = SDDS_dataset->data[index];
1041 switch (type) {
1042 case SDDS_LONGDOUBLE:
1043 for (i = j = 0; i < SDDS_dataset->n_rows; i++) {
1044 if (SDDS_dataset->row_flag[i])
1045 data[j++] = ((long double *)rawData)[i];
1046 }
1047 break;
1048 case SDDS_DOUBLE:
1049 for (i = j = 0; i < SDDS_dataset->n_rows; i++) {
1050 if (SDDS_dataset->row_flag[i])
1051 data[j++] = ((double *)rawData)[i];
1052 }
1053 break;
1054 case SDDS_FLOAT:
1055 for (i = j = 0; i < SDDS_dataset->n_rows; i++) {
1056 if (SDDS_dataset->row_flag[i])
1057 data[j++] = ((float *)rawData)[i];
1058 }
1059 break;
1060 case SDDS_LONG:
1061 for (i = j = 0; i < SDDS_dataset->n_rows; i++) {
1062 if (SDDS_dataset->row_flag[i])
1063 data[j++] = ((int32_t *)rawData)[i];
1064 }
1065 break;
1066 case SDDS_ULONG:
1067 for (i = j = 0; i < SDDS_dataset->n_rows; i++) {
1068 if (SDDS_dataset->row_flag[i])
1069 data[j++] = ((uint32_t *)rawData)[i];
1070 }
1071 break;
1072 case SDDS_LONG64:
1073 for (i = j = 0; i < SDDS_dataset->n_rows; i++) {
1074 if (SDDS_dataset->row_flag[i])
1075 data[j++] = ((int64_t *)rawData)[i];
1076 }
1077 break;
1078 case SDDS_ULONG64:
1079 for (i = j = 0; i < SDDS_dataset->n_rows; i++) {
1080 if (SDDS_dataset->row_flag[i])
1081 data[j++] = ((uint64_t *)rawData)[i];
1082 }
1083 break;
1084 case SDDS_SHORT:
1085 for (i = j = 0; i < SDDS_dataset->n_rows; i++) {
1086 if (SDDS_dataset->row_flag[i])
1087 data[j++] = ((short *)rawData)[i];
1088 }
1089 break;
1090 case SDDS_USHORT:
1091 for (i = j = 0; i < SDDS_dataset->n_rows; i++) {
1092 if (SDDS_dataset->row_flag[i])
1093 data[j++] = ((unsigned short *)rawData)[i];
1094 }
1095 break;
1096 case SDDS_CHARACTER:
1097 for (i = j = 0; i < SDDS_dataset->n_rows; i++) {
1098 if (SDDS_dataset->row_flag[i])
1099 data[j++] = ((char *)rawData)[i];
1100 }
1101 break;
1102 }
1103 if (j != n_rows) {
1104 SDDS_SetError("Unable to get column--row number mismatch (SDDS_GetColumnInFloats)");
1105 return (NULL);
1106 }
1107 if (SDDS_GetColumnMemoryMode(SDDS_dataset) == DONT_TRACK_COLUMN_MEMORY_AFTER_ACCESS) {
1108 SDDS_dataset->column_track_memory[index] = 0;
1109 //Free internal copy now under the assumption that the program will not ask for it again.
1110 if (type == SDDS_STRING) {
1111 if (0) {
1112 //FIX this. It currently causes a memory error in SDDS_ScanData2 with multipage files
1113 char **ptr = (char **)SDDS_dataset->data[index];
1114 for (i = 0; i < SDDS_dataset->n_rows_allocated; i++, ptr++)
1115 if (*ptr)
1116 free(*ptr);
1117 free(SDDS_dataset->data[index]);
1118 SDDS_dataset->data[index] = NULL;
1119 }
1120 } else {
1121 free(SDDS_dataset->data[index]);
1122 SDDS_dataset->data[index] = NULL;
1123 }
1124 }
1125 return (data);
1126}

◆ SDDS_GetColumnInformation()

epicsShareFuncSDDS int32_t SDDS_GetColumnInformation ( SDDS_DATASET * SDDS_dataset,
char * field_name,
void * memory,
int32_t mode,
... )
extern

Retrieves information about a specified column in the SDDS dataset.

This function is the preferred alternative to SDDS_GetColumnDefinition. It allows you to obtain information about a specific field of a column, either by the column's name or index.

Parameters
[in]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
[in]field_nameA null-terminated string specifying the name of the field for which information is requested.
[out]memoryPointer to a variable where the retrieved information will be stored. The variable should be of type data_type*, where data_type corresponds to the type of the requested information. For STRING information, use char*. If memory is NULL, the function will verify the existence and type of the information, returning the data type without storing any data.
[in]modeSpecifies how to identify the column. Valid values are:
  • SDDS_GET_BY_NAME: Identify the column by its name. Requires an additional argument of type char* (column name).
  • SDDS_GET_BY_INDEX: Identify the column by its index. Requires an additional argument of type int32_t (column index).
Returns
On success, returns the SDDS data type of the requested information. On failure, returns zero and records an error message.
Note
This function uses variable arguments to accept either the column name or index based on the mode parameter.
See also
SDDS_GetColumnDefinition

Definition at line 41 of file SDDS_info.c.

41 {
42 int32_t field_index, type;
43 int32_t column_index;
44 COLUMN_DEFINITION *columndef;
45 char *column_name;
46 va_list argptr;
47 int32_t retval;
48
49 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_GetColumnInformation"))
50 return (0);
51
52 if (!field_name) {
53 SDDS_SetError("NULL field name passed. (SDDS_GetColumnInformation)");
54 return (0);
55 }
56
57 va_start(argptr, mode);
58 retval = 1;
59 if (mode & SDDS_GET_BY_INDEX) {
60 if ((column_index = va_arg(argptr, int32_t)) < 0 || column_index >= SDDS_dataset->layout.n_columns) {
61 SDDS_SetError("Invalid column index passed. (SDDS_GetColumnInformation)");
62 retval = 0;
63 }
64 } else {
65 if (!(column_name = va_arg(argptr, char *))) {
66 SDDS_SetError("NULL column name passed. (SDDS_GetColumnInformation)");
67 retval = 0;
68 }
69 if ((column_index = SDDS_GetColumnIndex(SDDS_dataset, column_name)) < 0) {
70 SDDS_SetError("Unknown column name given (SDDS_GetColumnInformation)");
71 retval = 0;
72 }
73 }
74 columndef = SDDS_dataset->layout.column_definition + column_index;
75 va_end(argptr);
76 if (!retval)
77 return (0);
78
79 for (field_index = 0; field_index < SDDS_COLUMN_FIELDS; field_index++)
80 if (strcmp(field_name, SDDS_ColumnFieldInformation[field_index].name) == 0)
81 break;
82 if (field_index == SDDS_COLUMN_FIELDS) {
83 SDDS_SetError("Unknown field name given (SDDS_GetColumnInformation)");
84 return (0);
85 }
86 type = SDDS_ColumnFieldInformation[field_index].type;
87 if (!memory)
88 return (type);
89 if (type == SDDS_STRING) {
90 if (!SDDS_CopyString((char **)memory, *((char **)((char *)columndef + SDDS_ColumnFieldInformation[field_index].offset)))) {
91 SDDS_SetError("Unable to copy field data (SDDS_GetColumnInformation)");
92 return (0);
93 }
94 } else
95 memcpy(memory, (char *)columndef + SDDS_ColumnFieldInformation[field_index].offset, SDDS_type_size[type - 1]);
96 return (type);
97}

◆ SDDS_GetColumnInLong()

epicsShareFuncSDDS int32_t * SDDS_GetColumnInLong ( SDDS_DATASET * SDDS_dataset,
char * column_name )
extern

Retrieves the data of a specified numerical column as an array of 32-bit integers, considering only rows marked as "of interest".

This function extracts data from a specified column within the current data table of a dataset. It processes only those rows that are flagged as "of interest" (i.e., have a non-zero acceptance flag). The extracted data is returned as a newly allocated array of int32_t values.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the data set.
column_nameNULL-terminated string specifying the name of the column from which data is to be retrieved.
Returns
  • Pointer to an array of int32_t containing the data from the specified column for all rows marked as "of interest".
  • NULL if an error occurs (e.g., invalid dataset, unrecognized column name, non-numeric column type, memory allocation failure). In this case, an error message is recorded internally.
Warning
  • The caller is responsible for freeing the allocated memory to prevent memory leaks.
  • This function assumes that the specified column contains numerical data. Attempting to retrieve data from a non-numeric column (excluding SDDS_CHARACTER) will result in an error.
Note
  • The number of elements in the returned array corresponds to the number of rows marked as "of interest", which can be obtained using SDDS_CountRowsOfInterest.
  • If the dataset's memory mode for the column is set to DONT_TRACK_COLUMN_MEMORY_AFTER_ACCESS, the internal data for the column may be freed after access.
See also

Definition at line 1157 of file SDDS_extract.c.

1157 {
1158 int32_t size, type, index;
1159 int64_t i, j, n_rows;
1160 int32_t *data;
1161 void *rawData;
1162 j = 0;
1163 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_GetColumnInLong"))
1164 return (NULL);
1165 if ((index = SDDS_GetColumnIndex(SDDS_dataset, column_name)) < 0) {
1166 SDDS_SetError("Unable to get column--name is not recognized (SDDS_GetColumnInLong)");
1167 return (NULL);
1168 }
1169 if ((n_rows = SDDS_CountRowsOfInterest(SDDS_dataset)) <= 0) {
1170 SDDS_SetError("Unable to get column--no rows left (SDDS_GetColumnInLong)");
1171 return (NULL);
1172 }
1173 if ((type = SDDS_GetColumnType(SDDS_dataset, index)) <= 0 || (size = SDDS_GetTypeSize(type)) <= 0 || (!SDDS_NUMERIC_TYPE(type) && type != SDDS_CHARACTER)) {
1174 SDDS_SetError("Unable to get column--data size or type undefined or non-numeric (SDDS_GetColumnInLong)");
1175 return (NULL);
1176 }
1177 if (!(data = (int32_t *)SDDS_Malloc(sizeof(int32_t) * n_rows))) {
1178 SDDS_SetError("Unable to get column--memory allocation failure (SDDS_GetColumnInLong)");
1179 return (NULL);
1180 }
1181 rawData = SDDS_dataset->data[index];
1182 switch (type) {
1183 case SDDS_LONGDOUBLE:
1184 for (i = j = 0; i < SDDS_dataset->n_rows; i++) {
1185 if (SDDS_dataset->row_flag[i])
1186 data[j++] = ((long double *)rawData)[i];
1187 }
1188 break;
1189 case SDDS_DOUBLE:
1190 for (i = j = 0; i < SDDS_dataset->n_rows; i++) {
1191 if (SDDS_dataset->row_flag[i])
1192 data[j++] = ((double *)rawData)[i];
1193 }
1194 break;
1195 case SDDS_FLOAT:
1196 for (i = j = 0; i < SDDS_dataset->n_rows; i++) {
1197 if (SDDS_dataset->row_flag[i])
1198 data[j++] = ((float *)rawData)[i];
1199 }
1200 break;
1201 case SDDS_LONG:
1202 for (i = j = 0; i < SDDS_dataset->n_rows; i++) {
1203 if (SDDS_dataset->row_flag[i])
1204 data[j++] = ((int32_t *)rawData)[i];
1205 }
1206 break;
1207 case SDDS_ULONG:
1208 for (i = j = 0; i < SDDS_dataset->n_rows; i++) {
1209 if (SDDS_dataset->row_flag[i])
1210 data[j++] = ((uint32_t *)rawData)[i];
1211 }
1212 break;
1213 case SDDS_LONG64:
1214 for (i = j = 0; i < SDDS_dataset->n_rows; i++) {
1215 if (SDDS_dataset->row_flag[i])
1216 data[j++] = ((int64_t *)rawData)[i];
1217 }
1218 break;
1219 case SDDS_ULONG64:
1220 for (i = j = 0; i < SDDS_dataset->n_rows; i++) {
1221 if (SDDS_dataset->row_flag[i])
1222 data[j++] = ((uint64_t *)rawData)[i];
1223 }
1224 break;
1225 case SDDS_SHORT:
1226 for (i = j = 0; i < SDDS_dataset->n_rows; i++) {
1227 if (SDDS_dataset->row_flag[i])
1228 data[j++] = ((short *)rawData)[i];
1229 }
1230 break;
1231 case SDDS_USHORT:
1232 for (i = j = 0; i < SDDS_dataset->n_rows; i++) {
1233 if (SDDS_dataset->row_flag[i])
1234 data[j++] = ((unsigned short *)rawData)[i];
1235 }
1236 break;
1237 case SDDS_CHARACTER:
1238 for (i = j = 0; i < SDDS_dataset->n_rows; i++) {
1239 if (SDDS_dataset->row_flag[i])
1240 data[j++] = ((char *)rawData)[i];
1241 }
1242 break;
1243 }
1244 if (j != n_rows) {
1245 SDDS_SetError("Unable to get column--row number mismatch (SDDS_GetColumnInLong)");
1246 return (NULL);
1247 }
1248 if (SDDS_GetColumnMemoryMode(SDDS_dataset) == DONT_TRACK_COLUMN_MEMORY_AFTER_ACCESS) {
1249 SDDS_dataset->column_track_memory[index] = 0;
1250 //Free internal copy now under the assumption that the program will not ask for it again.
1251 if (type == SDDS_STRING) {
1252 if (0) {
1253 //FIX this. It currently causes a memory error in SDDS_ScanData2 with multipage files
1254 char **ptr = (char **)SDDS_dataset->data[index];
1255 for (i = 0; i < SDDS_dataset->n_rows_allocated; i++, ptr++)
1256 if (*ptr)
1257 free(*ptr);
1258 free(SDDS_dataset->data[index]);
1259 SDDS_dataset->data[index] = NULL;
1260 }
1261 } else {
1262 free(SDDS_dataset->data[index]);
1263 SDDS_dataset->data[index] = NULL;
1264 }
1265 }
1266 return (data);
1267}

◆ SDDS_GetColumnInShort()

epicsShareFuncSDDS short * SDDS_GetColumnInShort ( SDDS_DATASET * SDDS_dataset,
char * column_name )
extern

Retrieves the data of a specified numerical column as an array of short integers, considering only rows marked as "of interest".

This function extracts data from a specified column within the current data table of a dataset. It processes only those rows that are flagged as "of interest" (i.e., have a non-zero acceptance flag). The extracted data is returned as a newly allocated array of short values.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the data set.
column_nameNULL-terminated string specifying the name of the column from which data is to be retrieved.
Returns
  • Pointer to an array of short containing the data from the specified column for all rows marked as "of interest".
  • NULL if an error occurs (e.g., invalid dataset, unrecognized column name, non-numeric column type, memory allocation failure). In this case, an error message is recorded internally.
Warning
  • The caller is responsible for freeing the allocated memory to prevent memory leaks.
  • This function assumes that the specified column contains numerical data. Attempting to retrieve data from a non-numeric column (excluding SDDS_CHARACTER) will result in an error.
Note
  • The number of elements in the returned array corresponds to the number of rows marked as "of interest", which can be obtained using SDDS_CountRowsOfInterest.
  • If the dataset's memory mode for the column is set to DONT_TRACK_COLUMN_MEMORY_AFTER_ACCESS, the internal data for the column may be freed after access.
See also

Definition at line 1298 of file SDDS_extract.c.

1298 {
1299 int32_t size, type, index;
1300 int64_t i, j, n_rows;
1301 short *data;
1302 void *rawData;
1303 j = 0;
1304 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_GetColumnInShort"))
1305 return (NULL);
1306 if ((index = SDDS_GetColumnIndex(SDDS_dataset, column_name)) < 0) {
1307 SDDS_SetError("Unable to get column--name is not recognized (SDDS_GetColumnInShort)");
1308 return (NULL);
1309 }
1310 if ((n_rows = SDDS_CountRowsOfInterest(SDDS_dataset)) <= 0) {
1311 SDDS_SetError("Unable to get column--no rows left (SDDS_GetColumnInShort)");
1312 return (NULL);
1313 }
1314 if ((type = SDDS_GetColumnType(SDDS_dataset, index)) <= 0 || (size = SDDS_GetTypeSize(type)) <= 0 || (!SDDS_NUMERIC_TYPE(type) && type != SDDS_CHARACTER)) {
1315 SDDS_SetError("Unable to get column--data size or type undefined or non-numeric (SDDS_GetColumnInShort)");
1316 return (NULL);
1317 }
1318 if (!(data = (short *)SDDS_Malloc(sizeof(short) * n_rows))) {
1319 SDDS_SetError("Unable to get column--memory allocation failure (SDDS_GetColumnInShort)");
1320 return (NULL);
1321 }
1322 rawData = SDDS_dataset->data[index];
1323 switch (type) {
1324 case SDDS_LONGDOUBLE:
1325 for (i = j = 0; i < SDDS_dataset->n_rows; i++) {
1326 if (SDDS_dataset->row_flag[i])
1327 data[j++] = ((long double *)rawData)[i];
1328 }
1329 break;
1330 case SDDS_DOUBLE:
1331 for (i = j = 0; i < SDDS_dataset->n_rows; i++) {
1332 if (SDDS_dataset->row_flag[i])
1333 data[j++] = ((double *)rawData)[i];
1334 }
1335 break;
1336 case SDDS_FLOAT:
1337 for (i = j = 0; i < SDDS_dataset->n_rows; i++) {
1338 if (SDDS_dataset->row_flag[i])
1339 data[j++] = ((float *)rawData)[i];
1340 }
1341 break;
1342 case SDDS_LONG:
1343 for (i = j = 0; i < SDDS_dataset->n_rows; i++) {
1344 if (SDDS_dataset->row_flag[i])
1345 data[j++] = ((int32_t *)rawData)[i];
1346 }
1347 break;
1348 case SDDS_ULONG:
1349 for (i = j = 0; i < SDDS_dataset->n_rows; i++) {
1350 if (SDDS_dataset->row_flag[i])
1351 data[j++] = ((uint32_t *)rawData)[i];
1352 }
1353 break;
1354 case SDDS_LONG64:
1355 for (i = j = 0; i < SDDS_dataset->n_rows; i++) {
1356 if (SDDS_dataset->row_flag[i])
1357 data[j++] = ((int64_t *)rawData)[i];
1358 }
1359 break;
1360 case SDDS_ULONG64:
1361 for (i = j = 0; i < SDDS_dataset->n_rows; i++) {
1362 if (SDDS_dataset->row_flag[i])
1363 data[j++] = ((uint64_t *)rawData)[i];
1364 }
1365 break;
1366 case SDDS_SHORT:
1367 for (i = j = 0; i < SDDS_dataset->n_rows; i++) {
1368 if (SDDS_dataset->row_flag[i])
1369 data[j++] = ((short *)rawData)[i];
1370 }
1371 break;
1372 case SDDS_USHORT:
1373 for (i = j = 0; i < SDDS_dataset->n_rows; i++) {
1374 if (SDDS_dataset->row_flag[i])
1375 data[j++] = ((unsigned short *)rawData)[i];
1376 }
1377 break;
1378 case SDDS_CHARACTER:
1379 for (i = j = 0; i < SDDS_dataset->n_rows; i++) {
1380 if (SDDS_dataset->row_flag[i])
1381 data[j++] = ((char *)rawData)[i];
1382 }
1383 break;
1384 }
1385 if (j != n_rows) {
1386 SDDS_SetError("Unable to get column--row number mismatch (SDDS_GetColumnInShort)");
1387 return (NULL);
1388 }
1389 if (SDDS_GetColumnMemoryMode(SDDS_dataset) == DONT_TRACK_COLUMN_MEMORY_AFTER_ACCESS) {
1390 SDDS_dataset->column_track_memory[index] = 0;
1391 //Free internal copy now under the assumption that the program will not ask for it again.
1392 if (type == SDDS_STRING) {
1393 if (0) {
1394 //FIX this. It currently causes a memory error in SDDS_ScanData2 with multipage files
1395 char **ptr = (char **)SDDS_dataset->data[index];
1396 for (i = 0; i < SDDS_dataset->n_rows_allocated; i++, ptr++)
1397 if (*ptr)
1398 free(*ptr);
1399 free(SDDS_dataset->data[index]);
1400 SDDS_dataset->data[index] = NULL;
1401 }
1402 } else {
1403 free(SDDS_dataset->data[index]);
1404 SDDS_dataset->data[index] = NULL;
1405 }
1406 }
1407 return (data);
1408}

◆ SDDS_GetColumnInString()

epicsShareFuncSDDS char ** SDDS_GetColumnInString ( SDDS_DATASET * SDDS_dataset,
char * column_name )
extern

Retrieves the data of a specified column as an array of strings, considering only rows marked as "of interest".

This function extracts data from a specified column within the current data table of a dataset. It processes only those rows that are flagged as "of interest" (i.e., have a non-zero acceptance flag). The extracted data is returned as a newly allocated array of char* (strings).

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the data set.
column_nameNULL-terminated string specifying the name of the column from which data is to be retrieved.
Returns
  • Pointer to an array of char* containing the data from the specified column for all rows marked as "of interest".
  • NULL if an error occurs (e.g., invalid dataset, unrecognized column name, non-string column type, memory allocation failure). In this case, an error message is recorded internally.
Warning
  • The caller is responsible for freeing the allocated memory to prevent memory leaks. Each string within the array should be freed individually, followed by the array itself.
  • This function assumes that the specified column contains string data (SDDS_STRING or SDDS_CHARACTER). Attempting to retrieve data from a non-string column will result in an error.
Note
  • The number of elements in the returned array corresponds to the number of rows marked as "of interest", which can be obtained using SDDS_CountRowsOfInterest.
  • If the dataset's memory mode for the column is set to DONT_TRACK_COLUMN_MEMORY_AFTER_ACCESS, the internal data for the column may be freed after access.
See also

Definition at line 1439 of file SDDS_extract.c.

1439 {
1440 int32_t size, type, index;
1441 int64_t i, j, n_rows;
1442 char **data;
1443 char buffer[SDDS_MAXLINE];
1444
1445 void *rawData;
1446 j = 0;
1447 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_GetColumnInString"))
1448 return (NULL);
1449 if ((index = SDDS_GetColumnIndex(SDDS_dataset, column_name)) < 0) {
1450 SDDS_SetError("Unable to get column--name is not recognized (SDDS_GetColumnInString)");
1451 return (NULL);
1452 }
1453 if ((n_rows = SDDS_CountRowsOfInterest(SDDS_dataset)) <= 0) {
1454 SDDS_SetError("Unable to get column--no rows left (SDDS_GetColumnInString)");
1455 return (NULL);
1456 }
1457
1458 if ((type = SDDS_GetColumnType(SDDS_dataset, index)) <= 0 || (size = SDDS_GetTypeSize(type)) <= 0 ||
1459 (!SDDS_NUMERIC_TYPE(type) && type != SDDS_CHARACTER && type != SDDS_STRING)) {
1460 SDDS_SetError("Unable to get column--data size or type undefined or non-numeric (SDDS_GetColumnInString)");
1461 return (NULL);
1462 }
1463 if (!(data = (char **)SDDS_Malloc(sizeof(*data) * n_rows))) {
1464 SDDS_SetError("Unable to get column--memory allocation failure (SDDS_GetColumnInString)");
1465 return (NULL);
1466 }
1467 rawData = SDDS_dataset->data[index];
1468 switch (type) {
1469 case SDDS_LONGDOUBLE:
1470 for (i = j = 0; i < SDDS_dataset->n_rows; i++) {
1471 if (SDDS_dataset->row_flag[i]) {
1472 if (LDBL_DIG == 18) {
1473 sprintf(buffer, "%22.18Le", ((long double *)rawData)[i]);
1474 } else {
1475 sprintf(buffer, "%22.15Le", ((long double *)rawData)[i]);
1476 }
1477 SDDS_CopyString(&data[j++], buffer);
1478 }
1479 }
1480 break;
1481 case SDDS_DOUBLE:
1482 for (i = j = 0; i < SDDS_dataset->n_rows; i++) {
1483 if (SDDS_dataset->row_flag[i]) {
1484 sprintf(buffer, "%22.15le", ((double *)rawData)[i]);
1485 SDDS_CopyString(&data[j++], buffer);
1486 }
1487 }
1488 break;
1489 case SDDS_FLOAT:
1490 for (i = j = 0; i < SDDS_dataset->n_rows; i++) {
1491 if (SDDS_dataset->row_flag[i]) {
1492 sprintf(buffer, "%15.8e", ((float *)rawData)[i]);
1493 SDDS_CopyString(&data[j++], buffer);
1494 }
1495 }
1496 break;
1497 case SDDS_LONG64:
1498 for (i = j = 0; i < SDDS_dataset->n_rows; i++) {
1499 if (SDDS_dataset->row_flag[i]) {
1500 sprintf(buffer, "%" PRId64, ((int64_t *)rawData)[i]);
1501 SDDS_CopyString(&data[j++], buffer);
1502 }
1503 }
1504 break;
1505 case SDDS_ULONG64:
1506 for (i = j = 0; i < SDDS_dataset->n_rows; i++) {
1507 if (SDDS_dataset->row_flag[i]) {
1508 sprintf(buffer, "%" PRIu64, ((uint64_t *)rawData)[i]);
1509 SDDS_CopyString(&data[j++], buffer);
1510 }
1511 }
1512 break;
1513 case SDDS_LONG:
1514 for (i = j = 0; i < SDDS_dataset->n_rows; i++) {
1515 if (SDDS_dataset->row_flag[i]) {
1516 sprintf(buffer, "%" PRId32, ((int32_t *)rawData)[i]);
1517 SDDS_CopyString(&data[j++], buffer);
1518 }
1519 }
1520 break;
1521 case SDDS_ULONG:
1522 for (i = j = 0; i < SDDS_dataset->n_rows; i++) {
1523 if (SDDS_dataset->row_flag[i]) {
1524 sprintf(buffer, "%" PRIu32, ((uint32_t *)rawData)[i]);
1525 SDDS_CopyString(&data[j++], buffer);
1526 }
1527 }
1528 break;
1529 case SDDS_SHORT:
1530 for (i = j = 0; i < SDDS_dataset->n_rows; i++) {
1531 if (SDDS_dataset->row_flag[i]) {
1532 sprintf(buffer, "%hd", ((short *)rawData)[i]);
1533 SDDS_CopyString(&data[j++], buffer);
1534 }
1535 }
1536 break;
1537 case SDDS_USHORT:
1538 for (i = j = 0; i < SDDS_dataset->n_rows; i++) {
1539 if (SDDS_dataset->row_flag[i]) {
1540 sprintf(buffer, "%hu", ((unsigned short *)rawData)[i]);
1541 SDDS_CopyString(&data[j++], buffer);
1542 }
1543 }
1544 break;
1545 case SDDS_CHARACTER:
1546 for (i = j = 0; i < SDDS_dataset->n_rows; i++) {
1547 if (SDDS_dataset->row_flag[i]) {
1548 sprintf(buffer, "%c", ((char *)rawData)[i]);
1549 SDDS_CopyString(&data[j++], buffer);
1550 }
1551 }
1552 break;
1553 case SDDS_STRING:
1554 for (i = j = 0; i < SDDS_dataset->n_rows; i++) {
1555 if (SDDS_dataset->row_flag[i]) {
1556 SDDS_CopyString(&data[j++], ((char **)rawData)[i]);
1557 }
1558 }
1559 break;
1560 }
1561 if (j != n_rows) {
1562 SDDS_SetError("Unable to get column--row number mismatch (SDDS_GetColumnInString)");
1563 return (NULL);
1564 }
1565 if (SDDS_GetColumnMemoryMode(SDDS_dataset) == DONT_TRACK_COLUMN_MEMORY_AFTER_ACCESS) {
1566 SDDS_dataset->column_track_memory[index] = 0;
1567 //Free internal copy now under the assumption that the program will not ask for it again.
1568 if (type == SDDS_STRING) {
1569 if (0) {
1570 //FIX this. It currently causes a memory error in SDDS_ScanData2 with multipage files
1571 char **ptr = (char **)SDDS_dataset->data[index];
1572 for (i = 0; i < SDDS_dataset->n_rows_allocated; i++, ptr++)
1573 if (*ptr)
1574 free(*ptr);
1575 free(SDDS_dataset->data[index]);
1576 SDDS_dataset->data[index] = NULL;
1577 }
1578 } else {
1579 free(SDDS_dataset->data[index]);
1580 SDDS_dataset->data[index] = NULL;
1581 }
1582 }
1583 return (data);
1584}

◆ SDDS_GetColumnMemoryMode()

epicsShareFuncSDDS int32_t SDDS_GetColumnMemoryMode ( SDDS_DATASET * SDDS_dataset)
extern

Retrieves the current column memory mode for the SDDS dataset.

Parameters
SDDS_datasetThe SDDS dataset to query.
Returns
The current column memory mode.

Definition at line 1381 of file SDDS_input.c.

1381 {
1382 return (SDDS_dataset->layout.data_mode.column_memory_mode);
1383}

◆ SDDS_GetColumnNames()

epicsShareFuncSDDS char ** SDDS_GetColumnNames ( SDDS_DATASET * SDDS_dataset,
int32_t * number )
extern

Retrieves the names of all columns in the SDDS dataset.

This function allocates and returns an array of NULL-terminated strings containing the names of the columns in the provided SDDS_dataset. It only includes columns that are flagged as of interest if column_flag is set.

Parameters
[in]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
[out]numberPointer to an int32_t variable where the number of retrieved column names will be stored.
Returns
  • Returns a pointer to an array of NULL-terminated strings containing the column names on success.
  • Returns NULL on failure (e.g., if the dataset is invalid or memory allocation fails) and records an error message.
Note
The caller is responsible for freeing the memory allocated for the returned array and its strings using SDDS_FreeStringArray or similar functions.
See also
SDDS_CheckDataset
SDDS_Malloc
SDDS_CopyString
SDDS_SetError

Definition at line 2526 of file SDDS_utils.c.

2526 {
2527 int64_t i;
2528 char **name;
2529 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_GetColumnNames"))
2530 return (NULL);
2531 *number = 0;
2532 if (!(name = (char **)SDDS_Malloc(sizeof(*name) * SDDS_dataset->layout.n_columns))) {
2533 SDDS_SetError("Unable to get column names--allocation failure (SDDS_GetColumnNames)");
2534 return (NULL);
2535 }
2536 for (i = 0; i < SDDS_dataset->layout.n_columns; i++) {
2537 if (!SDDS_dataset->column_flag || SDDS_dataset->column_flag[i]) {
2538 if (!SDDS_CopyString(name + *number, SDDS_dataset->layout.column_definition[i].name)) {
2539 free(name);
2540 return (NULL);
2541 }
2542 *number += 1;
2543 }
2544 }
2545 return (name);
2546}

◆ SDDS_GetColumnType()

epicsShareFuncSDDS int32_t SDDS_GetColumnType ( SDDS_DATASET * SDDS_dataset,
int32_t index )
extern

Retrieves the data type of a column in the SDDS dataset by its index.

This function returns the SDDS data type of the specified column within the dataset. The data type corresponds to one of the predefined SDDS type constants, such as SDDS_LONGDOUBLE, SDDS_DOUBLE, SDDS_FLOAT, etc.

Parameters
[in]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
[in]indexThe zero-based index of the column whose data type is to be retrieved. The index should be obtained from SDDS_DefineColumn or SDDS_GetColumnIndex.
Returns
On success, returns the SDDS data type of the column as an int32_t. On failure (e.g., if the index is out of range or the dataset is invalid), returns 0 and records an error message.
Note
The function does not perform type validation beyond checking the index range. It assumes that the dataset's column definitions are correctly initialized.
See also
SDDS_GetColumnIndex
SDDS_SetError

Definition at line 2219 of file SDDS_utils.c.

2219 {
2220 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_GetColumnType"))
2221 return (0);
2222 if (index < 0 || index >= SDDS_dataset->layout.n_columns) {
2223 SDDS_SetError("Unable to get column type--column index is out of range (SDDS_GetColumnType)");
2224 return (0);
2225 }
2226 return (SDDS_dataset->layout.column_definition[index].type);
2227}

◆ SDDS_GetDescription()

epicsShareFuncSDDS int32_t SDDS_GetDescription ( SDDS_DATASET * SDDS_dataset,
char ** text,
char ** contents )
extern

Retrieves the text and contents descriptions from an SDDS dataset.

This function extracts the text description and contents description from the specified SDDS dataset. The descriptions are copied into the provided pointers if they are not NULL. This allows users to obtain metadata information about the dataset's content and purpose.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
textPointer to a char* variable where the text description will be copied. If NULL, the text description is not retrieved.
contentsPointer to a char* variable where the contents description will be copied. If NULL, the contents description is not retrieved.
Returns
Returns 1 on successful retrieval of the descriptions. On failure, returns 0 and sets an appropriate error message.
Return values
1Indicates that the descriptions were successfully retrieved and copied.
0Indicates that an error occurred (e.g., invalid dataset, memory allocation failure).
Note
  • The caller is responsible for freeing the memory allocated for text and contents if they are not NULL.
  • Ensure that the dataset is properly initialized before calling this function.
See also
SDDS_SetDescription, SDDS_GetArray, SDDS_GetParameter

Definition at line 4627 of file SDDS_extract.c.

4627 {
4628 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_GetDescription"))
4629 return (0);
4630 if (text) {
4631 *text = NULL;
4632 if (!SDDS_CopyString(text, SDDS_dataset->layout.description)) {
4633 SDDS_SetError("Unable to retrieve description data (SDDS_GetDescription)");
4634 return (0);
4635 }
4636 }
4637 if (contents) {
4638 *contents = NULL;
4639 if (!SDDS_CopyString(contents, SDDS_dataset->layout.contents)) {
4640 SDDS_SetError("Unable to retrieve description data (SDDS_GetDescription)");
4641 return (0);
4642 }
4643 }
4644
4645 return (1);
4646}

◆ SDDS_GetDoubleMatrixFromColumn()

epicsShareFuncSDDS void * SDDS_GetDoubleMatrixFromColumn ( SDDS_DATASET * SDDS_dataset,
char * column_name,
int64_t dimension1,
int64_t dimension2,
int32_t mode )
extern

Extracts a matrix of doubles from a specified column in the current data table of an SDDS dataset.

This function retrieves the data from the specified column as double values and organizes it into a matrix with the given dimensions. The data is arranged in either row-major or column-major order based on the mode parameter. The function allocates memory for the matrix, which should be freed by the caller.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
column_nameA null-terminated string specifying the name of the column from which to extract the matrix.
dimension1The number of rows in the resulting matrix.
dimension2The number of columns in the resulting matrix.
modeSpecifies the data layout in the matrix. Use SDDS_ROW_MAJOR_DATA for row-major order or SDDS_COLUMN_MAJOR_DATA for column-major order.
Returns
On success, returns a pointer to the allocated matrix containing double values. The matrix is an array of pointers, where each pointer refers to a row (for row-major) or a column (for column-major) in the matrix. On failure, returns NULL and sets an appropriate error message.
Return values
NULLIndicates that an error occurred (e.g., invalid dataset, column not found, dimension mismatch, memory allocation failure).
Non-NULLPointer to the allocated matrix containing double values.
Note
The caller is responsible for freeing the allocated matrix and its contents.
See also
SDDS_GetMatrixFromColumn, SDDS_GetDoubleMatrixFromRow, SDDS_AllocateMatrix

Definition at line 3215 of file SDDS_extract.c.

3215 {
3216 int32_t size, index;
3217 int64_t n_rows, i, j;
3218 void **data, *column;
3219 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_GetDoubleMatrixFromColumn"))
3220 return (NULL);
3221 if (!column_name) {
3222 SDDS_SetError("Unable to get matrix--column name is NULL (SDDS_GetDoubleMatrixFromColumn)");
3223 return (NULL);
3224 }
3225 if ((n_rows = SDDS_CountRowsOfInterest(SDDS_dataset)) <= 0) {
3226 SDDS_SetError("Unable to get matrix--no rows selected (SDDS_GetDoubleMatrixFromColumn)");
3227 return (NULL);
3228 }
3229 if (n_rows != dimension1 * dimension2) {
3230 char s[1024];
3231 sprintf(s, "Unable to get matrix--number of rows (%" PRId64 ") doesn't correspond to given dimensions (%" PRId64 " x %" PRId64 ") (SDDS_GetDoubleMatrixFromColumn)", n_rows, dimension1, dimension2);
3232 SDDS_SetError(s);
3233 return (NULL);
3234 }
3235 if ((index = SDDS_GetColumnIndex(SDDS_dataset, column_name)) < 0) {
3236 SDDS_SetError("Unable to get matrix--column name is unrecognized (SDDS_GetDoubleMatrixFromColumn)");
3237 return (NULL);
3238 }
3239 if (!(column = SDDS_GetColumnInDoubles(SDDS_dataset, column_name))) {
3240 SDDS_SetError("Unable to get matrix (SDDS_GetDoubleMatrixFromColumn)");
3241 return (NULL);
3242 }
3243 size = sizeof(double);
3244 if (!(data = SDDS_AllocateMatrix(size, dimension1, dimension2))) {
3245 SDDS_SetError("Unable to allocate matrix (SDDS_GetDoubleMatrixFromColumn)");
3246 return (NULL);
3247 }
3248 if (mode & SDDS_ROW_MAJOR_DATA || !(mode & SDDS_COLUMN_MAJOR_DATA)) {
3249 for (i = 0; i < dimension1; i++)
3250 memcpy(data[i], (char *)column + i * dimension2 * size, dimension2 * size);
3251 } else {
3252 for (i = 0; i < dimension1; i++) {
3253 for (j = 0; j < dimension2; j++) {
3254 memcpy((char *)data[i] + size * j, (char *)column + (j * dimension1 + i) * size, size);
3255 }
3256 }
3257 }
3258
3259 free(column);
3260 return (data);
3261}
double * SDDS_GetColumnInDoubles(SDDS_DATASET *SDDS_dataset, char *column_name)
Retrieves the data of a specified numerical column as an array of doubles, considering only rows mark...
void * SDDS_AllocateMatrix(int32_t size, int64_t dim1, int64_t dim2)
Allocates a two-dimensional matrix with zero-initialized elements.

◆ SDDS_GetErrorMessages()

epicsShareFuncSDDS char ** SDDS_GetErrorMessages ( int32_t * number,
int32_t mode )
extern

Retrieves recorded error messages from the SDDS error stack.

This function fetches error messages that have been recorded by SDDS library routines. Depending on the mode parameter, it can retrieve a single error message or all recorded errors.

Parameters
[out]numberPointer to an int32_t variable where the number of retrieved error messages will be stored. If NULL, the function returns NULL.
[in]modeFlags controlling the retrieval behavior:
  • 0: Retrieve only the most recent error message.
  • SDDS_ALL_GetErrorMessages: Retrieve all recorded error messages.
Returns
A dynamically allocated array of strings containing the error messages. Returns NULL if no errors are recorded or if memory allocation fails.
Note
The caller is responsible for freeing the memory allocated for the returned error messages.
See also
SDDS_SetError
SDDS_ClearErrors

Definition at line 526 of file SDDS_utils.c.

526 {
527 int32_t i, j, depth;
528 char **message;
529
530 if (!number)
531 return NULL;
532
533 *number = 0;
534 if (!n_errors)
535 return NULL;
536
537 if (mode & SDDS_ALL_GetErrorMessages)
538 depth = n_errors;
539 else
540 depth = 1;
541 if (!(message = (char **)SDDS_Malloc(sizeof(*message) * depth)))
542 return NULL;
543 for (i = 0; i < depth; i++)
544 message[i] = NULL;
545 if (!error_description) {
546 fprintf(stderr, "warning: internal error: error_description pointer is unexpectedly NULL (SDDS_GetErrorMessages)\n");
547 free(message);
548 return NULL;
549 } else {
550 for (i = depth - 1; i >= 0; i--) {
551 if (!error_description[i]) {
552 fprintf(stderr, "internal error: error_description[%" PRId32 "] is unexpectedly NULL (SDDS_GetErrorMessages)\n", i);
553 for (j = 0; j < depth; j++)
554 free(message[j]);
555 free(message);
556 return NULL;
557 }
558 if (!SDDS_CopyString(message + i, error_description[i])) {
559 fprintf(stderr, "unable to copy error message text (SDDS_GetErrorMessages)\n");
560 for (j = 0; j < depth; j++)
561 free(message[j]);
562 free(message);
563 return NULL;
564 }
565 }
566 }
567 *number = depth;
568 return message;
569}

◆ SDDS_GetFixedValueParameter()

epicsShareFuncSDDS void * SDDS_GetFixedValueParameter ( SDDS_DATASET * SDDS_dataset,
char * parameter_name,
void * memory )
extern

Retrieves the fixed value of a specified parameter from an SDDS dataset.

This function accesses the fixed value defined for a given parameter in the dataset's layout and converts it to the appropriate data type. If the memory pointer is provided, the converted value is stored at the specified memory location. Otherwise, memory is allocated internally to hold the value, which must be freed by the caller.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
parameter_nameA null-terminated string specifying the name of the parameter whose fixed value is to be retrieved.
memoryOptional pointer to a memory location where the fixed value will be stored. The size of the memory should correspond to the size of the parameter's data type. If NULL, memory is allocated internally to hold the value.
Returns
On success, returns a pointer to the memory containing the fixed value. On failure, returns NULL and sets an appropriate error message.
Return values
NULLIndicates that an error occurred (e.g., invalid dataset, parameter not found, invalid data type, memory allocation failure, or scan failure).
Non-NULLPointer to the memory containing the fixed parameter value.
Note
The caller is responsible for freeing the allocated memory if the memory parameter is NULL.
See also
SDDS_SetParameterFixedValue, SDDS_GetParameterAsDouble, SDDS_GetParameterAsString

Definition at line 3085 of file SDDS_extract.c.

3085 {
3086 int32_t index, type, size;
3087 void *data;
3088 char s[SDDS_MAXLINE];
3089
3090 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_GetFixValueParameter"))
3091 return (NULL);
3092 if (!parameter_name) {
3093 SDDS_SetError("Unable to get parameter value--parameter name pointer is NULL (SDDS_GetFixedValueParameter)");
3094 return (NULL);
3095 }
3096 if ((index = SDDS_GetParameterIndex(SDDS_dataset, parameter_name)) < 0) {
3097 SDDS_SetError("Unable to get parameter value--parameter name is unrecognized (SDDS_GetFixedValueParameter)");
3098 return (NULL);
3099 }
3100 if (!(type = SDDS_GetParameterType(SDDS_dataset, index))) {
3101 SDDS_SetError("Unable to get parameter value--parameter data type is invalid (SDDS_GetFixedValueParameter)");
3102 return (NULL);
3103 }
3104 size = SDDS_type_size[type - 1];
3105 if (memory)
3106 data = memory;
3107 else if (!(data = SDDS_Malloc(size))) {
3108 SDDS_SetError("Unable to get parameter value--parameter data size is invalid (SDDS_GetFixedValueParameter)");
3109 return (NULL);
3110 }
3111 strcpy(s, SDDS_dataset->layout.parameter_definition[index].fixed_value);
3112 if (!SDDS_ScanData(s, type, 0, data, 0, 1)) {
3113 SDDS_SetError("Unable to retrieve fixed-value paramter--scan failed (SDDS_GetFixedValueParameter)");
3114 return (NULL);
3115 }
3116 return (data);
3117}

◆ SDDS_GetInternalColumn()

epicsShareFuncSDDS void * SDDS_GetInternalColumn ( SDDS_DATASET * SDDS_dataset,
char * column_name )
extern

Retrieves an internal pointer to the data of a specified column, including all rows.

This function returns a direct pointer to the internal data array of the specified column. Unlike SDDS_GetColumn, it includes all rows, regardless of their acceptance flags.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the data set.
column_nameNULL-terminated string specifying the name of the column to retrieve.
Returns
  • Pointer to the internal data array on success. The type of the pointer corresponds to the column's data type.
  • NULL on failure, with an error message recorded (e.g., unrecognized column name).
Warning
Modifying the data through the returned pointer affects the internal state of the dataset. Use with caution to avoid unintended side effects.
Note
  • If the column's memory mode is set to DONT_TRACK_COLUMN_MEMORY_AFTER_ACCESS, the internal data may be freed after access.
  • This function does not allocate new memory; it provides direct access to the dataset's internal structures.
See also
SDDS_GetColumn, SDDS_SetColumnFlags, SDDS_CountColumnsOfInterest

Definition at line 688 of file SDDS_extract.c.

688 {
689 int32_t index;
690 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_GetInternalColumn"))
691 return (NULL);
692 if ((index = SDDS_GetColumnIndex(SDDS_dataset, column_name)) < 0) {
693 SDDS_SetError("Unable to get column--name is not recognized (SDDS_GetInternalColumn)");
694 return (NULL);
695 }
696 if (SDDS_GetColumnMemoryMode(SDDS_dataset) == DONT_TRACK_COLUMN_MEMORY_AFTER_ACCESS) {
697 SDDS_dataset->column_track_memory[index] = 0;
698 }
699 return SDDS_dataset->data[index];
700}

◆ SDDS_GetLZMACompressionLevel()

epicsShareFuncSDDS int32_t SDDS_GetLZMACompressionLevel ( void )
extern

Definition at line 91 of file SDDS_lzma.c.

91 {
92 return SDDS_GetLockedLZMACompressionLevel();
93}

◆ SDDS_GetMatrixFromColumn()

epicsShareFuncSDDS void * SDDS_GetMatrixFromColumn ( SDDS_DATASET * SDDS_dataset,
char * column_name,
int64_t dimension1,
int64_t dimension2,
int32_t mode )
extern

Extracts a matrix from a specified column in the current data table of an SDDS dataset.

This function retrieves the data from the specified column and organizes it into a matrix with the given dimensions. The data is arranged in either row-major or column-major order based on the mode parameter. The function allocates memory for the matrix, which should be freed by the caller.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
column_nameA null-terminated string specifying the name of the column from which to extract the matrix.
dimension1The number of rows in the resulting matrix.
dimension2The number of columns in the resulting matrix.
modeSpecifies the data layout in the matrix. Use SDDS_ROW_MAJOR_DATA for row-major order or SDDS_COLUMN_MAJOR_DATA for column-major order.
Returns
On success, returns a pointer to the allocated matrix. The matrix is an array of pointers, where each pointer refers to a row (for row-major) or a column (for column-major) in the matrix. On failure, returns NULL and sets an appropriate error message.
Return values
NULLIndicates that an error occurred (e.g., invalid dataset, column not found, dimension mismatch, memory allocation failure).
Non-NULLPointer to the allocated matrix.
Note
The caller is responsible for freeing the allocated matrix and its contents.
See also
SDDS_GetDoubleMatrixFromColumn, SDDS_GetMatrixFromRow, SDDS_AllocateMatrix

Definition at line 3143 of file SDDS_extract.c.

3143 {
3144 int32_t size, type, index;
3145 int64_t n_rows, i, j;
3146 void **data, *column;
3147 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_GetMatrixFromColumn"))
3148 return (NULL);
3149 if (!column_name) {
3150 SDDS_SetError("Unable to get matrix--column name is NULL (SDDS_GetMatrixFromColumn)");
3151 return (NULL);
3152 }
3153 if ((n_rows = SDDS_CountRowsOfInterest(SDDS_dataset)) <= 0) {
3154 SDDS_SetError("Unable to get matrix--no rows selected (SDDS_GetMatrixFromColumn)");
3155 return (NULL);
3156 }
3157 if (n_rows != dimension1 * dimension2) {
3158 char s[1024];
3159 sprintf(s, "Unable to get matrix--number of rows (%" PRId64 ") doesn't correspond to given dimensions (%" PRId64 " x %" PRId64 ") (SDDS_GetMatrixFromColumn)", n_rows, dimension1, dimension2);
3160 SDDS_SetError(s);
3161 return (NULL);
3162 }
3163 if ((index = SDDS_GetColumnIndex(SDDS_dataset, column_name)) < 0 || (type = SDDS_GetColumnType(SDDS_dataset, index)) < 0 || (size = SDDS_GetTypeSize(type)) <= 0) {
3164 SDDS_SetError("Unable to get matrix--column name is unrecognized (SDDS_GetMatrixFromColumn)");
3165 return (NULL);
3166 }
3167 if (!(column = SDDS_GetColumn(SDDS_dataset, column_name))) {
3168 SDDS_SetError("Unable to get matrix (SDDS_GetMatrixFromColumn)");
3169 return (NULL);
3170 }
3171 if (!(data = SDDS_AllocateMatrix(size, dimension1, dimension2))) {
3172 SDDS_SetError("Unable to allocate matrix (SDDS_GetMatrixFromColumn)");
3173 return (NULL);
3174 }
3175 if (mode & SDDS_ROW_MAJOR_DATA || !(mode & SDDS_COLUMN_MAJOR_DATA)) {
3176 for (i = 0; i < dimension1; i++)
3177 memcpy(data[i], (char *)column + i * dimension2 * size, dimension2 * size);
3178 } else {
3179 for (i = 0; i < dimension1; i++) {
3180 for (j = 0; j < dimension2; j++) {
3181 memcpy((char *)data[i] + size * j, (char *)column + (j * dimension1 + i) * size, size);
3182 }
3183 }
3184 }
3185
3186 free(column);
3187 return (data);
3188}
void * SDDS_GetColumn(SDDS_DATASET *SDDS_dataset, char *column_name)
Retrieves a copy of the data for a specified column, including only rows marked as "of interest".

◆ SDDS_GetMatrixOfRows()

epicsShareFuncSDDS void * SDDS_GetMatrixOfRows ( SDDS_DATASET * SDDS_dataset,
int64_t * n_rows )
extern

Retrieves all rows marked as "of interest" as a matrix (array of row arrays).

This function extracts all rows that are flagged as "of interest" within the current data table of a dataset. It processes only those columns that are flagged as "of interest" and returns the data as a matrix, where each row is an array of values corresponding to the selected columns.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the data set.
n_rowsPointer to an int64_t variable where the number of rows retrieved will be stored.
Returns
  • Pointer to an array of pointers, where each pointer references a row's data array.
  • NULL if an error occurs (e.g., invalid dataset, no columns selected, inconsistent row types, memory allocation failure). In this case, an error message is recorded internally.
Warning
  • The caller is responsible for freeing the allocated memory to prevent memory leaks. This includes freeing each individual row array followed by the array of pointers itself.
  • All selected columns must have the same data type. If there is an inconsistency, the function will fail.
Note
  • The number of rows retrieved is stored in the variable pointed to by n_rows.
  • For columns containing string data (SDDS_STRING), each element in the row arrays is a dynamically allocated string that must be freed individually.
  • If the dataset's memory mode for the columns is set to DONT_TRACK_COLUMN_MEMORY_AFTER_ACCESS, the internal data for the columns may be freed after access.
See also

Definition at line 2267 of file SDDS_extract.c.

2267 {
2268 void **data;
2269 int32_t size, type;
2270 int64_t i, j, k;
2271 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_GetMatrixOfRows"))
2272 return (NULL);
2273 if (SDDS_dataset->n_of_interest <= 0) {
2274 SDDS_SetError("Unable to get matrix of rows--no columns selected (SDDS_GetMatrixOfRows)");
2275 return (NULL);
2276 }
2277 if (!SDDS_CheckTabularData(SDDS_dataset, "SDDS_GetMatrixOfRows"))
2278 return (NULL);
2279 if ((type = SDDS_GetRowType(SDDS_dataset)) <= 0) {
2280 SDDS_SetError("Unable to get row--inconsistent data type in selected columns (SDDS_GetMatrixOfRows)");
2281 return (NULL);
2282 }
2283 size = SDDS_type_size[type - 1];
2284 if ((*n_rows = SDDS_CountRowsOfInterest(SDDS_dataset)) <= 0) {
2285 SDDS_SetError("Unable to get matrix of rows--no rows of interest (SDDS_GetMatrixOfRows)");
2286 return (NULL);
2287 }
2288 if (!(data = (void **)SDDS_Malloc(sizeof(*data) * (*n_rows)))) {
2289 SDDS_SetError("Unable to get matrix of rows--memory allocation failure (SDDS_GetMatrixOfRows)");
2290 return (NULL);
2291 }
2292 for (j = k = 0; j < SDDS_dataset->n_rows; j++) {
2293 if (SDDS_dataset->row_flag[j]) {
2294 if (!(data[k] = SDDS_Malloc(size * SDDS_dataset->n_of_interest))) {
2295 SDDS_SetError("Unable to get matrix of rows--memory allocation failure (SDDS_GetMatrixOfRows)");
2296 return (NULL);
2297 }
2298 if (type != SDDS_STRING)
2299 for (i = 0; i < SDDS_dataset->n_of_interest; i++)
2300 memcpy((char *)data[k] + i * size, (char *)SDDS_dataset->data[SDDS_dataset->column_order[i]] + j * size, size);
2301 else
2302 for (i = 0; i < SDDS_dataset->n_of_interest; i++)
2303 if (!SDDS_CopyString((char **)(data[k]) + i, ((char **)SDDS_dataset->data[SDDS_dataset->column_order[i]])[j]))
2304 return (NULL);
2305 k++;
2306 }
2307 }
2308 return (data);
2309}
int32_t SDDS_GetRowType(SDDS_DATASET *SDDS_dataset)
Determines the data type of the rows based on selected columns in the current data table.

◆ SDDS_GetNamedArrayType()

epicsShareFuncSDDS int32_t SDDS_GetNamedArrayType ( SDDS_DATASET * SDDS_dataset,
char * name )
extern

Retrieves the data type of an array in the SDDS dataset by its name.

This function searches for an array by its name within the dataset and returns its SDDS data type. The data type corresponds to one of the predefined SDDS type constants, such as SDDS_LONGDOUBLE, SDDS_DOUBLE, SDDS_FLOAT, etc.

Parameters
[in]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
[in]nameA null-terminated string specifying the name of the array whose data type is to be retrieved.
Returns
On success, returns the SDDS data type of the array as an int32_t. On failure (e.g., if the array name is not found or the dataset is invalid), returns 0 and records an error message.
Note
The function internally uses SDDS_GetArrayIndex to find the array's index before retrieving its type.
See also
SDDS_GetArrayIndex
SDDS_SetError

Definition at line 2293 of file SDDS_utils.c.

2293 {
2294 int32_t index;
2295 if ((index = SDDS_GetArrayIndex(SDDS_dataset, name)) < 0 || index >= SDDS_dataset->layout.n_arrays) {
2296 SDDS_SetError("Unable to get array type--array index is out of range (SDDS_GetNamedArrayType)");
2297 return (0);
2298 }
2299 return (SDDS_dataset->layout.array_definition[index].type);
2300}

◆ SDDS_GetNamedColumnType()

epicsShareFuncSDDS int32_t SDDS_GetNamedColumnType ( SDDS_DATASET * SDDS_dataset,
char * name )
extern

Retrieves the data type of a column in the SDDS dataset by its name.

This function searches for a column by its name within the dataset and returns its SDDS data type. The data type corresponds to one of the predefined SDDS type constants, such as SDDS_LONGDOUBLE, SDDS_DOUBLE, SDDS_FLOAT, etc.

Parameters
[in]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
[in]nameA null-terminated string specifying the name of the column whose data type is to be retrieved.
Returns
On success, returns the SDDS data type of the column as an int32_t. On failure (e.g., if the column name is not found or the dataset is invalid), returns 0 and records an error message.
Note
The function internally uses SDDS_GetColumnIndex to find the column's index before retrieving its type.
See also
SDDS_GetColumnIndex
SDDS_SetError

Definition at line 2244 of file SDDS_utils.c.

2244 {
2245 int64_t index;
2246 if ((index = SDDS_GetColumnIndex(SDDS_dataset, name)) < 0 || index >= SDDS_dataset->layout.n_columns) {
2247 SDDS_SetError("Unable to get column type--column index is out of range (SDDS_GetNamedColumnType)");
2248 return (0);
2249 }
2250 return (SDDS_dataset->layout.column_definition[index].type);
2251}

◆ SDDS_GetNamedParameterType()

epicsShareFuncSDDS int32_t SDDS_GetNamedParameterType ( SDDS_DATASET * SDDS_dataset,
char * name )
extern

Retrieves the data type of a parameter in the SDDS dataset by its name.

This function searches for a parameter by its name within the dataset and returns its SDDS data type. The data type corresponds to one of the predefined SDDS type constants, such as SDDS_LONGDOUBLE, SDDS_DOUBLE, SDDS_FLOAT, etc.

Parameters
[in]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
[in]nameA null-terminated string specifying the name of the parameter whose data type is to be retrieved.
Returns
On success, returns the SDDS data type of the parameter as an int32_t. On failure (e.g., if the parameter name is not found or the dataset is invalid), returns 0 and records an error message.
Note
The function internally uses SDDS_GetParameterIndex to find the parameter's index before retrieving its type.
See also
SDDS_GetParameterIndex
SDDS_SetError

Definition at line 2342 of file SDDS_utils.c.

2342 {
2343 int32_t index;
2344 if ((index = SDDS_GetParameterIndex(SDDS_dataset, name)) < 0 || index >= SDDS_dataset->layout.n_parameters) {
2345 SDDS_SetError("Unable to get parameter type--parameter index is out of range (SDDS_GetNamedParameterType)");
2346 return (0);
2347 }
2348 return (SDDS_dataset->layout.parameter_definition[index].type);
2349}

◆ SDDS_GetNumericColumn()

epicsShareFuncSDDS void * SDDS_GetNumericColumn ( SDDS_DATASET * SDDS_dataset,
char * column_name,
int32_t desiredType )
extern

Retrieves the data of a specified numerical column as an array of a desired numerical type, considering only rows marked as "of interest".

This function extracts data from a specified column within the current data table of a dataset. It processes only those rows that are flagged as "of interest" (i.e., have a non-zero acceptance flag). The extracted data is returned as a newly allocated array of the specified numerical type.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the data set.
column_nameNULL-terminated string specifying the name of the column from which data is to be retrieved.
desiredTypeInteger constant representing the desired data type for the returned array. Must be one of the supported SDDS numerical types (e.g., SDDS_DOUBLE, SDDS_FLOAT, etc.).
Returns
  • Pointer to an array of the desired numerical type containing the data from the specified column for all rows marked as "of interest".
  • NULL if an error occurs (e.g., invalid dataset, unrecognized column name, non-numeric column type, memory allocation failure, type casting failure). In this case, an error message is recorded internally.
Warning
  • The caller is responsible for freeing the allocated memory to prevent memory leaks.
  • This function assumes that the specified column contains numerical data. Attempting to retrieve data from a non-numeric column (excluding SDDS_CHARACTER) will result in an error.
Note
  • The number of elements in the returned array corresponds to the number of rows marked as "of interest", which can be obtained using SDDS_CountRowsOfInterest.
  • If the dataset's memory mode for the column is set to DONT_TRACK_COLUMN_MEMORY_AFTER_ACCESS, the internal data for the column may be freed after access.
  • If the desiredType matches the column's data type, this function internally calls SDDS_GetColumn. Otherwise, it performs type casting using SDDS_CastValue.
See also

Definition at line 1618 of file SDDS_extract.c.

1618 {
1619 int32_t size, type, desiredTypeSize, index;
1620 int64_t i, j, n_rows;
1621 void *data;
1622 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_GetNumericColumn"))
1623 return (NULL);
1624 if (!SDDS_NUMERIC_TYPE(desiredType) && desiredType != SDDS_CHARACTER) {
1625 SDDS_SetError("Unable to get column--desired type is nonnumeric (SDDS_GetNumericColumn)");
1626 return (NULL);
1627 }
1628 if ((index = SDDS_GetColumnIndex(SDDS_dataset, column_name)) < 0) {
1629 SDDS_SetError("Unable to get column--name is not recognized (SDDS_GetNumericColumn)");
1630 return (NULL);
1631 }
1632 if ((type = SDDS_GetColumnType(SDDS_dataset, index)) <= 0 || (size = SDDS_GetTypeSize(type)) <= 0 || (!SDDS_NUMERIC_TYPE(type) && type != SDDS_CHARACTER)) {
1633 SDDS_SetError("Unable to get column--data size or type undefined or non-numeric (SDDS_GetNumericColumn)");
1634 return (NULL);
1635 }
1636 if (type == desiredType)
1637 return SDDS_GetColumn(SDDS_dataset, column_name);
1638 if ((n_rows = SDDS_CountRowsOfInterest(SDDS_dataset)) <= 0) {
1639 SDDS_SetError("Unable to get column--no rows left (SDDS_GetNumericColumn)");
1640 return (NULL);
1641 }
1642 if (!(data = (void *)SDDS_Malloc((desiredTypeSize = SDDS_GetTypeSize(desiredType)) * n_rows))) {
1643 SDDS_SetError("Unable to get column--memory allocation failure (SDDS_GetNumericColumn)");
1644 return (NULL);
1645 }
1646 for (i = j = 0; i < SDDS_dataset->n_rows; i++) {
1647 if (SDDS_dataset->row_flag[i] && !SDDS_CastValue(SDDS_dataset->data[index], i, type, desiredType, (char *)data + desiredTypeSize * j++)) {
1648 SDDS_SetError("Unable to get column--cast to double failed (SDDS_GetNumericColumn)");
1649 return (NULL);
1650 }
1651 }
1652 if (j != n_rows) {
1653 SDDS_SetError("Unable to get column--row number mismatch (SDDS_GetNumericColumn)");
1654 return (NULL);
1655 }
1656 if (SDDS_GetColumnMemoryMode(SDDS_dataset) == DONT_TRACK_COLUMN_MEMORY_AFTER_ACCESS) {
1657 SDDS_dataset->column_track_memory[index] = 0;
1658 //Free internal copy now under the assumption that the program will not ask for it again.
1659 if (type == SDDS_STRING) {
1660 if (0) {
1661 //FIX this. It currently causes a memory error in SDDS_ScanData2 with multipage files
1662 char **ptr = (char **)SDDS_dataset->data[index];
1663 for (i = 0; i < SDDS_dataset->n_rows_allocated; i++, ptr++)
1664 if (*ptr)
1665 free(*ptr);
1666 free(SDDS_dataset->data[index]);
1667 SDDS_dataset->data[index] = NULL;
1668 }
1669 } else {
1670 free(SDDS_dataset->data[index]);
1671 SDDS_dataset->data[index] = NULL;
1672 }
1673 }
1674 return (data);
1675}

◆ SDDS_GetParameter()

epicsShareFuncSDDS void * SDDS_GetParameter ( SDDS_DATASET * SDDS_dataset,
char * parameter_name,
void * memory )
extern

Retrieves the value of a specified parameter from the current data table of a data set.

This function accesses the value of a specific parameter (identified by its name) within the current data table of a dataset. The retrieved value is either copied into user-provided memory or returned as a direct pointer to the internal data.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the data set.
parameter_nameNULL-terminated string specifying the name of the parameter from which the value is to be retrieved.
memoryPointer to user-allocated memory where the retrieved parameter value will be stored. If NULL, the function allocates memory.
Returns
  • Pointer to the retrieved parameter value stored in memory (if provided) or to newly allocated memory.
  • NULL if an error occurs (e.g., invalid dataset, unrecognized parameter name, undefined data type, memory allocation failure, string copy failure). In this case, an error message is recorded internally.
Warning
  • If memory is NULL, the function allocates memory that the caller must free to prevent memory leaks.
  • For parameters containing string data (SDDS_STRING), the function copies the string into memory. A typical usage would involve passing a pointer to a char* variable. c char *string; SDDS_GetParameter(&SDDS_dataset, "parameter_name", &string); // or string = *(char**)SDDS_GetParameter(&SDDS_dataset, "parameter_name", NULL);
Note
  • The size of the allocated memory corresponds to the parameter's data type, which can be obtained using SDDS_GetParameterType.
  • If the dataset's memory mode for the parameter is set to DONT_TRACK_PARAMETER_MEMORY_AFTER_ACCESS, the internal data for the parameter may be freed after access.
See also

Definition at line 2482 of file SDDS_extract.c.

2482 {
2483 int32_t index, type, size;
2484 char s[SDDS_MAXLINE];
2485 void *data;
2486 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_GetParameter"))
2487 return (NULL);
2488 if (!parameter_name) {
2489 SDDS_SetError("Unable to get parameter value--parameter name pointer is NULL (SDDS_GetParameter)");
2490 return (NULL);
2491 }
2492 if ((index = SDDS_GetParameterIndex(SDDS_dataset, parameter_name)) < 0) {
2493 sprintf(s, "Unable to get parameter value--parameter name %s is unrecognized (SDDS_GetParameter)", parameter_name);
2494 SDDS_SetError(s);
2495 return (NULL);
2496 }
2497 if (!(type = SDDS_GetParameterType(SDDS_dataset, index))) {
2498 SDDS_SetError("Unable to get parameter value--parameter data type is invalid (SDDS_GetParameter)");
2499 return (NULL);
2500 }
2501 if (!SDDS_dataset->parameter || !SDDS_dataset->parameter[index]) {
2502 SDDS_SetError("Unable to get parameter value--parameter data array is NULL (SDDS_GetParameter)");
2503 return (NULL);
2504 }
2505 size = SDDS_type_size[type - 1];
2506 if (memory)
2507 data = memory;
2508 else if (!(data = SDDS_Malloc(size))) {
2509 SDDS_SetError("Unable to get parameter value--parameter data size is invalid (SDDS_GetParameter)");
2510 return (NULL);
2511 }
2512 if (type != SDDS_STRING)
2513 memcpy(data, SDDS_dataset->parameter[index], size);
2514 else if (!SDDS_CopyString((char **)data, *(char **)SDDS_dataset->parameter[index]))
2515 return (NULL);
2516 return (data);
2517}

◆ SDDS_GetParameterAsDouble()

epicsShareFuncSDDS double * SDDS_GetParameterAsDouble ( SDDS_DATASET * SDDS_dataset,
char * parameter_name,
double * memory )
extern

Retrieves the value of a specified parameter as a double from the current data table of an SDDS dataset.

This function searches for the parameter by name within the provided SDDS dataset and retrieves its value as a double. If the memory pointer is supplied, the value is stored at the specified memory location. If memory is NULL, the function allocates memory for storing the value, which should be freed by the caller.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
parameter_nameA null-terminated string specifying the name of the parameter to retrieve.
memoryOptional pointer to a double variable where the parameter value will be stored. If NULL, memory is allocated internally to hold the value.
Returns
On success, returns a pointer to the double containing the parameter value. On failure, returns NULL and sets an appropriate error message.
Return values
NULLIndicates that an error occurred (e.g., invalid dataset, parameter not found, type mismatch, or memory allocation failure).
Non-NULLPointer to the double containing the parameter value.
Note
The caller is responsible for freeing the allocated memory if the memory parameter is NULL.
See also
SDDS_GetParameterAsLong64, SDDS_GetParameterAsLongDouble, SDDS_GetParameterAsString

Definition at line 2783 of file SDDS_extract.c.

2783 {
2784 int32_t index = -1, type = -1;
2785 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_GetParameterAsDouble"))
2786 return (NULL);
2787 if (!parameter_name) {
2788 SDDS_SetError("Unable to get parameter value--parameter name pointer is NULL (SDDS_GetParameterAsDouble)");
2789 return (NULL);
2790 }
2791 if ((index = SDDS_GetParameterIndex(SDDS_dataset, parameter_name)) < 0) {
2792 SDDS_SetError("Unable to get parameter value--parameter name is unrecognized (SDDS_GetParameterAsDouble)");
2793 return (NULL);
2794 }
2795 if (!(type = SDDS_GetParameterType(SDDS_dataset, index))) {
2796 SDDS_SetError("Unable to get parameter value--parameter data type is invalid (SDDS_GetParameterAsDouble)");
2797 return (NULL);
2798 }
2799 if (type == SDDS_STRING) {
2800 SDDS_SetError("Unable to get parameter value--parameter data type is SDDS_STRING (SDDS_GetParameterAsDouble)");
2801 return (NULL);
2802 }
2803 if (!SDDS_dataset->parameter || !SDDS_dataset->parameter[index]) {
2804 SDDS_SetError("Unable to get parameter value--parameter data array is NULL (SDDS_GetParameterAsDouble)");
2805 return (NULL);
2806 }
2807
2808 if (!memory && !(memory = (double *)SDDS_Malloc(sizeof(double)))) {
2809 SDDS_SetError("Unable to get parameter value--memory allocation failure (SDDS_GetParameterAsDouble)");
2810 return (NULL);
2811 }
2812 *memory = SDDS_ConvertToDouble(type, SDDS_dataset->parameter[index], 0);
2813 return (memory);
2814}
double SDDS_ConvertToDouble(int32_t type, void *data, int64_t index)
Converts a value to double based on its type.
Definition SDDS_rpn.c:199

◆ SDDS_GetParameterAsFormattedString()

epicsShareFuncSDDS char * SDDS_GetParameterAsFormattedString ( SDDS_DATASET * SDDS_dataset,
char * parameter_name,
char ** memory,
char * suppliedformat )
extern

Retrieves the value of a specified parameter as a formatted string from the current data table of an SDDS dataset.

This function searches for the parameter by name within the provided SDDS dataset, formats its value based on the supplied format string, and returns it as a null-terminated string. If suppliedformat is NULL, the function uses the format string defined in the parameter's definition. If the memory pointer is provided, the formatted string is stored at the specified memory location. Otherwise, memory is allocated internally to hold the string, which must be freed by the caller.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
parameter_nameA null-terminated string specifying the name of the parameter to retrieve.
memoryOptional pointer to a char* variable where the formatted string will be stored. If NULL, memory is allocated internally to hold the string.
suppliedformatA null-terminated format string (similar to printf format specifiers) to format the parameter value. If NULL, the function uses the format string defined in the parameter's definition within the dataset.
Returns
On success, returns a pointer to the null-terminated formatted string containing the parameter value. On failure, returns NULL and sets an appropriate error message.
Return values
NULLIndicates that an error occurred (e.g., invalid dataset, parameter not found, invalid format string, type mismatch, memory allocation failure, or unknown data type).
Non-NULLPointer to the null-terminated string containing the formatted parameter value.
Note
The caller is responsible for freeing the allocated memory if the memory parameter is NULL.
See also
SDDS_GetParameterAsDouble, SDDS_GetParameterAsString, SDDS_GetParameterAsLong64, SDDS_GetParameterAsLongDouble

Definition at line 2936 of file SDDS_extract.c.

2936 {
2937 int32_t index, type;
2938 char buffer[SDDS_MAXLINE], *parValue;
2939 void *value;
2940 char *format = NULL;
2941
2942 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_GetParameterAsFormattedString"))
2943 return (NULL);
2944 if (!parameter_name) {
2945 SDDS_SetError("Unable to get parameter value--parameter name pointer is NULL (SDDS_GetParameterAsFormattedString)");
2946 return (NULL);
2947 }
2948 if ((index = SDDS_GetParameterIndex(SDDS_dataset, parameter_name)) < 0) {
2949 SDDS_SetError("Unable to get parameter value--parameter name is unrecognized (SDDS_GetParameterAsFormattedString)");
2950 return (NULL);
2951 }
2952 if (!(type = SDDS_GetParameterType(SDDS_dataset, index))) {
2953 SDDS_SetError("Unable to get parameter value--parameter data type is invalid (SDDS_GetParameterAsFormattedString)");
2954 return (NULL);
2955 }
2956 if (suppliedformat != NULL) {
2957 format = suppliedformat;
2958 if (!SDDS_VerifyPrintfFormat(format, type)) {
2959 SDDS_SetError("Unable to get parameter value--given format for parameter is invalid (SDDS_GetParameterAsFormattedString)");
2960 return (NULL);
2961 }
2962 } else {
2963 if (SDDS_GetParameterInformation(SDDS_dataset, "format_string", &format, SDDS_GET_BY_INDEX, index) != SDDS_STRING) {
2964 SDDS_SetError("Unable to get parameter value--parameter definition is invalid (SDDS_GetParameterAsFormattedString)");
2965 return (NULL);
2966 }
2967 }
2968 value = SDDS_dataset->parameter[index];
2969
2970 if (!SDDS_StringIsBlank(format)) {
2971 switch (type) {
2972 case SDDS_LONGDOUBLE:
2973 sprintf(buffer, format, *(long double *)value);
2974 break;
2975 case SDDS_DOUBLE:
2976 sprintf(buffer, format, *(double *)value);
2977 break;
2978 case SDDS_FLOAT:
2979 sprintf(buffer, format, *(float *)value);
2980 break;
2981 case SDDS_LONG64:
2982 sprintf(buffer, format, *(int64_t *)value);
2983 break;
2984 case SDDS_ULONG64:
2985 sprintf(buffer, format, *(uint64_t *)value);
2986 break;
2987 case SDDS_LONG:
2988 sprintf(buffer, format, *(int32_t *)value);
2989 break;
2990 case SDDS_ULONG:
2991 sprintf(buffer, format, *(uint32_t *)value);
2992 break;
2993 case SDDS_SHORT:
2994 sprintf(buffer, format, *(short *)value);
2995 break;
2996 case SDDS_USHORT:
2997 sprintf(buffer, format, *(unsigned short *)value);
2998 break;
2999 case SDDS_CHARACTER:
3000 sprintf(buffer, format, *(char *)value);
3001 break;
3002 case SDDS_STRING:
3003 sprintf(buffer, format, *(char **)value);
3004 break;
3005 default:
3006 SDDS_SetError("Unknown data type of parameter (SDDS_GetParameterAsFormattedString)");
3007 return (NULL);
3008 }
3009 } else {
3010 switch (type) {
3011 case SDDS_LONGDOUBLE:
3012 if (LDBL_DIG == 18) {
3013 sprintf(buffer, "%22.18Le", *(long double *)value);
3014 } else {
3015 sprintf(buffer, "%22.15Le", *(long double *)value);
3016 }
3017 break;
3018 case SDDS_DOUBLE:
3019 sprintf(buffer, "%22.15le", *(double *)value);
3020 break;
3021 case SDDS_FLOAT:
3022 sprintf(buffer, "%15.8e", *(float *)value);
3023 break;
3024 case SDDS_LONG64:
3025 sprintf(buffer, "%" PRId64, *(int64_t *)value);
3026 break;
3027 case SDDS_ULONG64:
3028 sprintf(buffer, "%" PRIu64, *(uint64_t *)value);
3029 break;
3030 case SDDS_LONG:
3031 sprintf(buffer, "%" PRId32, *(int32_t *)value);
3032 break;
3033 case SDDS_ULONG:
3034 sprintf(buffer, "%" PRIu32, *(uint32_t *)value);
3035 break;
3036 case SDDS_SHORT:
3037 sprintf(buffer, "%hd", *(short *)value);
3038 break;
3039 case SDDS_USHORT:
3040 sprintf(buffer, "%hu", *(unsigned short *)value);
3041 break;
3042 case SDDS_CHARACTER:
3043 sprintf(buffer, "%c", *(char *)value);
3044 break;
3045 case SDDS_STRING:
3046 sprintf(buffer, "%s", *(char **)value);
3047 break;
3048 default:
3049 SDDS_SetError("Unknown data type of parameter (SDDS_GetParameterAsFormattedString)");
3050 return (NULL);
3051 }
3052 }
3053 if (!(parValue = malloc(sizeof(char) * (strlen(buffer) + 1)))) {
3054 SDDS_SetError("Unable to get parameter value--memory allocation failure (SDDS_GetParameterAsFormattedString)");
3055 return (NULL);
3056 }
3057 strcpy(parValue, buffer);
3058 if (memory)
3059 *memory = parValue;
3060 return parValue;
3061}

◆ SDDS_GetParameterAsLong()

epicsShareFuncSDDS int32_t * SDDS_GetParameterAsLong ( SDDS_DATASET * SDDS_dataset,
char * parameter_name,
int32_t * memory )
extern

Retrieves the value of a specified parameter as a 32-bit integer from the current data table of a data set.

This function accesses the value of a specific parameter (identified by its name) within the current data table of a dataset and converts it to a 32-bit integer (int32_t). The converted value is either stored in user-provided memory or allocated by the function.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the data set.
parameter_nameNULL-terminated string specifying the name of the parameter from which the value is to be retrieved.
memoryPointer to a 32-bit integer where the converted parameter value will be stored. If NULL, the function allocates memory.
Returns
  • Pointer to the int32_t value stored in memory (if provided) or to newly allocated memory containing the converted value.
  • NULL if an error occurs (e.g., invalid dataset, unrecognized parameter name, undefined data type, memory allocation failure, parameter type is SDDS_STRING). In this case, an error message is recorded internally.
Warning
  • If memory is NULL, the function allocates memory that the caller must free to prevent memory leaks.
  • This function does not support parameters of type SDDS_STRING. Attempting to retrieve string parameters as long integers will result in an error.
Note
  • The conversion is performed using SDDS_ConvertToLong, which handles casting from various numerical types to int32_t.
  • Ensure that the parameter's data type is compatible with 32-bit integer conversion to avoid data loss or undefined behavior.
See also

Definition at line 2616 of file SDDS_extract.c.

2616 {
2617 int32_t index, type;
2618 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_GetParameterAsLong"))
2619 return (NULL);
2620 if (!parameter_name) {
2621 SDDS_SetError("Unable to get parameter value--parameter name pointer is NULL (SDDS_GetParameterAsLong)");
2622 return (NULL);
2623 }
2624 if ((index = SDDS_GetParameterIndex(SDDS_dataset, parameter_name)) < 0) {
2625 SDDS_SetError("Unable to get parameter value--parameter name is unrecognized (SDDS_GetParameterAsLong)");
2626 return (NULL);
2627 }
2628 if (!(type = SDDS_GetParameterType(SDDS_dataset, index))) {
2629 SDDS_SetError("Unable to get parameter value--parameter data type is invalid (SDDS_GetParameterAsLong)");
2630 return (NULL);
2631 }
2632 if (type == SDDS_STRING) {
2633 SDDS_SetError("Unable to get parameter value--parameter data type is SDDS_STRING (SDDS_GetParameterAsLong)");
2634 return (NULL);
2635 }
2636 if (!SDDS_dataset->parameter || !SDDS_dataset->parameter[index]) {
2637 SDDS_SetError("Unable to get parameter value--parameter data array is NULL (SDDS_GetParameterAsLong)");
2638 return (NULL);
2639 }
2640
2641 if (!memory && !(memory = (int32_t *)SDDS_Malloc(sizeof(int32_t)))) {
2642 SDDS_SetError("Unable to get parameter value--memory allocation failure (SDDS_GetParameterAsLong)");
2643 return (NULL);
2644 }
2645
2646 *memory = SDDS_ConvertToLong(type, SDDS_dataset->parameter[index], 0);
2647 return (memory);
2648}
int32_t SDDS_ConvertToLong(int32_t type, void *data, int64_t index)
Converts a value to a 32-bit integer based on its type.
Definition SDDS_rpn.c:279

◆ SDDS_GetParameterAsLong64()

epicsShareFuncSDDS int64_t * SDDS_GetParameterAsLong64 ( SDDS_DATASET * SDDS_dataset,
char * parameter_name,
int64_t * memory )
extern

Retrieves the value of a specified parameter as a 64-bit integer from the current data table of an SDDS dataset.

This function looks up the parameter by name within the given SDDS dataset and returns its value as an int64_t. If the memory pointer is provided, the value is stored at the given memory location. Otherwise, the function allocates memory to store the value, which must be freed by the caller.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
parameter_nameA null-terminated string specifying the name of the parameter to retrieve.
memoryOptional pointer to an int64_t variable where the parameter value will be stored. If NULL, memory is allocated internally to hold the value.
Returns
On success, returns a pointer to the int64_t containing the parameter value. On failure, returns NULL and sets an appropriate error message.
Return values
NULLIndicates that an error occurred (e.g., invalid dataset, parameter not found, type mismatch, or memory allocation failure).
Non-NULLPointer to the int64_t containing the parameter value.
Note
The caller is responsible for freeing the allocated memory if the memory parameter is NULL.
See also
SDDS_GetParameterAsDouble, SDDS_GetParameterAsString

Definition at line 2672 of file SDDS_extract.c.

2672 {
2673 int32_t index, type;
2674 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_GetParameterAsLong64"))
2675 return (NULL);
2676 if (!parameter_name) {
2677 SDDS_SetError("Unable to get parameter value--parameter name pointer is NULL (SDDS_GetParameterAsLong64)");
2678 return (NULL);
2679 }
2680 if ((index = SDDS_GetParameterIndex(SDDS_dataset, parameter_name)) < 0) {
2681 SDDS_SetError("Unable to get parameter value--parameter name is unrecognized (SDDS_GetParameterAsLong64)");
2682 return (NULL);
2683 }
2684 if (!(type = SDDS_GetParameterType(SDDS_dataset, index))) {
2685 SDDS_SetError("Unable to get parameter value--parameter data type is invalid (SDDS_GetParameterAsLong64)");
2686 return (NULL);
2687 }
2688 if (type == SDDS_STRING) {
2689 SDDS_SetError("Unable to get parameter value--parameter data type is SDDS_STRING (SDDS_GetParameterAsLong64)");
2690 return (NULL);
2691 }
2692 if (!SDDS_dataset->parameter || !SDDS_dataset->parameter[index]) {
2693 SDDS_SetError("Unable to get parameter value--parameter data array is NULL (SDDS_GetParameterAsLong64)");
2694 return (NULL);
2695 }
2696
2697 if (!memory && !(memory = (int64_t *)SDDS_Malloc(sizeof(int64_t)))) {
2698 SDDS_SetError("Unable to get parameter value--memory allocation failure (SDDS_GetParameterAsLong64)");
2699 return (NULL);
2700 }
2701
2702 *memory = SDDS_ConvertToLong64(type, SDDS_dataset->parameter[index], 0);
2703 return (memory);
2704}
int64_t SDDS_ConvertToLong64(int32_t type, void *data, int64_t index)
Converts a value to a 64-bit integer based on its type.
Definition SDDS_rpn.c:239

◆ SDDS_GetParameterAsLongDouble()

epicsShareFuncSDDS long double * SDDS_GetParameterAsLongDouble ( SDDS_DATASET * SDDS_dataset,
char * parameter_name,
long double * memory )
extern

Retrieves the value of a specified parameter as a long double from the current data table of an SDDS dataset.

This function searches for the parameter by name within the provided SDDS dataset and retrieves its value as a long double. If the memory pointer is supplied, the value is stored at the specified memory location. If memory is NULL, the function allocates memory for storing the value, which should be freed by the caller.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
parameter_nameA null-terminated string specifying the name of the parameter to retrieve.
memoryOptional pointer to a long double variable where the parameter value will be stored. If NULL, memory is allocated internally to hold the value.
Returns
On success, returns a pointer to the long double containing the parameter value. On failure, returns NULL and sets an appropriate error message.
Return values
NULLIndicates that an error occurred (e.g., invalid dataset, parameter not found, type mismatch, or memory allocation failure).
Non-NULLPointer to the long double containing the parameter value.
Note
The caller is responsible for freeing the allocated memory if the memory parameter is NULL.
See also
SDDS_GetParameterAsDouble, SDDS_GetParameterAsLong64, SDDS_GetParameterAsString

Definition at line 2728 of file SDDS_extract.c.

2728 {
2729 int32_t index = -1, type = -1;
2730 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_GetParameterAsLongDouble"))
2731 return (NULL);
2732 if (!parameter_name) {
2733 SDDS_SetError("Unable to get parameter value--parameter name pointer is NULL (SDDS_GetParameterAsLongDouble)");
2734 return (NULL);
2735 }
2736 if ((index = SDDS_GetParameterIndex(SDDS_dataset, parameter_name)) < 0) {
2737 SDDS_SetError("Unable to get parameter value--parameter name is unrecognized (SDDS_GetParameterAsLongDouble)");
2738 return (NULL);
2739 }
2740 if (!(type = SDDS_GetParameterType(SDDS_dataset, index))) {
2741 SDDS_SetError("Unable to get parameter value--parameter data type is invalid (SDDS_GetParameterAsLongDouble)");
2742 return (NULL);
2743 }
2744 if (type == SDDS_STRING) {
2745 SDDS_SetError("Unable to get parameter value--parameter data type is SDDS_STRING (SDDS_GetParameterAsLongDouble)");
2746 return (NULL);
2747 }
2748 if (!SDDS_dataset->parameter || !SDDS_dataset->parameter[index]) {
2749 SDDS_SetError("Unable to get parameter value--parameter data array is NULL (SDDS_GetParameterAsLongDouble)");
2750 return (NULL);
2751 }
2752
2753 if (!memory && !(memory = (long double *)SDDS_Malloc(sizeof(long double)))) {
2754 SDDS_SetError("Unable to get parameter value--memory allocation failure (SDDS_GetParameterAsLongDouble)");
2755 return (NULL);
2756 }
2757 *memory = SDDS_ConvertToLongDouble(type, SDDS_dataset->parameter[index], 0);
2758 return (memory);
2759}
long double SDDS_ConvertToLongDouble(int32_t type, void *data, int64_t index)
Converts a value to long double based on its type.
Definition SDDS_rpn.c:159

◆ SDDS_GetParameterAsString()

epicsShareFuncSDDS char * SDDS_GetParameterAsString ( SDDS_DATASET * SDDS_dataset,
char * parameter_name,
char ** memory )
extern

Retrieves the value of a specified parameter as a string from the current data table of an SDDS dataset.

This function searches for the parameter by name within the provided SDDS dataset and retrieves its value as a string. The function formats the parameter's value based on its data type. If the memory pointer is provided, the string is stored at the specified memory location. Otherwise, the function allocates memory to hold the string, which must be freed by the caller.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
parameter_nameA null-terminated string specifying the name of the parameter to retrieve.
memoryOptional pointer to a char* variable where the string will be stored. If NULL, memory is allocated internally to hold the string.
Returns
On success, returns a pointer to the null-terminated string containing the parameter value. On failure, returns NULL and sets an appropriate error message.
Return values
NULLIndicates that an error occurred (e.g., invalid dataset, parameter not found, type mismatch, memory allocation failure, or unknown data type).
Non-NULLPointer to the null-terminated string containing the parameter value.
Note
The caller is responsible for freeing the allocated memory if the memory parameter is NULL.
See also
SDDS_GetParameterAsDouble, SDDS_GetParameterAsLong64, SDDS_GetParameterAsLongDouble

Definition at line 2839 of file SDDS_extract.c.

2839 {
2840 int32_t index, type;
2841 char buffer[SDDS_MAXLINE], *parValue;
2842 void *value;
2843
2844 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_GetParameterAsString"))
2845 return (NULL);
2846 if (!parameter_name) {
2847 SDDS_SetError("Unable to get parameter value--parameter name pointer is NULL (SDDS_GetParameterAsString)");
2848 return (NULL);
2849 }
2850 if ((index = SDDS_GetParameterIndex(SDDS_dataset, parameter_name)) < 0) {
2851 SDDS_SetError("Unable to get parameter value--parameter name is unrecognized (SDDS_GetParameterAsString)");
2852 return (NULL);
2853 }
2854 if (!(type = SDDS_GetParameterType(SDDS_dataset, index))) {
2855 SDDS_SetError("Unable to get parameter value--parameter data type is invalid (SDDS_GetParameterAsString)");
2856 return (NULL);
2857 }
2858 value = SDDS_dataset->parameter[index];
2859 switch (type) {
2860 case SDDS_LONGDOUBLE:
2861 if (LDBL_DIG == 18) {
2862 sprintf(buffer, "%.18Le", *(long double *)value);
2863 } else {
2864 sprintf(buffer, "%.15Le", *(long double *)value);
2865 }
2866 break;
2867 case SDDS_DOUBLE:
2868 sprintf(buffer, "%.15le", *(double *)value);
2869 break;
2870 case SDDS_FLOAT:
2871 sprintf(buffer, "%.8e", *(float *)value);
2872 break;
2873 case SDDS_LONG64:
2874 sprintf(buffer, "%" PRId64, *(int64_t *)value);
2875 break;
2876 case SDDS_ULONG64:
2877 sprintf(buffer, "%" PRIu64, *(uint64_t *)value);
2878 break;
2879 case SDDS_LONG:
2880 sprintf(buffer, "%" PRId32, *(int32_t *)value);
2881 break;
2882 case SDDS_ULONG:
2883 sprintf(buffer, "%" PRIu32, *(uint32_t *)value);
2884 break;
2885 case SDDS_SHORT:
2886 sprintf(buffer, "%hd", *(short *)value);
2887 break;
2888 case SDDS_USHORT:
2889 sprintf(buffer, "%hu", *(unsigned short *)value);
2890 break;
2891 case SDDS_CHARACTER:
2892 sprintf(buffer, "%c", *(char *)value);
2893 break;
2894 case SDDS_STRING:
2895 sprintf(buffer, "%s", *(char **)value);
2896 break;
2897 default:
2898 SDDS_SetError("Unknown data type of parameter (SDDS_GetParameterAsString)");
2899 return (NULL);
2900 }
2901 if (!(parValue = malloc(sizeof(char) * (strlen(buffer) + 1)))) {
2902 SDDS_SetError("Unable to get parameter value--memory allocation failure (SDDS_GetParameterAsString)");
2903 return (NULL);
2904 }
2905 strcpy(parValue, buffer);
2906 if (memory)
2907 *memory = parValue;
2908 return parValue;
2909}

◆ SDDS_GetParameterByIndex()

epicsShareFuncSDDS void * SDDS_GetParameterByIndex ( SDDS_DATASET * SDDS_dataset,
int32_t index,
void * memory )
extern

Retrieves the value of a specified parameter by its index from the current data table of a data set.

This function accesses the value of a specific parameter (identified by its index) within the current data table of a dataset. The retrieved value is either copied into user-provided memory or returned as a direct pointer to the internal data.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the data set.
indexZero-based index of the parameter to retrieve. Must be within the range [0, n_parameters-1].
memoryPointer to user-allocated memory where the retrieved parameter value will be stored. If NULL, the function allocates memory.
Returns
  • Pointer to the retrieved parameter value stored in memory (if provided) or to newly allocated memory.
  • NULL if an error occurs (e.g., invalid dataset, parameter index out of range, undefined data type, memory allocation failure, string copy failure). In this case, an error message is recorded internally.
Warning
  • If memory is NULL, the function allocates memory that the caller must free to prevent memory leaks.
  • For parameters containing string data (SDDS_STRING), the function copies the string into memory. A typical usage would involve passing a pointer to a char* variable. c char *string; SDDS_GetParameterByIndex(&SDDS_dataset, index, &string); // or string = *(char**)SDDS_GetParameterByIndex(&SDDS_dataset, index, NULL);
Note
  • The size of the allocated memory corresponds to the parameter's data type, which can be obtained using SDDS_GetParameterType.
  • If the dataset's memory mode for the parameter is set to DONT_TRACK_PARAMETER_MEMORY_AFTER_ACCESS, the internal data for the parameter may be freed after access.
See also

Definition at line 2555 of file SDDS_extract.c.

2555 {
2556 int32_t type, size;
2557 void *data;
2558 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_GetParameter"))
2559 return (NULL);
2560 if (index < 0 || index >= SDDS_dataset->layout.n_parameters) {
2561 SDDS_SetError("Unable to get parameter value--parameter index is invalid (SDDS_GetParameterByIndex)");
2562 return (NULL);
2563 }
2564 if (!(type = SDDS_GetParameterType(SDDS_dataset, index))) {
2565 SDDS_SetError("Unable to get parameter value--parameter data type is invalid (SDDS_GetParameterByIndex)");
2566 return (NULL);
2567 }
2568 if (!SDDS_dataset->parameter || !SDDS_dataset->parameter[index]) {
2569 SDDS_SetError("Unable to get parameter value--parameter data array is NULL (SDDS_GetParameterByIndex)");
2570 return (NULL);
2571 }
2572 size = SDDS_type_size[type - 1];
2573 if (memory)
2574 data = memory;
2575 else if (!(data = SDDS_Malloc(size))) {
2576 SDDS_SetError("Unable to get parameter value--parameter data size is invalid (SDDS_GetParameterByIndex)");
2577 return (NULL);
2578 }
2579 if (type != SDDS_STRING)
2580 memcpy(data, SDDS_dataset->parameter[index], size);
2581 else if (!SDDS_CopyString((char **)data, *(char **)SDDS_dataset->parameter[index]))
2582 return (NULL);
2583 return (data);
2584}

◆ SDDS_GetParameterDefinition()

epicsShareFuncSDDS PARAMETER_DEFINITION * SDDS_GetParameterDefinition ( SDDS_DATASET * SDDS_dataset,
char * name )
extern

Retrieves the definition of a specified parameter from the SDDS dataset.

This function searches for a parameter by its name within the provided SDDS dataset. If found, it creates a copy of the parameter's definition and returns a pointer to it. The returned pointer should be freed by the caller using SDDS_FreeParameterDefinition to avoid memory leaks.

Parameters
[in]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
[in]nameA null-terminated string specifying the name of the parameter to retrieve.
Returns
On success, returns a pointer to a newly allocated PARAMETER_DEFINITION structure containing the parameter's information. On failure (e.g., if the parameter is not found or a copy fails), returns NULL and records an error message.
Note
The caller is responsible for freeing the returned PARAMETER_DEFINITION pointer using SDDS_FreeParameterDefinition.
See also
SDDS_CopyParameterDefinition
SDDS_FreeParameterDefinition
SDDS_SetError

Definition at line 1141 of file SDDS_utils.c.

1141 {
1142 int32_t i;
1143 PARAMETER_DEFINITION *pardef;
1144 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_GetParameterDefinition"))
1145 return (NULL);
1146 if (!name) {
1147 SDDS_SetError("Unable to get parameter definition--name is NULL (SDDS_GetParameterDefinition)");
1148 return (NULL);
1149 }
1150 if ((i = SDDS_GetParameterIndex(SDDS_dataset, name)) < 0)
1151 return NULL;
1152 if (!SDDS_CopyParameterDefinition(&pardef, SDDS_dataset->layout.parameter_definition + i)) {
1153 SDDS_SetError("Unable to get parameter definition--copy failure (SDDS_GetParameterDefinition)");
1154 return (NULL);
1155 }
1156 return (pardef);
1157}
PARAMETER_DEFINITION * SDDS_CopyParameterDefinition(PARAMETER_DEFINITION **target, PARAMETER_DEFINITION *source)
Creates a copy of a parameter definition.

◆ SDDS_GetParameterIndex()

epicsShareFuncSDDS int32_t SDDS_GetParameterIndex ( SDDS_DATASET * SDDS_dataset,
char * name )
extern

Retrieves the index of a named parameter in the SDDS dataset.

This function searches for a parameter by its name within the provided SDDS dataset and returns its index. The index can then be used with other routines for faster access to the parameter's data or metadata.

Parameters
[in]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
[in]nameA null-terminated string specifying the name of the parameter whose index is desired.
Returns
On success, returns a non-negative integer representing the index of the parameter. On failure (e.g., if the parameter is not found), returns -1 and records an error message.
See also
SDDS_GetParameterDefinition
SDDS_SetError

Definition at line 1404 of file SDDS_utils.c.

1404 {
1405 int32_t i;
1406 SORTED_INDEX key;
1407
1408 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_GetParameterIndex"))
1409 return (-1);
1410 if (!name) {
1411 SDDS_SetError("Unable to get parameter index--name is NULL (SDDS_GetParameterIndex)");
1412 return (-1);
1413 }
1414 key.name = name;
1415 if ((i = binaryIndexSearch((void **)SDDS_dataset->layout.parameter_index, SDDS_dataset->layout.n_parameters, &key, SDDS_CompareIndexedNames, 0)) < 0)
1416 return -1;
1417 return SDDS_dataset->layout.parameter_index[i]->index;
1418}

◆ SDDS_GetParameterInformation()

epicsShareFuncSDDS int32_t SDDS_GetParameterInformation ( SDDS_DATASET * SDDS_dataset,
char * field_name,
void * memory,
int32_t mode,
... )
extern

Retrieves information about a specified parameter in the SDDS dataset.

This function is the preferred alternative to SDDS_GetParameterDefinition. It allows you to obtain information about a specific field of a parameter, either by the parameter's name or index.

Parameters
[in]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
[in]field_nameA null-terminated string specifying the name of the field for which information is requested.
[out]memoryPointer to a variable where the retrieved information will be stored. The variable should be of type data_type*, where data_type corresponds to the type of the requested information. For STRING information, use char*. If memory is NULL, the function will verify the existence and type of the information, returning the data type without storing any data.
[in]modeSpecifies how to identify the parameter. Valid values are:
  • SDDS_GET_BY_NAME: Identify the parameter by its name. Requires an additional argument of type char* (parameter name).
  • SDDS_GET_BY_INDEX: Identify the parameter by its index. Requires an additional argument of type int32_t (parameter index).
Returns
On success, returns the SDDS data type of the requested information. On failure, returns zero and records an error message.
Note
This function uses variable arguments to accept either the parameter name or index based on the mode parameter.
See also
SDDS_GetParameterDefinition

Definition at line 117 of file SDDS_info.c.

117 {
118 int32_t field_index, type, parameter_index;
119 PARAMETER_DEFINITION *parameterdef;
120 char *parameter_name;
121 va_list argptr;
122 int32_t retval;
123
124 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_GetParameterInformation"))
125 return (0);
126
127 if (!field_name) {
128 SDDS_SetError("NULL field name passed. (SDDS_GetParameterInformation)");
129 return (0);
130 }
131
132 va_start(argptr, mode);
133 retval = 1;
134 if (mode & SDDS_GET_BY_INDEX) {
135 if ((parameter_index = va_arg(argptr, int32_t)) < 0 || parameter_index >= SDDS_dataset->layout.n_parameters) {
136 SDDS_SetError("Invalid parameter index passed. (SDDS_GetParameterInformation)");
137 retval = 0;
138 }
139 } else {
140 if (!(parameter_name = va_arg(argptr, char *))) {
141 SDDS_SetError("NULL parameter name passed. (SDDS_GetParameterInformation)");
142 retval = 0;
143 }
144 if ((parameter_index = SDDS_GetParameterIndex(SDDS_dataset, parameter_name)) < 0) {
145 SDDS_SetError("Unknown parameter name given (SDDS_GetParameterInformation)");
146 retval = 0;
147 }
148 }
149 parameterdef = SDDS_dataset->layout.parameter_definition + parameter_index;
150 va_end(argptr);
151 if (!retval)
152 return (0);
153
154 for (field_index = 0; field_index < SDDS_PARAMETER_FIELDS; field_index++)
155 if (strcmp(field_name, SDDS_ParameterFieldInformation[field_index].name) == 0)
156 break;
157 if (field_index == SDDS_PARAMETER_FIELDS) {
158 SDDS_SetError("Unknown field name given (SDDS_GetParameterInformation)");
159 return (0);
160 }
161 type = SDDS_ParameterFieldInformation[field_index].type;
162 if (!memory)
163 return (type);
164 if (type == SDDS_STRING) {
165 if (!SDDS_CopyString((char **)memory, *((char **)((char *)parameterdef + SDDS_ParameterFieldInformation[field_index].offset)))) {
166 SDDS_SetError("Unable to copy field data (SDDS_GetParameterInformation)");
167 return (0);
168 }
169 } else
170 memcpy(memory, (char *)parameterdef + SDDS_ParameterFieldInformation[field_index].offset, SDDS_type_size[type - 1]);
171 return (type);
172}

◆ SDDS_GetParameterNames()

epicsShareFuncSDDS char ** SDDS_GetParameterNames ( SDDS_DATASET * SDDS_dataset,
int32_t * number )
extern

Retrieves the names of all parameters in the SDDS dataset.

This function allocates and returns an array of NULL-terminated strings containing the names of the parameters in the provided SDDS_dataset.

Parameters
[in]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
[out]numberPointer to an int32_t variable where the number of retrieved parameter names will be stored.
Returns
  • Returns a pointer to an array of NULL-terminated strings containing the parameter names on success.
  • Returns NULL on failure (e.g., if the dataset is invalid or memory allocation fails) and records an error message.
Note
The caller is responsible for freeing the memory allocated for the returned array and its strings using SDDS_FreeStringArray or similar functions.
See also
SDDS_CheckDataset
SDDS_Malloc
SDDS_CopyString
SDDS_SetError

Definition at line 2567 of file SDDS_utils.c.

2567 {
2568 int32_t i;
2569 char **name;
2570 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_GetParameterNames"))
2571 return (NULL);
2572 *number = SDDS_dataset->layout.n_parameters;
2573 if (!(name = (char **)SDDS_Malloc(sizeof(*name) * SDDS_dataset->layout.n_parameters))) {
2574 SDDS_SetError("Unable to get parameter names--allocation failure (SDDS_GetParameterNames)");
2575 return (NULL);
2576 }
2577 for (i = 0; i < SDDS_dataset->layout.n_parameters; i++) {
2578 if (!SDDS_CopyString(name + i, SDDS_dataset->layout.parameter_definition[i].name)) {
2579 free(name);
2580 return (NULL);
2581 }
2582 }
2583 return (name);
2584}

◆ SDDS_GetParameters()

epicsShareFuncSDDS int32_t SDDS_GetParameters ( SDDS_DATASET * SDDS_dataset,
... )
extern

Retrieves multiple parameter values from the current data table of a data set.

This variadic function allows the retrieval of multiple parameter values in a single call. Each parameter's name and corresponding memory location are provided as pairs of arguments.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the data set.
...Variable arguments consisting of pairs of:
  • char *parameter_name: NULL-terminated string specifying the name of the parameter.
  • void *memory: Pointer to memory where the parameter's value will be stored. If NULL, the function will fail for that parameter.
  • The argument list should be terminated when parameter_name is NULL.
Returns
  • 1 on successful retrieval of all specified parameters.
  • 0 if any parameter retrieval fails. An error message is recorded for the first failure encountered.
Warning
  • The function expects an even number of arguments (pairs of parameter names and memory pointers). An odd number may result in undefined behavior.
  • Ensure that the memory pointers provided are of appropriate types and have sufficient space to hold the parameter values.
Note
  • To terminate the argument list, pass a NULL as the parameter name. c SDDS_GetParameters(&SDDS_dataset, "param1", &value1, "param2", &value2, NULL);
See also

Definition at line 2421 of file SDDS_extract.c.

2421 {
2422 va_list argptr;
2423 char *name;
2424 void *data;
2425 int32_t retval;
2426 char s[SDDS_MAXLINE];
2427
2428 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_GetParameters"))
2429 return 0;
2430 va_start(argptr, SDDS_dataset);
2431 retval = 1;
2432 do {
2433 if (!(name = va_arg(argptr, char *)))
2434 break;
2435 if (!(data = va_arg(argptr, void *)))
2436 retval = 0;
2437 if (!SDDS_GetParameter(SDDS_dataset, name, data)) {
2438 sprintf(s, "Unable to get value of parameter %s (SDDS_GetParameters)", name);
2439 SDDS_SetError(s);
2440 }
2441 } while (retval);
2442 va_end(argptr);
2443 return retval;
2444}
void * SDDS_GetParameter(SDDS_DATASET *SDDS_dataset, char *parameter_name, void *memory)
Retrieves the value of a specified parameter from the current data table of a data set.

◆ SDDS_GetParameterType()

epicsShareFuncSDDS int32_t SDDS_GetParameterType ( SDDS_DATASET * SDDS_dataset,
int32_t index )
extern

Retrieves the data type of a parameter in the SDDS dataset by its index.

This function returns the SDDS data type of the specified parameter within the dataset. The data type corresponds to one of the predefined SDDS type constants, such as SDDS_LONGDOUBLE, SDDS_DOUBLE, SDDS_FLOAT, etc.

Parameters
[in]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
[in]indexThe zero-based index of the parameter whose data type is to be retrieved. The index should be obtained from SDDS_DefineParameter or SDDS_GetParameterIndex.
Returns
On success, returns the SDDS data type of the parameter as an int32_t. On failure (e.g., if the index is out of range or the dataset is invalid), returns 0 and records an error message.
Note
The function does not perform type validation beyond checking the index range. It assumes that the dataset's parameter definitions are correctly initialized.
See also
SDDS_GetParameterIndex
SDDS_SetError

Definition at line 2317 of file SDDS_utils.c.

2317 {
2318 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_GetParameterType"))
2319 return (0);
2320 if (index < 0 || index >= SDDS_dataset->layout.n_parameters) {
2321 SDDS_SetError("Unable to get parameter type--parameter index is out of range (SDDS_GetParameterType)");
2322 return (0);
2323 }
2324 return (SDDS_dataset->layout.parameter_definition[index].type);
2325}

◆ SDDS_GetRow()

epicsShareFuncSDDS void * SDDS_GetRow ( SDDS_DATASET * SDDS_dataset,
int64_t srow_index,
void * memory )
extern

Retrieves the data of a specific selected row as an array, considering only columns marked as "of interest".

This function extracts data from a specific selected row (identified by its selected row index among rows marked as "of interest") within the current data table of a dataset. It processes only those columns that are flagged as "of interest" and returns the row's data as a newly allocated array or stores it in user-provided memory.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the data set.
srow_indexZero-based index representing the position of the selected row among all rows marked as "of interest".
memoryPointer to user-allocated memory where the retrieved row data will be stored. If NULL, the function allocates memory.
Returns
  • Pointer to the retrieved row data array stored in memory (if provided) or to newly allocated memory.
  • NULL if an error occurs (e.g., invalid dataset, row index out of range, inconsistent row types, memory allocation failure). In this case, an error message is recorded internally.
Warning
  • If memory is NULL, the function allocates memory that the caller must free to prevent memory leaks.
  • All selected columns must have the same data type. If there is an inconsistency, the function will fail.
  • For columns containing string data (SDDS_STRING), each element in the returned array is a dynamically allocated string that must be freed individually, followed by the array itself.
Note
  • The number of elements in the returned array corresponds to the number of columns marked as "of interest", which can be obtained using SDDS_CountColumnsOfInterest.
  • If the dataset's memory mode for the columns is set to DONT_TRACK_COLUMN_MEMORY_AFTER_ACCESS, the internal data for the columns may be freed after access.
See also

Definition at line 2202 of file SDDS_extract.c.

2202 {
2203 void *data;
2204 int32_t size, type;
2205 int64_t i, row_index;
2206
2207 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_GetRow"))
2208 return (NULL);
2209 if ((row_index = SDDS_GetSelectedRowIndex(SDDS_dataset, srow_index)) < 0) {
2210 SDDS_SetError("Unable to get row--row index out of range (SDDS_GetRow)");
2211 return (NULL);
2212 }
2213 if (SDDS_dataset->n_of_interest <= 0) {
2214 SDDS_SetError("Unable to get row--no columns selected (SDDS_GetRow)");
2215 return (NULL);
2216 }
2217 if ((type = SDDS_GetRowType(SDDS_dataset)) <= 0) {
2218 SDDS_SetError("Unable to get row--inconsistent data type in selected columns (SDDS_GetRow)");
2219 return (NULL);
2220 }
2221 size = SDDS_type_size[type - 1];
2222 if (memory)
2223 data = memory;
2224 else if (!(data = SDDS_Malloc(size * SDDS_dataset->n_of_interest))) {
2225 SDDS_SetError("Unable to get row--memory allocation failure (SDDS_GetRow)");
2226 return (NULL);
2227 }
2228 if (type != SDDS_STRING)
2229 for (i = 0; i < SDDS_dataset->n_of_interest; i++)
2230 memcpy((char *)data + i * size, (char *)SDDS_dataset->data[SDDS_dataset->column_order[i]] + row_index * size, size);
2231 else
2232 for (i = 0; i < SDDS_dataset->n_of_interest; i++)
2233 if (!SDDS_CopyString((char **)data + i, ((char **)SDDS_dataset->data[SDDS_dataset->column_order[i]])[row_index]))
2234 return (NULL);
2235 return (data);
2236}
int64_t SDDS_GetSelectedRowIndex(SDDS_DATASET *SDDS_dataset, int64_t srow_index)
Retrieves the actual row index corresponding to a selected row position within the current data table...

◆ SDDS_GetRowFlag()

epicsShareFuncSDDS int32_t SDDS_GetRowFlag ( SDDS_DATASET * SDDS_dataset,
int64_t row )
extern

Retrieves the acceptance flag of a specific row in the current data table.

This function fetches the acceptance flag for a given row. The flag indicates whether the row is "of interest" (non-zero) or rejected (zero).

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the data set.
rowIndex of the row whose flag is to be retrieved. Must be within the range [0, n_rows-1].
Returns
  • Non-negative integer representing the flag value of the specified row.
  • -1 if the dataset is invalid or the row index is out of bounds.
See also
SDDS_SetRowFlags, SDDS_GetRowFlags

Definition at line 71 of file SDDS_extract.c.

71 {
72 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_GetRowFlag"))
73 return -1;
74 if (row < 0 || row >= SDDS_dataset->n_rows)
75 return -1;
76 return SDDS_dataset->row_flag[row];
77}

◆ SDDS_GetRowFlags()

epicsShareFuncSDDS int32_t SDDS_GetRowFlags ( SDDS_DATASET * SDDS_dataset,
int32_t * flag,
int64_t rows )
extern

Retrieves the acceptance flags for all rows in the current data table.

This function copies the acceptance flags of each row into a provided array. Each flag indicates whether the corresponding row is "of interest" (non-zero) or rejected (zero).

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the data set.
flagPointer to an integer array where the row flags will be stored. The array must have at least rows elements.
rowsNumber of rows to retrieve flags for. Typically, this should match the total number of rows in the data table.
Returns
  • 1 on successful retrieval of all row flags.
  • 0 on failure, with an error message recorded (e.g., if row count mismatches).
Note
Ensure that the flag array is adequately allocated to hold the flags for all specified rows.
See also
SDDS_SetRowFlags, SDDS_GetRowFlag

Definition at line 97 of file SDDS_extract.c.

97 {
98 int64_t i;
99 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_GetRowFlags"))
100 return 0;
101 if (rows != SDDS_dataset->n_rows) {
102 SDDS_SetError("Row count mismatch (SDDS_GetRowFlags)");
103 return 0;
104 }
105 for (i = 0; i < rows; i++)
106 flag[i] = SDDS_dataset->row_flag[i];
107 return 1;
108}

◆ SDDS_GetRowLimit()

epicsShareFuncSDDS int64_t SDDS_GetRowLimit ( )
extern

Retrieves the current row limit for the SDDS dataset.

Returns
The current row limit.

Definition at line 1259 of file SDDS_input.c.

1259 {
1260 return SDDS_GetLockedRowLimit();
1261}

◆ SDDS_GetToken()

epicsShareFuncSDDS int32_t SDDS_GetToken ( char * s,
char * buffer,
int32_t buflen )
extern

Extracts the next token from a string, handling quoted substrings and escape characters.

This function parses the input string s to extract the next token, considering quoted substrings and escape characters. If the token is enclosed in double quotes ("), the function ensures that embedded quotes are handled correctly. After extracting the token, the original string s is updated to remove the extracted portion.

Parameters
[in,out]sPointer to the string from which to extract the token. This string will be modified to remove the extracted token.
[out]bufferPointer to a character array where the extracted token will be stored.
[in]buflenThe maximum number of characters to copy into buffer, including the null terminator.
Returns
On success, returns the length of the extracted token as an int32_t. If no token is found or an error occurs (e.g., buffer overflow), returns -1.
Note
The function assumes that the input string s is null-terminated. The caller must ensure that buffer has sufficient space to hold the extracted token.
See also
SDDS_GetToken2

Definition at line 1806 of file SDDS_utils.c.

1806 {
1807 char *ptr0, *ptr1, *escptr, *temp;
1808
1809 /* save the pointer to the head of the string */
1810 ptr0 = s;
1811
1812 /* skip leading white-space */
1813 while (isspace(*s))
1814 s++;
1815 if (*s == 0)
1816 return (-1);
1817 ptr1 = s;
1818
1819 if (*s == '"') {
1820 /* if quoted string, skip to next quotation mark */
1821 ptr1 = s + 1; /* beginning of actual token */
1822 do {
1823 s++;
1824 escptr = NULL;
1825 if (*s == '\\' && *(s + 1) == '\\') {
1826 /* skip and remember literal \ (indicated by \\ in the string) */
1827 escptr = s + 1;
1828 s += 2;
1829 }
1830 } while (*s && (*s != '"' || (*(s - 1) == '\\' && (s - 1) != escptr)));
1831 /* replace trailing quotation mark with a space */
1832 if (*s == '"')
1833 *s = ' ';
1834 } else {
1835 /* skip to first white-space following token */
1836 do {
1837 s++;
1838 /* imbedded quotation marks are handled here */
1839 if (*s == '"' && *(s - 1) != '\\') {
1840 while (*++s && !(*s == '"' && *(s - 1) != '\\'))
1841 ;
1842 }
1843 } while (*s && !isspace(*s));
1844 }
1845
1846 if ((int32_t)(s - ptr1) >= buflen)
1847 return (-1);
1848 strncpy(buffer, ptr1, s - ptr1);
1849 buffer[s - ptr1] = 0;
1850
1851 /* update the original string to delete the token */
1852 temp = malloc(sizeof(char) * (strlen(s) + 1));
1853 strcpy(temp, s);
1854 strcpy(ptr0, temp);
1855 free(temp);
1856
1857 /* return the string length */
1858 return ((int32_t)(s - ptr1));
1859}

◆ SDDS_GetToken2()

epicsShareFuncSDDS int32_t SDDS_GetToken2 ( char * s,
char ** st,
int32_t * strlength,
char * buffer,
int32_t buflen )
extern

Extracts the next token from a string, handling quoted substrings and escape characters, with updated string pointers.

This function parses the input string s to extract the next token, considering quoted substrings and escape characters. If the token is enclosed in double quotes ("), the function ensures that embedded quotes are handled correctly. After extracting the token, the original string s is updated by adjusting the string pointer st and the remaining string length strlength.

Parameters
[in,out]sPointer to the string from which to extract the token. This string will be modified to remove the extracted token.
[in,out]stPointer to the current position in the string s. This will be updated to point to the next character after the extracted token.
[in,out]strlengthPointer to an int32_t variable representing the remaining length of the string s. This will be decremented by the length of the extracted token.
[out]bufferPointer to a character array where the extracted token will be stored.
[in]buflenThe maximum number of characters to copy into buffer, including the null terminator.
Returns
On success, returns the length of the extracted token as an int32_t. If no token is found or an error occurs (e.g., buffer overflow), returns -1.
Note
The caller is responsible for ensuring that buffer has sufficient space to hold the extracted token. Additionally, st and strlength should accurately reflect the current parsing state of the string.
See also
SDDS_GetToken

Definition at line 1878 of file SDDS_utils.c.

1878 {
1879 char *ptr0, *ptr1, *escptr;
1880
1881 /* save the pointer to the head of the string */
1882 ptr0 = s;
1883
1884 /* skip leading white-space */
1885 while (isspace(*s))
1886 s++;
1887 if (*s == 0)
1888 return (-1);
1889 ptr1 = s;
1890
1891 if (*s == '"') {
1892 /* if quoted string, skip to next quotation mark */
1893 ptr1 = s + 1; /* beginning of actual token */
1894 do {
1895 s++;
1896 escptr = NULL;
1897 if (*s == '\\' && *(s + 1) == '\\') {
1898 /* skip and remember literal \ (indicated by \\ in the string) */
1899 escptr = s + 1;
1900 s += 2;
1901 }
1902 } while (*s && (*s != '"' || (*(s - 1) == '\\' && (s - 1) != escptr)));
1903 /* replace trailing quotation mark with a space */
1904 if (*s == '"')
1905 *s = ' ';
1906 } else {
1907 /* skip to first white-space following token */
1908 do {
1909 s++;
1910 /* imbedded quotation marks are handled here */
1911 if (*s == '"' && *(s - 1) != '\\') {
1912 while (*++s && !(*s == '"' && *(s - 1) != '\\'))
1913 ;
1914 }
1915 } while (*s && !isspace(*s));
1916 }
1917
1918 if ((int32_t)(s - ptr1) >= buflen)
1919 return (-1);
1920 strncpy(buffer, ptr1, s - ptr1);
1921 buffer[s - ptr1] = 0;
1922
1923 /* update the original string to delete the token */
1924 *st += s - ptr0;
1925 *strlength -= s - ptr0;
1926
1927 /* return the string length including whitespace */
1928 return ((int32_t)(s - ptr1));
1929}

◆ SDDS_GetTypeName()

epicsShareFuncSDDS char * SDDS_GetTypeName ( int32_t type)
extern

Retrieves the name of a specified SDDS data type as a string.

This function returns a dynamically allocated string containing the name of the specified SDDS data type. The name corresponds to the textual representation of the data type, such as "double", "float", "int32", etc.

Parameters
[in]typeThe SDDS data type for which the name is requested. Must be one of the predefined constants:
  • SDDS_LONGDOUBLE
  • SDDS_DOUBLE
  • SDDS_FLOAT
  • SDDS_LONG
  • SDDS_ULONG
  • SDDS_SHORT
  • SDDS_USHORT
  • SDDS_CHARACTER
  • SDDS_STRING
Returns
On success, returns a pointer to a newly allocated string containing the name of the data type. On failure (e.g., if the type is invalid or memory allocation fails), returns NULL.
Note
The caller is responsible for freeing the memory allocated for the returned string using SDDS_Free.
See also
SDDS_GetTypeSize
SDDS_SetError

Definition at line 2403 of file SDDS_utils.c.

2403 {
2404 char *name;
2405 if (!SDDS_VALID_TYPE(type))
2406 return NULL;
2407 if (!SDDS_CopyString(&name, SDDS_type_name[type - 1]))
2408 return NULL;
2409 return name;
2410}
char * SDDS_type_name[SDDS_NUM_TYPES]
Array of supported data type names.
Definition SDDS_data.c:43

◆ SDDS_GetTypeSize()

epicsShareFuncSDDS int32_t SDDS_GetTypeSize ( int32_t type)
extern

Retrieves the size in bytes of a specified SDDS data type.

This function returns the size, in bytes, of the specified SDDS data type. The size corresponds to the memory footprint of the data type when stored in the dataset.

Parameters
[in]typeThe SDDS data type for which the size is requested. Must be one of the predefined constants:
  • SDDS_LONGDOUBLE
  • SDDS_DOUBLE
  • SDDS_FLOAT
  • SDDS_LONG
  • SDDS_ULONG
  • SDDS_SHORT
  • SDDS_USHORT
  • SDDS_CHARACTER
  • SDDS_STRING
Returns
On success, returns a positive integer representing the size of the data type in bytes. On failure (e.g., if the type is invalid), returns -1 and records an error message.
Note
The function relies on the SDDS_type_size array, which should be properly initialized with the sizes of all supported SDDS data types.
See also
SDDS_GetTypeName
SDDS_SetError

Definition at line 2374 of file SDDS_utils.c.

2374 {
2375 if (!SDDS_VALID_TYPE(type))
2376 return (-1);
2377 return (SDDS_type_size[type - 1]);
2378}

◆ SDDS_GetValue()

epicsShareFuncSDDS void * SDDS_GetValue ( SDDS_DATASET * SDDS_dataset,
char * column_name,
int64_t srow_index,
void * memory )
extern

Retrieves the value from a specified column and selected row, optionally storing it in provided memory.

This function accesses the value of a specific column and selected row within the current data table of a dataset. It returns the value as a pointer to the data, allowing for both direct access and optional storage in user-provided memory.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the data set.
column_nameNULL-terminated string specifying the name of the column from which the value is to be retrieved.
srow_indexZero-based index representing the position of the selected row among all rows marked as "of interest".
memoryPointer to user-allocated memory where the retrieved value will be stored. If NULL, the function allocates memory internally, and the caller is responsible for freeing it.
Returns
  • Pointer to the retrieved value stored in memory (if provided) or in newly allocated memory.
  • NULL if an error occurs (e.g., invalid dataset, unrecognized column name, undefined data type, memory allocation failure, invalid row index). In this case, an error message is recorded internally.
Warning
  • If memory is NULL, the function allocates memory that the caller must free to prevent memory leaks.
  • The function does not perform type casting. Ensure that the provided memory is of the appropriate type matching the column's data type.
  • Modifying the data through the returned pointer affects the internal state of the dataset. Use with caution to avoid unintended side effects.
Note
  • For columns containing string data (SDDS_STRING), the function copies the string into memory. A typical usage would involve passing a pointer to a char* variable. c char *string; SDDS_GetValue(&SDDS_dataset, "name", index, &string); // or string = *(char**)SDDS_GetValue(&SDDS_dataset, "name", index, NULL);
  • The number of rows marked as "of interest" can be obtained using SDDS_CountRowsOfInterest.
See also

Definition at line 1755 of file SDDS_extract.c.

1755 {
1756 int32_t type, size, column_index;
1757 int64_t row_index;
1758 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_GetValue"))
1759 return (NULL);
1760 if ((column_index = SDDS_GetColumnIndex(SDDS_dataset, column_name)) < 0) {
1761 SDDS_SetError("Unable to get value--column name is not recognized (SDDS_GetValue)");
1762 return (NULL);
1763 }
1764 if (!(type = SDDS_GetColumnType(SDDS_dataset, column_index))) {
1765 SDDS_SetError("Unable to get value--data type undefined (SDDS_GetValue)");
1766 return (NULL);
1767 }
1768 size = SDDS_type_size[type - 1];
1769 if ((row_index = SDDS_GetSelectedRowIndex(SDDS_dataset, srow_index)) < 0) {
1770 SDDS_SetError("Unable to get value--row index out of range (SDDS_GetValue)");
1771 return (NULL);
1772 }
1773 if (type != SDDS_STRING) {
1774 if (!memory && !(memory = SDDS_Malloc(size))) {
1775 SDDS_SetError("Unable to get value--memory allocation failure (SDDS_GetValue)");
1776 return (NULL);
1777 }
1778 memcpy(memory, (char *)SDDS_dataset->data[column_index] + row_index * size, size);
1779 return (memory);
1780 }
1781 /* for character string data, a typical call would be
1782 * char *string;
1783 * SDDS_GetValue(&SDDS_dataset, "name", index, &string) or
1784 * string = *(char**)SDDS_GetValue(&SDDS_dataset, "name", index, NULL)
1785 */
1786 if (!memory && !(memory = SDDS_Malloc(size))) {
1787 SDDS_SetError("Unable to get value--memory allocation failure (SDDS_GetValue)");
1788 return (NULL);
1789 }
1790 if (SDDS_CopyString(memory, ((char **)SDDS_dataset->data[column_index])[row_index]))
1791 return (memory);
1792 return (NULL);
1793}

◆ SDDS_GetValueAsDouble()

epicsShareFuncSDDS double SDDS_GetValueAsDouble ( SDDS_DATASET * SDDS_dataset,
char * column_name,
int64_t srow_index )
extern

Retrieves the value from a specified column and selected row, casting it to a double.

This function accesses the value of a specific column and selected row within the current data table of a dataset. It casts the retrieved value to a double before returning it.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the data set.
column_nameNULL-terminated string specifying the name of the column from which the value is to be retrieved.
srow_indexZero-based index representing the position of the selected row among all rows marked as "of interest".
Returns
  • Double representing the casted value from the specified column and row.
  • 0 if an error occurs (e.g., invalid dataset, unrecognized column name, undefined data type, invalid row index, non-numeric column type). In this case, an error message is recorded internally.
Warning
  • This function only supports numerical data types. Attempting to retrieve and cast data from non-numeric columns (excluding SDDS_CHARACTER) will result in an error.
Note
  • The function internally allocates temporary memory to store the value before casting. This memory is freed before the function returns.
See also

Definition at line 1822 of file SDDS_extract.c.

1822 {
1823 int32_t type, size, column_index;
1824 int64_t row_index;
1825 void *memory;
1826 double value = 0;
1827 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_GetValueAsDouble"))
1828 return (0);
1829 if ((column_index = SDDS_GetColumnIndex(SDDS_dataset, column_name)) < 0) {
1830 SDDS_SetError("Unable to get value--column name is not recognized (SDDS_GetValueAsDouble)");
1831 return (0);
1832 }
1833 if (!(type = SDDS_GetColumnType(SDDS_dataset, column_index))) {
1834 SDDS_SetError("Unable to get value--data type undefined (SDDS_GetValueAsDouble)");
1835 return (0);
1836 }
1837 size = SDDS_type_size[type - 1];
1838 if ((row_index = SDDS_GetSelectedRowIndex(SDDS_dataset, srow_index)) < 0) {
1839 SDDS_SetError("Unable to get value--row index out of range (SDDS_GetValueAsDouble)");
1840 return (0);
1841 }
1842 if ((type != SDDS_STRING) && (type != SDDS_CHARACTER)) {
1843 memory = SDDS_Malloc(size);
1844 memcpy(memory, (char *)SDDS_dataset->data[column_index] + row_index * size, size);
1845 switch (type) {
1846 case SDDS_SHORT:
1847 value = *(short *)memory;
1848 break;
1849 case SDDS_USHORT:
1850 value = *(unsigned short *)memory;
1851 break;
1852 case SDDS_LONG:
1853 value = *(int32_t *)memory;
1854 break;
1855 case SDDS_ULONG:
1856 value = *(uint32_t *)memory;
1857 break;
1858 case SDDS_LONG64:
1859 value = *(int64_t *)memory;
1860 break;
1861 case SDDS_ULONG64:
1862 value = *(uint64_t *)memory;
1863 break;
1864 case SDDS_FLOAT:
1865 value = *(float *)memory;
1866 break;
1867 case SDDS_DOUBLE:
1868 value = *(double *)memory;
1869 break;
1870 case SDDS_LONGDOUBLE:
1871 value = *(long double *)memory;
1872 break;
1873 }
1874 free(memory);
1875 return (value);
1876 }
1877 SDDS_SetError("Unable to get non-numeric value as double (SDDS_GetValueAsDouble)");
1878 return (0);
1879}

◆ SDDS_GetValueByAbsIndex()

epicsShareFuncSDDS void * SDDS_GetValueByAbsIndex ( SDDS_DATASET * SDDS_dataset,
int32_t column_index,
int64_t row_index,
void * memory )
extern

Retrieves the value from a specified column and absolute row index, optionally storing it in provided memory.

This function accesses the value of a specific column (identified by its index) and an absolute row index within the current data table of a dataset. The retrieved value is either copied into user-provided memory or returned as a direct pointer to the internal data.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the data set.
column_indexZero-based index of the column from which the value is to be retrieved. Must be within the range [0, n_columns-1].
row_indexAbsolute zero-based row index within the dataset's data table. Must be within the range [0, n_rows-1].
memoryPointer to user-allocated memory where the retrieved value will be stored. If NULL, the function returns a pointer to the internal data.
Returns
  • Pointer to the retrieved value stored in memory (if provided) or to the internal data.
  • NULL if an error occurs (e.g., invalid dataset, column index out of range, row index out of range, undefined data type, memory allocation failure, non-numeric column type). In this case, an error message is recorded internally.
Warning
  • If memory is NULL, the function returns a direct pointer to the internal data. Modifying the data through this pointer affects the dataset's internal state.
  • If memory is provided, ensure that it points to sufficient memory to hold the data type of the column.
  • This function does not perform type casting. Ensure that the memory type matches the column's data type.
Note
  • Unlike SDDS_GetValueByIndex, this function uses an absolute row index rather than a selected row index among rows marked as "of interest".
  • For columns containing string data (SDDS_STRING), the function copies the string into memory. A typical usage would involve passing a pointer to a char* variable. c char *string; SDDS_GetValueByAbsIndex(&SDDS_dataset, column_index, row_index, &string); // or string = *(char**)SDDS_GetValueByAbsIndex(&SDDS_dataset, column_index, row_index, NULL);
See also

Definition at line 2091 of file SDDS_extract.c.

2091 {
2092 int32_t type, size;
2093 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_GetValueByAbsIndex"))
2094 return (NULL);
2095 if (column_index < 0 || column_index >= SDDS_dataset->layout.n_columns) {
2096 SDDS_SetError("Unable to get value--column index out of range (SDDS_GetValueByAbsIndex)");
2097 return (NULL);
2098 }
2099 if (row_index < 0 || row_index >= SDDS_dataset->n_rows) {
2100 SDDS_SetError("Unable to get value--index out of range (SDDS_GetValueByAbsIndex)");
2101 return (NULL);
2102 }
2103 if (!(type = SDDS_GetColumnType(SDDS_dataset, column_index))) {
2104 SDDS_SetError("Unable to get value--data type undefined (SDDS_GetValueByAbsIndex)");
2105 return (NULL);
2106 }
2107 size = SDDS_type_size[type - 1];
2108 if (type != SDDS_STRING) {
2109 if (memory) {
2110 memcpy(memory, (char *)SDDS_dataset->data[column_index] + row_index * size, size);
2111 return (memory);
2112 }
2113 return ((char *)SDDS_dataset->data[column_index] + row_index * size);
2114 }
2115 /* for character string data, a typical call would be
2116 * char *string;
2117 * SDDS_GetValueByAbsIndex(&SDDS_dataset, cindex, index, &string) or
2118 * string = *(char**)SDDS_GetValue(&SDDS_dataset, cindex, index, NULL)
2119 */
2120 if (!memory)
2121 memory = SDDS_Malloc(size);
2122 if (SDDS_CopyString(memory, ((char **)SDDS_dataset->data[column_index])[row_index]))
2123 return (memory);
2124 return (NULL);
2125}

◆ SDDS_GetValueByIndex()

epicsShareFuncSDDS void * SDDS_GetValueByIndex ( SDDS_DATASET * SDDS_dataset,
int32_t column_index,
int64_t srow_index,
void * memory )
extern

Retrieves the value from a specified column and selected row, optionally storing it in provided memory.

This function accesses the value of a specific column (identified by its index) and a selected row (identified by its selected row index among rows marked as "of interest") within the current data table of a dataset. The retrieved value is either copied into user-provided memory or returned as a direct pointer to the internal data.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the data set.
column_indexZero-based index of the column from which the value is to be retrieved. Must be within the range [0, n_columns-1].
srow_indexZero-based index representing the position of the selected row among all rows marked as "of interest".
memoryPointer to user-allocated memory where the retrieved value will be stored. If NULL, the function returns a pointer to the internal data.
Returns
  • Pointer to the retrieved value stored in memory (if provided) or to the internal data.
  • NULL if an error occurs (e.g., invalid dataset, column index out of range, undefined data type, row index out of range, memory allocation failure, non-numeric column type). In this case, an error message is recorded internally.
Warning
  • If memory is NULL, the function returns a direct pointer to the internal data. Modifying the data through this pointer affects the dataset's internal state.
  • If memory is provided, ensure that it points to sufficient memory to hold the data type of the column.
  • This function does not perform type casting. Ensure that the memory type matches the column's data type.
Note
  • For columns containing string data (SDDS_STRING), the function copies the string into memory. A typical usage would involve passing a pointer to a char* variable. c char *string; SDDS_GetValueByIndex(&SDDS_dataset, column_index, index, &string); // or string = *(char**)SDDS_GetValueByIndex(&SDDS_dataset, column_index, index, NULL);
  • The number of rows marked as "of interest" can be obtained using SDDS_CountRowsOfInterest.
See also

Definition at line 2015 of file SDDS_extract.c.

2015 {
2016 int32_t type, size;
2017 int64_t row_index;
2018 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_GetValueByIndex"))
2019 return (NULL);
2020 if (column_index < 0 || column_index >= SDDS_dataset->layout.n_columns) {
2021 SDDS_SetError("Unable to get value--column index out of range (SDDS_GetValueByIndex)");
2022 return (NULL);
2023 }
2024 if (!(type = SDDS_GetColumnType(SDDS_dataset, column_index))) {
2025 SDDS_SetError("Unable to get value--data type undefined (SDDS_GetValueByIndex)");
2026 return (NULL);
2027 }
2028 size = SDDS_type_size[type - 1];
2029 if ((row_index = SDDS_GetSelectedRowIndex(SDDS_dataset, srow_index)) < 0) {
2030 SDDS_SetError("Unable to get value--row index out of range (SDDS_GetValueByIndex)");
2031 return (NULL);
2032 }
2033 if (type != SDDS_STRING) {
2034 if (memory) {
2035 memcpy(memory, (char *)SDDS_dataset->data[column_index] + row_index * size, size);
2036 return (memory);
2037 }
2038 return ((char *)SDDS_dataset->data[column_index] + row_index * size);
2039 }
2040 /* for character string data, a typical call would be
2041 * char *string;
2042 * SDDS_GetValueByIndex(&SDDS_dataset, cindex, index, &string) or
2043 * string = *(char**)SDDS_GetValue(&SDDS_dataset, cindex, index, NULL)
2044 */
2045 if (!memory)
2046 memory = SDDS_Malloc(size);
2047 if (SDDS_CopyString(memory, ((char **)SDDS_dataset->data[column_index])[row_index]))
2048 return (memory);
2049 return (NULL);
2050}

◆ SDDS_GetValueByIndexAsDouble()

epicsShareFuncSDDS double SDDS_GetValueByIndexAsDouble ( SDDS_DATASET * SDDS_dataset,
int32_t column_index,
int64_t srow_index )
extern

Retrieves the value from a specified column and selected row, casting it to a double.

This function accesses the value of a specific column (identified by its index) and a selected row (identified by its selected row index among rows marked as "of interest") within the current data table of a dataset. It casts the retrieved value to a double before returning it.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the data set.
column_indexZero-based index of the column from which the value is to be retrieved. Must be within the range [0, n_columns-1].
srow_indexZero-based index representing the position of the selected row among all rows marked as "of interest".
Returns
  • Double representing the casted value from the specified column and row.
  • 0.0 if an error occurs (e.g., invalid dataset, column index out of range, undefined data type, row index out of range, non-numeric column type). In this case, an error message is recorded internally.
Warning
  • This function only supports numerical data types. Attempting to retrieve and cast data from non-numeric columns (excluding SDDS_CHARACTER) will result in an error.
  • The returned value 0.0 may be ambiguous if it is a valid data value. Always check for errors using SDDS_CheckError or similar mechanisms.
Note
  • The number of rows marked as "of interest" can be obtained using SDDS_CountRowsOfInterest.
  • If the dataset's memory mode for the column is set to DONT_TRACK_COLUMN_MEMORY_AFTER_ACCESS, the internal data for the column may be freed after access.
See also

Definition at line 1915 of file SDDS_extract.c.

1915 {
1916 int32_t type, size;
1917 int64_t row_index;
1918 void *memory;
1919 double value = 0;
1920 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_GetValueByIndexAsDouble"))
1921 return (0);
1922 if (column_index < 0 || column_index >= SDDS_dataset->layout.n_columns) {
1923 SDDS_SetError("Unable to get value--column index out of range (SDDS_GetValueByIndexAsDouble)");
1924 return (0);
1925 }
1926 if (!(type = SDDS_GetColumnType(SDDS_dataset, column_index))) {
1927 SDDS_SetError("Unable to get value--data type undefined (SDDS_GetValueByIndexAsDouble)");
1928 return (0);
1929 }
1930 size = SDDS_type_size[type - 1];
1931 if ((row_index = SDDS_GetSelectedRowIndex(SDDS_dataset, srow_index)) < 0) {
1932 SDDS_SetError("Unable to get value--row index out of range (SDDS_GetValueByIndexAsDouble)");
1933 return (0);
1934 }
1935 if ((type != SDDS_STRING) && (type != SDDS_CHARACTER)) {
1936 memory = SDDS_Malloc(size);
1937 memcpy(memory, (char *)SDDS_dataset->data[column_index] + row_index * size, size);
1938 switch (type) {
1939 case SDDS_SHORT:
1940 value = *(short *)memory;
1941 break;
1942 case SDDS_USHORT:
1943 value = *(unsigned short *)memory;
1944 break;
1945 case SDDS_LONG:
1946 value = *(int32_t *)memory;
1947 break;
1948 case SDDS_ULONG:
1949 value = *(uint32_t *)memory;
1950 break;
1951 case SDDS_LONG64:
1952 value = *(int64_t *)memory;
1953 break;
1954 case SDDS_ULONG64:
1955 value = *(uint64_t *)memory;
1956 break;
1957 case SDDS_FLOAT:
1958 value = *(float *)memory;
1959 break;
1960 case SDDS_DOUBLE:
1961 value = *(double *)memory;
1962 break;
1963 case SDDS_LONGDOUBLE:
1964 value = *(long double *)memory;
1965 break;
1966 }
1967 free(memory);
1968 return (value);
1969 }
1970 SDDS_SetError("Unable to get non-numeric value as double (SDDS_GetValueByIndexAsDouble)");
1971 return (0);
1972}

◆ SDDS_GotoPage()

epicsShareFuncSDDS int32_t SDDS_GotoPage ( SDDS_DATASET * SDDS_dataset,
int32_t page_number )
extern

Sets the current page of the SDDS dataset to the specified page number.

This function is used to navigate to a specific page of the SDDS dataset. It is only supported for non-zip files and does not work for pipe input.

Parameters
SDDS_datasetThe SDDS dataset to operate on.
page_numberThe page number to navigate to.
Returns
Returns 1 on success, 0 on failure.

Definition at line 1273 of file SDDS_input.c.

1273 {
1274 int64_t offset;
1275
1276 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_GotoPage"))
1277 return (0);
1278 if (SDDS_dataset->layout.disconnected) {
1279 SDDS_SetError("Can't go to page--file is disconnected (SDDS_GotoPage)");
1280 return 0;
1281 }
1282 if (SDDS_dataset->layout.popenUsed || !SDDS_dataset->layout.filename) {
1283 SDDS_SetError("Can't go to page of pipe is used (SDDS_GotoPage)");
1284 return 0;
1285 }
1286#if defined(zLib)
1287 if (SDDS_dataset->layout.gzipFile) {
1288 SDDS_SetError("Can not go to page of a gzip file (SDDS_GotoPage)");
1289 return (0);
1290 } else {
1291#endif
1292 if (SDDS_dataset->layout.lzmaFile) {
1293 SDDS_SetError("Can not go to page of an .lzma or .xz file (SDDS_GotoPage)");
1294 return (0);
1295 } else {
1296 if (!SDDS_dataset->layout.fp) {
1297 SDDS_SetError("Unable to go to page--NULL file pointer (SDDS_GotoPage)");
1298 return (0);
1299 }
1300 }
1301#if defined(zLib)
1302 }
1303#endif
1304 if (!SDDS_dataset->layout.filename) {
1305 SDDS_SetError("Can't go to page--NULL filename pointer (SDDS_GotoPage)");
1306 return 0;
1307 }
1308 if (SDDS_dataset->mode != SDDS_READMODE) {
1309 SDDS_SetError("Can't go to page--file mode has to be reading mode (SDDS_GotoPage)");
1310 return 0;
1311 }
1312 if (SDDS_dataset->fBuffer.bufferSize) {
1313 SDDS_SetError("Can't go to page--file buffering is turned on (SDDS_GotoPage)");
1314 return 0;
1315 }
1316 if (page_number < 1) {
1317 SDDS_SetError("The page_number can not be less than 1 (SDDS_GotoPage)");
1318 return (0);
1319 }
1320 if (page_number > SDDS_dataset->pages_read) {
1321 offset = SDDS_dataset->pagecount_offset[SDDS_dataset->pages_read] - ftell(SDDS_dataset->layout.fp);
1322 fseek(SDDS_dataset->layout.fp, offset, 1);
1323 SDDS_dataset->page_number = SDDS_dataset->pages_read;
1324 while (SDDS_dataset->pages_read < page_number) {
1325 if (SDDS_ReadPageSparse(SDDS_dataset, 0, SDDS_dataset->layout.data_mode.column_major ? 1 : 10000, 0, 0) <= 0) {
1326 SDDS_SetError("The page_number is greater than the total pages (SDDS_GotoPage)");
1327 return (0);
1328 }
1329 }
1330 } else {
1331 offset = SDDS_dataset->pagecount_offset[page_number - 1] - ftell(SDDS_dataset->layout.fp);
1332 fseek(SDDS_dataset->layout.fp, offset, 1); /*seek to the position from current offset */
1333 SDDS_dataset->page_number = page_number - 1;
1334 }
1335 return 1;
1336}
int32_t SDDS_ReadPageSparse(SDDS_DATASET *SDDS_dataset, uint32_t mode, int64_t sparse_interval, int64_t sparse_offset, int32_t sparse_statistics)

◆ SDDS_HasWhitespace()

epicsShareFuncSDDS int32_t SDDS_HasWhitespace ( char * string)
extern

Checks if a string contains any whitespace characters.

This function scans through the provided string to determine if it contains any whitespace characters (e.g., space, tab, newline).

Parameters
[in]stringPointer to the null-terminated string to be checked.
Returns
Returns 1 if the string contains at least one whitespace character. Returns 0 if no whitespace characters are found or if the input string is NULL.
See also
isspace

Definition at line 1488 of file SDDS_utils.c.

1488 {
1489 if (!string)
1490 return (0);
1491 while (*string) {
1492 if (isspace(*string))
1493 return (1);
1494 string++;
1495 }
1496 return (0);
1497}

◆ SDDS_IdentifyType()

epicsShareFuncSDDS int32_t SDDS_IdentifyType ( char * typeName)
extern

Identifies the SDDS data type based on its string name.

This function searches for the SDDS data type that matches the provided string typeName. It returns the corresponding SDDS data type constant if a match is found.

Parameters
[in]typeNameA null-terminated string representing the name of the SDDS data type to identify.
Returns
On success, returns the SDDS data type constant (int32_t) corresponding to typeName. On failure (e.g., if typeName does not match any known data type), returns 0.
Note
The function performs a case-sensitive comparison between typeName and the names of supported SDDS data types.
See also
SDDS_GetTypeName
SDDS_SetError

Definition at line 2426 of file SDDS_utils.c.

2426 {
2427 int32_t i;
2428 for (i = 0; i < SDDS_NUM_TYPES; i++)
2429 if (strcmp(typeName, SDDS_type_name[i]) == 0)
2430 return i + 1;
2431 return 0;
2432}

◆ SDDS_InitializeAppend()

epicsShareFuncSDDS int32_t SDDS_InitializeAppend ( SDDS_DATASET * SDDS_dataset,
const char * filename )
extern

Initializes the SDDS dataset for appending data by adding a new page to an existing file.

This function prepares the SDDS dataset for appending additional data to an existing SDDS file by initializing necessary data structures, verifying file integrity, and setting up for the addition of a new data page. It ensures that the file is writable, not compressed, and properly locked to prevent concurrent modifications.

Parameters
[in,out]SDDS_datasetPointer to the SDDS_DATASET structure to be initialized for appending.
[in]filenameThe name of the existing SDDS file to which data will be appended. If NULL, data will be appended to standard input.
Returns
  • 1 on successful initialization.
  • 0 on error. In this case, an internal error message is set describing the failure.
Precondition
  • The specified file must exist and be a valid SDDS file.
  • The file must not be compressed (gzip, lzma, xz) and must be accessible for read and write operations.
Postcondition
  • The dataset is ready to append data as a new page.
  • The file is locked to prevent concurrent writes.
Note
  • If filename is NULL, the dataset will append data from standard input.
  • The function sets internal flags indicating whether the file was previously empty or had existing data.
Warning
  • Appending to a compressed file is not supported and will result in an error.
  • Ensure that no other processes are accessing the file simultaneously to avoid conflicts.

Definition at line 288 of file SDDS_output.c.

288 {
289 /* char *ptr, *datafile, *headerfile; */
290 char s[SDDS_MAXLINE];
291 int64_t endOfLayoutOffset, endOfFileOffset;
292 char *extension;
293
294 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_InitializeAppend"))
295 return 0;
296 if (!SDDS_ZeroMemory((void *)SDDS_dataset, sizeof(SDDS_DATASET))) {
297 sprintf(s, "Unable to initialize input for file %s--can't zero SDDS_DATASET structure (SDDS_InitializeAppend)", filename);
298 SDDS_SetError(s);
299 return 0;
300 }
301 SDDS_dataset->layout.popenUsed = SDDS_dataset->layout.gzipFile = SDDS_dataset->layout.lzmaFile = SDDS_dataset->layout.disconnected = 0;
302 SDDS_dataset->layout.depth = SDDS_dataset->layout.data_command_seen = SDDS_dataset->layout.commentFlags = SDDS_dataset->deferSavingLayout = 0;
303 if (!filename)
304 SDDS_dataset->layout.filename = NULL;
305 else if (!SDDS_CopyString(&SDDS_dataset->layout.filename, filename)) {
306 sprintf(s, "Memory allocation failure initializing file %s (SDDS_InitializeAppend)", filename);
307 SDDS_SetError(s);
308 return 0;
309 } else if ((extension = strrchr(filename, '.')) && ((strcmp(extension, ".gz") == 0) || (strcmp(extension, ".lzma") == 0) || (strcmp(extension, ".xz") == 0))) {
310 sprintf(s, "Cannot append to a compressed file %s (SDDS_InitializeAppend)", filename);
311 SDDS_SetError(s);
312 return 0;
313 }
314
315 SDDS_dataset->layout.popenUsed = 0;
316 if (!filename) {
317#if defined(_WIN32)
318 if (_setmode(_fileno(stdin), _O_BINARY) == -1) {
319 sprintf(s, "unable to set stdin to binary mode");
320 SDDS_SetError(s);
321 return 0;
322 }
323#endif
324 SDDS_dataset->layout.fp = stdin;
325 } else {
326 if (SDDS_FileIsLocked(filename)) {
327 sprintf(s, "unable to open file %s for appending--file is locked (SDDS_InitializeAppend)", filename);
328 SDDS_SetError(s);
329 return 0;
330 }
331 if (!(SDDS_dataset->layout.fp = fopen(filename, FOPEN_READ_AND_WRITE_MODE))) {
332 sprintf(s, "Unable to open file %s for appending (SDDS_InitializeAppend)", filename);
333 SDDS_SetError(s);
334 return 0;
335 }
336 if (!SDDS_LockFile(SDDS_dataset->layout.fp, filename, "SDDS_InitializeAppend"))
337 return 0;
338 }
339
340 if (!SDDS_ReadLayout(SDDS_dataset, SDDS_dataset->layout.fp))
341 return 0;
342 endOfLayoutOffset = ftell(SDDS_dataset->layout.fp);
343 if (SDDS_dataset->layout.n_columns &&
344 (!(SDDS_dataset->column_flag = (int32_t *)SDDS_Malloc(sizeof(int32_t) * SDDS_dataset->layout.n_columns)) ||
345 !(SDDS_dataset->column_order = (int32_t *)SDDS_Malloc(sizeof(int32_t) * SDDS_dataset->layout.n_columns)) ||
346 !SDDS_SetMemory(SDDS_dataset->column_flag, SDDS_dataset->layout.n_columns, SDDS_LONG, (int32_t)1, (int32_t)0) ||
347 !SDDS_SetMemory(SDDS_dataset->column_order, SDDS_dataset->layout.n_columns, SDDS_LONG, (int32_t)0, (int32_t)1))) {
348 SDDS_SetError("Unable to initialize input--memory allocation failure (SDDS_InitializeAppend)");
349 return 0;
350 }
351 if (fseek(SDDS_dataset->layout.fp, 0, 2) == -1) {
352 SDDS_SetError("Unable to initialize append--seek failure (SDDS_InitializeAppend)");
353 return 0;
354 }
355 endOfFileOffset = ftell(SDDS_dataset->layout.fp);
356 if (endOfFileOffset == endOfLayoutOffset)
357 SDDS_dataset->file_had_data = 0; /* appending to empty file */
358 else
359 SDDS_dataset->file_had_data = 1; /* appending to nonempty file */
360 SDDS_dataset->layout.layout_written = 1; /* its already in the file */
361 SDDS_dataset->mode = SDDS_WRITEMODE; /*writing */
362 return 1;
363}
int32_t SDDS_ReadLayout(SDDS_DATASET *SDDS_dataset, FILE *fp)
Definition SDDS_input.c:518
int32_t SDDS_FileIsLocked(const char *filename)
Determines if a specified file is locked.
int32_t SDDS_LockFile(FILE *fp, const char *filename, const char *caller)
Attempts to lock a specified file.

◆ SDDS_InitializeAppendToPage()

epicsShareFuncSDDS int32_t SDDS_InitializeAppendToPage ( SDDS_DATASET * SDDS_dataset,
const char * filename,
int64_t updateInterval,
int64_t * rowsPresentReturn )
extern

Initializes the SDDS dataset for appending data to the last page of an existing file.

This function sets up the SDDS dataset to append additional data rows to the last page of an existing SDDS file. It reads the existing file layout, determines the current state of data (including row counts), and prepares internal data structures to accommodate new data. The function also handles file locking, buffer management, and ensures that the file is ready for efficient data appending based on the specified update interval.

Parameters
[in,out]SDDS_datasetPointer to the SDDS_DATASET structure to be initialized for appending.
[in]filenameThe name of the existing SDDS file to which data will be appended. If NULL, data will be appended to standard input.
[in]updateIntervalThe number of rows to write before the dataset reallocates memory or flushes data. This parameter controls the frequency of memory allocation and disk I/O operations during the append process.
[out]rowsPresentReturnPointer to an int64_t variable where the function will store the number of rows present in the dataset after initialization. This provides information on the current dataset size.
Returns
  • 1 on successful initialization.
  • 0 on error. In this case, an internal error message is set detailing the issue.
Precondition
  • The specified file must exist and be a valid SDDS file.
  • The file must not be compressed (gzip, lzma, xz) and must be accessible for read and write operations.
Postcondition
  • The dataset is configured to append data to the last page of the file.
  • Internal structures are initialized to track row counts and manage memory efficiently based on the update interval.
  • The file is locked to prevent concurrent modifications.
  • rowsPresentReturn is updated with the current number of rows in the dataset.
Note
  • If filename is NULL, data will be appended from standard input.
  • The function sets internal flags indicating whether the file already contained data prior to appending.
Warning
  • Appending to a compressed file is not supported and will result in an error.
  • Ensure that no other processes are accessing the file simultaneously to avoid conflicts.

Definition at line 397 of file SDDS_output.c.

397 {
398 /* char *ptr, *datafile, *headerfile; */
399 char s[SDDS_MAXLINE];
400 int64_t endOfLayoutOffset, endOfFileOffset, rowCountOffset, offset;
401 int32_t rowsPresent32;
402 int64_t rowsPresent;
403 char *extension;
404 int32_t previousBufferSize;
405
406 *rowsPresentReturn = -1;
407 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_InitializeAppendToPage"))
408 return 0;
409 if (!SDDS_ZeroMemory((void *)SDDS_dataset, sizeof(SDDS_DATASET))) {
410 sprintf(s, "Unable to initialize input for file %s--can't zero SDDS_DATASET structure (SDDS_InitializeAppendToPage)", filename);
411 SDDS_SetError(s);
412 return 0;
413 }
414 SDDS_dataset->layout.popenUsed = SDDS_dataset->layout.gzipFile = SDDS_dataset->layout.lzmaFile = SDDS_dataset->layout.disconnected = 0;
415 SDDS_dataset->layout.depth = SDDS_dataset->layout.data_command_seen = SDDS_dataset->layout.commentFlags = SDDS_dataset->deferSavingLayout = 0;
416 if (!filename)
417 SDDS_dataset->layout.filename = NULL;
418 else if (!SDDS_CopyString(&SDDS_dataset->layout.filename, filename)) {
419 sprintf(s, "Memory allocation failure initializing file %s (SDDS_InitializeAppendToPage)", filename);
420 SDDS_SetError(s);
421 return 0;
422 } else if ((extension = strrchr(filename, '.')) && ((strcmp(extension, ".gz") == 0) || (strcmp(extension, ".lzma") == 0) || (strcmp(extension, ".xz") == 0))) {
423 sprintf(s, "Cannot append to a compressed file %s (SDDS_InitializeAppendToPage)", filename);
424 SDDS_SetError(s);
425 return 0;
426 }
427
428 if (!filename) {
429#if defined(_WIN32)
430 if (_setmode(_fileno(stdin), _O_BINARY) == -1) {
431 sprintf(s, "unable to set stdin to binary mode");
432 SDDS_SetError(s);
433 return 0;
434 }
435#endif
436 SDDS_dataset->layout.fp = stdin;
437 } else {
438 if (SDDS_FileIsLocked(filename)) {
439 sprintf(s, "unable to open file %s for appending--file is locked (SDDS_InitializeAppendToPage)", filename);
440 SDDS_SetError(s);
441 return 0;
442 }
443 if (!(SDDS_dataset->layout.fp = fopen(filename, FOPEN_READ_AND_WRITE_MODE))) {
444 sprintf(s, "Unable to open file %s for appending (SDDS_InitializeAppendToPage)", filename);
445 SDDS_SetError(s);
446 return 0;
447 }
448 if (!SDDS_LockFile(SDDS_dataset->layout.fp, filename, "SDDS_InitializeAppendToPage")) {
449 return 0;
450 }
451 }
452
453 if (!SDDS_ReadLayout(SDDS_dataset, SDDS_dataset->layout.fp)) {
454 return 0;
455 }
456 endOfLayoutOffset = ftell(SDDS_dataset->layout.fp);
457 if (SDDS_dataset->layout.n_columns &&
458 (!(SDDS_dataset->column_flag = (int32_t *)SDDS_Malloc(sizeof(int32_t) * SDDS_dataset->layout.n_columns)) ||
459 !(SDDS_dataset->column_order = (int32_t *)SDDS_Malloc(sizeof(int32_t) * SDDS_dataset->layout.n_columns)) ||
460 !SDDS_SetMemory(SDDS_dataset->column_flag, SDDS_dataset->layout.n_columns, SDDS_LONG, (int32_t)1, (int32_t)0) ||
461 !SDDS_SetMemory(SDDS_dataset->column_order, SDDS_dataset->layout.n_columns, SDDS_LONG, (int32_t)0, (int32_t)1))) {
462 SDDS_SetError("Unable to initialize input--memory allocation failure (SDDS_InitializeAppendToPage)");
463 return 0;
464 }
465 rowCountOffset = -1;
466 rowsPresent = 0;
467#ifdef DEBUG
468 fprintf(stderr, "Data mode is %s\n", SDDS_data_mode[SDDS_dataset->layout.data_mode.mode - 1]);
469#endif
470 SDDS_dataset->pagecount_offset = NULL;
471 previousBufferSize = SDDS_SetDefaultIOBufferSize(0);
472 if (!SDDS_dataset->layout.data_mode.no_row_counts) {
473 /* read pages to get to the last page */
474 while (SDDS_ReadPageSparse(SDDS_dataset, 0, 10000, 0, 0) > 0) {
475 rowCountOffset = SDDS_dataset->rowcount_offset;
476 offset = ftell(SDDS_dataset->layout.fp);
477 fseek(SDDS_dataset->layout.fp, rowCountOffset, 0);
478
479 if (SDDS_dataset->layout.data_mode.mode == SDDS_BINARY) {
480 if (fread(&rowsPresent32, sizeof(rowsPresent32), 1, SDDS_dataset->layout.fp) == 0) {
481 SDDS_SetError("Error: row count not present or not correct length");
482 return 0;
483 }
484 if (SDDS_dataset->swapByteOrder) {
485 SDDS_SwapLong(&rowsPresent32);
486 }
487 if (rowsPresent32 == INT32_MIN) {
488 if (fread(&rowsPresent, sizeof(rowsPresent), 1, SDDS_dataset->layout.fp) == 0) {
489 SDDS_SetError("Error: row count not present or not correct length");
490 return 0;
491 }
492 if (SDDS_dataset->swapByteOrder) {
493 SDDS_SwapLong64(&rowsPresent);
494 }
495 } else {
496 rowsPresent = rowsPresent32;
497 }
498 } else {
499 char buffer[30];
500 if (!fgets(buffer, 30, SDDS_dataset->layout.fp) || strlen(buffer) != 21 || sscanf(buffer, "%" SCNd64, &rowsPresent) != 1) {
501#ifdef DEBUG
502 fprintf(stderr, "buffer for row count data: >%s<\n", buffer);
503#endif
504 SDDS_SetError("Unable to initialize input--row count not present or not correct length (SDDS_InitializeAppendToPage)");
505 SDDS_SetDefaultIOBufferSize(previousBufferSize);
506 return 0;
507 }
508 }
509 fseek(SDDS_dataset->layout.fp, offset, 0);
510#ifdef DEBUG
511 fprintf(stderr, "%" PRId64 " rows present\n", rowsPresent);
512#endif
513 }
514 if (rowCountOffset == -1) {
515 SDDS_SetDefaultIOBufferSize(previousBufferSize);
516 SDDS_SetError("Unable to initialize input--problem finding row count offset (SDDS_InitializeAppendToPage)");
517 return 0;
518 }
519 }
520 SDDS_SetDefaultIOBufferSize(previousBufferSize);
521 SDDS_dataset->fBuffer.bytesLeft = SDDS_dataset->fBuffer.bufferSize;
522
523#ifdef DEBUG
524 fprintf(stderr, "Starting page with %" PRId64 " rows\n", updateInterval);
525#endif
526 if (!SDDS_StartPage(SDDS_dataset, updateInterval)) {
527 SDDS_SetError("Unable to initialize input--problem starting page (SDDS_InitializeAppendToPage)");
528 return 0;
529 }
530
531 /* seek to the end of the file */
532 if (fseek(SDDS_dataset->layout.fp, 0, 2) == -1) {
533 SDDS_SetError("Unable to initialize append--seek failure (SDDS_InitializeAppendToPage)");
534 return 0;
535 }
536 endOfFileOffset = ftell(SDDS_dataset->layout.fp);
537 if (endOfFileOffset == endOfLayoutOffset)
538 SDDS_dataset->file_had_data = 0; /* appending to empty file */
539 else {
540 SDDS_dataset->file_had_data = 1; /* appending to nonempty file */
541 if (rowCountOffset != -1) {
542 SDDS_dataset->rowcount_offset = rowCountOffset;
543 SDDS_dataset->n_rows_written = rowsPresent;
544 SDDS_dataset->first_row_in_mem = rowsPresent;
545 SDDS_dataset->last_row_written = -1;
546 *rowsPresentReturn = rowsPresent;
547 SDDS_dataset->writing_page = 1;
548 }
549 }
550#ifdef DEBUG
551 fprintf(stderr, "rowcount_offset = %" PRId64 ", n_rows_written = %" PRId64 ", first_row_in_mem = %" PRId64 ", last_row_written = %" PRId64 "\n", SDDS_dataset->rowcount_offset, SDDS_dataset->n_rows_written, SDDS_dataset->first_row_in_mem, SDDS_dataset->last_row_written);
552#endif
553 SDDS_dataset->page_number = 1;
554 SDDS_dataset->layout.layout_written = 1; /* its already in the file */
555 SDDS_dataset->mode = SDDS_WRITEMODE; /*writing */
556 return 1;
557}
int32_t SDDS_SetDefaultIOBufferSize(int32_t newValue)
Definition SDDS_binary.c:82
void SDDS_SwapLong64(int64_t *data)
Swaps the endianness of a 64-bit integer.
void SDDS_SwapLong(int32_t *data)
Swaps the endianness of a 32-bit integer.
char * SDDS_data_mode[SDDS_NUM_DATA_MODES]
Array of supported data modes.
Definition SDDS_data.c:33

◆ SDDS_InitializeCopy()

epicsShareFuncSDDS int32_t SDDS_InitializeCopy ( SDDS_DATASET * SDDS_target,
SDDS_DATASET * SDDS_source,
char * filename,
char * filemode )
extern

Initializes an SDDS_DATASET structure in preparation for copying a data table from another SDDS_DATASET structure.

Parameters
SDDS_targetAddress of SDDS_DATASET structure into which to copy data.
SDDS_sourceAddress of SDDS_DATASET structure from which to copy data.
filenameA NULL-terminated character string giving a filename to be associated with the new SDDS_DATASET. Typically, the name of a file to which the copied data will be written after modification. Ignored if NULL.
filemodeA NULL-terminated character string giving the fopen file mode to be used to open the file named by filename. Ignored if filename is NULL.
Returns
1 on success. On failure, returns 0 and records an error message.

Definition at line 40 of file SDDS_copy.c.

40 {
41 char s[SDDS_MAXLINE];
42#if defined(zLib)
43 char *extension;
44#endif
45
46 if (sizeof(gzFile) != sizeof(void *)) {
47 SDDS_SetError("gzFile is not the same size as void *, possible corruption of the SDDS_LAYOUT structure");
48 return (0);
49 }
50 if (!SDDS_CheckDataset(SDDS_source, "SDDS_InitializeCopy"))
51 return (0);
52 if (!SDDS_CheckDataset(SDDS_target, "SDDS_InitializeCopy"))
53 return (0);
54 if (!SDDS_ZeroMemory((void *)SDDS_target, sizeof(SDDS_DATASET))) {
55 SDDS_SetError("Unable to copy layout--can't zero SDDS_DATASET structure (SDDS_InitializeCopy)");
56 return (0);
57 }
58 if (strcmp(filemode, "r") == 0) {
59 filemode = FOPEN_READ_MODE;
60 SDDS_target->mode = SDDS_READMODE;
61 } else if (strcmp(filemode, "w") == 0) {
62 filemode = FOPEN_WRITE_MODE;
63 SDDS_target->mode = SDDS_WRITEMODE;
64 }
65 SDDS_target->pagecount_offset = NULL;
66 if (!(strcmp(filemode, "r") == 0 || strcmp(filemode, "w") == 0 || strcmp(filemode, "rb") == 0 || strcmp(filemode, "wb") == 0 || strcmp(filemode, "m") == 0)) {
67 SDDS_SetError("Programming error--invalid file mode (SDDS_InitializeCopy)");
68 return (0);
69 }
70
71 SDDS_target->layout.popenUsed = 0;
72 SDDS_target->layout.gzipFile = 0;
73 SDDS_target->layout.lzmaFile = 0;
74 if (filename) {
75 if (SDDS_FileIsLocked(filename)) {
76 sprintf(s, "unable to open file %s for copy--file is locked (SDDS_InitializeCopy)", filename);
78 return 0;
79 }
80
81 if ((extension = strrchr(filename, '.')) && ((strcmp(extension, ".xz") == 0) || (strcmp(extension, ".lzma") == 0))) {
82 SDDS_target->layout.lzmaFile = 1;
83 if (!filemode) {
84 sprintf(s, "Unable to open file %s (SDDS_InitializeCopy)", filename);
86 return (0);
87 }
88 if (!(SDDS_target->layout.lzmafp = lzma_open(filename, filemode))) {
89 sprintf(s, "Unable to open file %s for writing (SDDS_InitializeCopy)", filename);
91 return 0;
92 }
93 SDDS_target->layout.fp = SDDS_target->layout.lzmafp->fp;
94 } else {
95 if (!filemode || !(SDDS_target->layout.fp = fopen(filename, filemode))) {
96 sprintf(s, "Unable to open file %s (SDDS_InitializeCopy)", filename);
98 return (0);
99 }
100 }
101 if ((strcmp(filemode, "w") == 0 || strcmp(filemode, "wb") == 0) && !SDDS_LockFile(SDDS_target->layout.fp, filename, "SDDS_InitializeCopy"))
102 return 0;
103 if (!SDDS_CopyString(&SDDS_target->layout.filename, filename)) {
104 SDDS_SetError("Memory allocation failure (SDDS_InitializeCopy)");
105 return (0);
106 }
107#if defined(zLib)
108 if ((extension = strrchr(filename, '.')) && strcmp(extension, ".gz") == 0) {
109 SDDS_target->layout.gzipFile = 1;
110 if ((SDDS_target->layout.gzfp = gzdopen(fileno(SDDS_target->layout.fp), filemode)) == NULL) {
111 sprintf(s, "Unable to open compressed file %s for writing (SDDS_InitializeCopy)", filename);
112 SDDS_SetError(s);
113 return 0;
114 }
115 }
116#endif
117 } else {
118 SDDS_target->layout.filename = NULL;
119 SDDS_target->layout.fp = NULL;
120 SDDS_target->mode = SDDS_MEMMODE;
121 if (filemode) {
122 if (strcmp(filemode, "w") == 0 || strcmp(filemode, "wb") == 0)
123 SDDS_target->layout.fp = stdout;
124 else if (strcmp(filemode, "r") == 0 || strcmp(filemode, "rb") == 0)
125 SDDS_target->layout.fp = stdin;
126
127 /* else if (strcmp(filemode, "m")!=0) {
128 SDDS_SetError("Unknown filemode (SDDS_InitializeCopy)");
129 return(0);
130 } */
131#if defined(_WIN32)
132 if (strcmp(filemode, "m") != 0) {
133 if (_setmode(_fileno(SDDS_target->layout.fp), _O_BINARY) == -1) {
134 sprintf(s, "unable to set stdout or stdin to binary mode");
135 SDDS_SetError(s);
136 return 0;
137 }
138 }
139#endif
140 }
141 }
142 SDDS_target->page_number = SDDS_target->page_started = 0;
143 if (!SDDS_CopyLayout(SDDS_target, SDDS_source))
144 return (0);
145 return (1);
146}
int32_t SDDS_CopyLayout(SDDS_DATASET *SDDS_target, SDDS_DATASET *SDDS_source)
Definition SDDS_copy.c:222

◆ SDDS_InitializeHeaderlessInput()

epicsShareFuncSDDS int32_t SDDS_InitializeHeaderlessInput ( SDDS_DATASET * SDDS_dataset,
char * filename )
extern

Initializes the SDDS dataset for headerless input.

This function initializes the SDDS dataset structure for reading data from a file without a header.

Parameters
SDDS_datasetA pointer to the SDDS_DATASET structure to be initialized.
filenameThe name of the file to read data from.
Returns
Returns 1 on success, 0 on failure.

Definition at line 176 of file SDDS_input.c.

176 {
177 /* char *ptr, *datafile; */
178
179 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_InitializeInput"))
180 return (0);
181 if (!SDDS_ZeroMemory((void *)SDDS_dataset, sizeof(SDDS_DATASET))) {
182 SDDS_SetError("Unable to initialize input--can't zero SDDS_DATASET structure (SDDS_InitializeInput)");
183 return (0);
184 }
185 SDDS_dataset->layout.gzipFile = SDDS_dataset->layout.lzmaFile = 0;
186 SDDS_dataset->layout.depth = SDDS_dataset->layout.data_command_seen = SDDS_dataset->layout.commentFlags = SDDS_dataset->deferSavingLayout = 0;
187 if (!(SDDS_dataset->layout.fp = fopen(filename, FOPEN_READ_MODE))) {
188 SDDS_SetError("Unable to open file (SDDS_InitializeInput)");
189 return (0);
190 }
191 if (!SDDS_CopyString(&SDDS_dataset->layout.filename, filename)) {
192 SDDS_SetError("Memory allocation failure (SDDS_InitializeInput)");
193 return (0);
194 }
195 SDDS_dataset->mode = SDDS_READMODE; /*reading */
196 SDDS_dataset->page_number = SDDS_dataset->page_started = 0;
197 SDDS_dataset->pages_read = 0;
198 SDDS_dataset->pagecount_offset = malloc(sizeof(*SDDS_dataset->pagecount_offset));
199 SDDS_dataset->pagecount_offset[0] = ftell(SDDS_dataset->layout.fp);
200 fseek(SDDS_dataset->layout.fp, 0, 2); /*point to the end of the file */
201 SDDS_dataset->endOfFile_offset = ftell(SDDS_dataset->layout.fp);
202 fseek(SDDS_dataset->layout.fp, SDDS_dataset->pagecount_offset[0], 0);
203 /*point to the beginning of the first page */
204 return (1);
205}

◆ SDDS_InitializeInput()

epicsShareFuncSDDS int32_t SDDS_InitializeInput ( SDDS_DATASET * SDDS_dataset,
char * filename )
extern

Initializes a SDDS_DATASET structure for use in reading data from a SDDS file. This involves opening the file and reading the SDDS header.

Parameters
SDDS_datasetAddress of the SDDS_DATASET structure for the data set.
filenameA NULL-terminated character string giving the name of the file to set up for input.
Returns
1 on success. On failure, returns 0 and records an error message.

Definition at line 50 of file SDDS_input.c.

50 {
51 /* char *ptr, *datafile, *headerfile; */
52 char s[SDDS_MAXLINE];
53#if defined(zLib)
54 char *extension;
55#endif
56 if (sizeof(gzFile) != sizeof(void *)) {
57 SDDS_SetError("gzFile is not the same size as void *, possible corruption of the SDDS_LAYOUT structure");
58 return (0);
59 }
60 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_InitializeInput"))
61 return (0);
62
63 if (!SDDS_ZeroMemory((void *)SDDS_dataset, sizeof(SDDS_DATASET))) {
64 sprintf(s, "Unable to initialize input for file %s--can't zero SDDS_DATASET structure (SDDS_InitializeInput)", filename);
66 return (0);
67 }
68 SDDS_dataset->layout.gzipFile = SDDS_dataset->layout.lzmaFile = SDDS_dataset->layout.disconnected = SDDS_dataset->layout.popenUsed = 0;
69 SDDS_dataset->layout.depth = SDDS_dataset->layout.data_command_seen = SDDS_dataset->layout.commentFlags = SDDS_dataset->deferSavingLayout = 0;
70 SDDS_dataset->layout.data_mode.column_memory_mode = DEFAULT_COLUMN_MEMORY_MODE;
71 if (!filename)
72 SDDS_dataset->layout.filename = NULL;
73 else if (!SDDS_CopyString(&SDDS_dataset->layout.filename, filename)) {
74 sprintf(s, "Memory allocation failure initializing file \"%s\" (SDDS_InitializeInput)", filename);
76 return (0);
77 }
78 if (!filename) {
79#if defined(_WIN32)
80 if (_setmode(_fileno(stdin), _O_BINARY) == -1) {
81 sprintf(s, "unable to set stdin to binary mode");
83 return 0;
84 }
85#endif
86 SDDS_dataset->layout.fp = stdin;
87 } else {
88#if defined(zLib)
89 if (!(extension = strrchr(filename, '.')) || strcmp(extension, ".gz") != 0) {
90#endif
91 if ((extension = strrchr(filename, '.')) && ((strcmp(extension, ".lzma") == 0) || (strcmp(extension, ".xz") == 0))) {
92 SDDS_dataset->layout.lzmaFile = 1;
93 if (!(SDDS_dataset->layout.lzmafp = UnpackLZMAOpen(filename))) {
94 sprintf(s, "Unable to open file \"%s\" for reading (SDDS_InitializeInput)", filename);
96 return (0);
97 }
98 SDDS_dataset->layout.fp = SDDS_dataset->layout.lzmafp->fp;
99 } else {
100 if (!(SDDS_dataset->layout.fp = UnpackFopen(filename, UNPACK_REQUIRE_SDDS | UNPACK_USE_PIPE, &SDDS_dataset->layout.popenUsed, NULL))) {
101 sprintf(s, "Unable to open file \"%s\" for reading (SDDS_InitializeInput)", filename);
102 SDDS_SetError(s);
103 return (0);
104 }
105 }
106#if defined(zLib)
107 } else {
108 SDDS_dataset->layout.gzipFile = 1;
109 if (!(SDDS_dataset->layout.gzfp = gzopen(filename, "rb"))) {
110 sprintf(s, "Unable to open file \"%s\" for reading (SDDS_InitializeInput)", filename);
111 SDDS_SetError(s);
112 return (0);
113 }
114 }
115#endif
116 }
117 SDDS_dataset->page_number = SDDS_dataset->page_started = 0;
118 SDDS_dataset->file_had_data = 0;
119 SDDS_DeferSavingLayout(SDDS_dataset, 1);
120#if defined(zLib)
121 if (SDDS_dataset->layout.gzipFile) {
122 if (!SDDS_GZipReadLayout(SDDS_dataset, SDDS_dataset->layout.gzfp))
123 return (0);
124 } else {
125#endif
126 if (SDDS_dataset->layout.lzmaFile) {
127 if (!SDDS_LZMAReadLayout(SDDS_dataset, SDDS_dataset->layout.lzmafp))
128 return (0);
129 } else {
130 if (!SDDS_ReadLayout(SDDS_dataset, SDDS_dataset->layout.fp))
131 return (0);
132 }
133#if defined(zLib)
134 }
135#endif
136 SDDS_dataset->layout.layout_written = 0;
137 SDDS_DeferSavingLayout(SDDS_dataset, 0);
138 if (!SDDS_SaveLayout(SDDS_dataset))
139 return 0;
140 if (SDDS_dataset->layout.n_columns &&
141 ((!(SDDS_dataset->column_flag = (int32_t *)SDDS_Malloc(sizeof(int32_t) * SDDS_dataset->layout.n_columns)) ||
142 !(SDDS_dataset->column_order = (int32_t *)SDDS_Malloc(sizeof(int32_t) * SDDS_dataset->layout.n_columns))) ||
143 (!SDDS_SetMemory(SDDS_dataset->column_flag, SDDS_dataset->layout.n_columns, SDDS_LONG, (int32_t)1, (int32_t)0) ||
144 !SDDS_SetMemory(SDDS_dataset->column_order, SDDS_dataset->layout.n_columns, SDDS_LONG, (int32_t)0, (int32_t)1)))) {
145 SDDS_SetError("Unable to initialize input--memory allocation failure (SDDS_InitializeInput)");
146 return (0);
147 }
148 SDDS_dataset->mode = SDDS_READMODE; /*reading */
149 SDDS_dataset->pagecount_offset = NULL;
150 if (!SDDS_dataset->layout.gzipFile && !SDDS_dataset->layout.lzmaFile && !SDDS_dataset->layout.popenUsed && SDDS_dataset->layout.filename) {
151 /* Data is not:
152 1. from a gzip file
153 2. from a file that is being internally decompressed by a command executed with popen()
154 3. from a pipe set up externally (e.g., -pipe=in on commandline)
155 */
156 SDDS_dataset->pages_read = 0;
157 SDDS_dataset->pagecount_offset = malloc(sizeof(*SDDS_dataset->pagecount_offset));
158 SDDS_dataset->pagecount_offset[0] = ftell(SDDS_dataset->layout.fp);
159 fseek(SDDS_dataset->layout.fp, 0, 2); /*point to the end of the file */
160 SDDS_dataset->endOfFile_offset = ftell(SDDS_dataset->layout.fp);
161 fseek(SDDS_dataset->layout.fp, SDDS_dataset->pagecount_offset[0], 0);
162 /*point to the beginning of the first page */
163 }
164 return (1);
165}
int32_t SDDS_LZMAReadLayout(SDDS_DATASET *SDDS_dataset, struct lzmafile *lzmafp)
Definition SDDS_input.c:681
FILE * UnpackFopen(char *filename, unsigned long mode, short *popenUsed, char **tmpFileUsed)
Opens a file, potentially unpacking it based on its extension and mode.
Definition unpack.c:89

◆ SDDS_InitializeInputFromSearchPath()

epicsShareFuncSDDS int32_t SDDS_InitializeInputFromSearchPath ( SDDS_DATASET * SDDSin,
char * file )
extern

Initializes the SDDS_DATASET structure for input from the search path.

The search path is defined by calling setSearchPath. This function attempts to find the file in the search path and initializes the SDDS dataset for input.

Parameters
SDDSinThe SDDS_DATASET structure to be initialized.
fileThe name of the file to be opened for input.
Returns
1 on success, 0 on failure.

Definition at line 1811 of file SDDS_input.c.

1811 {
1812 char *filename;
1813 int32_t value;
1814 if (!(filename = findFileInSearchPath(file))) {
1815 char *s;
1816 if (!(s = SDDS_Malloc(sizeof(*s) * (strlen(file) + 100))))
1817 SDDS_SetError("file does not exist in search path (InitializeInputFromSearchPath)");
1818 else {
1819 sprintf(s, "file %s does not exist in search path (InitializeInputFromSearchPath)", file);
1820 SDDS_SetError(s);
1821 free(s);
1822 }
1823 return 0;
1824 }
1825 value = SDDS_InitializeInput(SDDSin, filename);
1826 free(filename);
1827 return value;
1828}
int32_t SDDS_InitializeInput(SDDS_DATASET *SDDS_dataset, char *filename)
Definition SDDS_input.c:50
char * findFileInSearchPath(const char *filename)
Finds a file within the configured search path.
Definition searchPath.c:57

◆ SDDS_InitializeOutput()

epicsShareFuncSDDS int32_t SDDS_InitializeOutput ( SDDS_DATASET * SDDS_dataset,
int32_t data_mode,
int32_t lines_per_row,
const char * description,
const char * contents,
const char * filename )
extern

Initializes the SDDS output dataset.

This function sets up the SDDS dataset for output operations by initializing the necessary structures, configuring the data mode (ASCII, Binary, or Parallel), handling file opening (including compressed files), and setting dataset metadata such as description and contents. It ensures that the dataset is ready for writing data according to the specified parameters.

Parameters
[in,out]SDDS_datasetPointer to the SDDS_DATASET structure to be initialized for output.
[in]data_modeThe data mode for the output dataset. Acceptable values are:
  • SDDS_ASCII: ASCII text format.
  • SDDS_BINARY: Binary format.
  • SDDS_PARALLEL: Parallel processing mode.
[in]lines_per_rowThe number of lines per row in the output dataset. This parameter is used only for ASCII output and is typically set to 1.
[in]descriptionA string containing the description of the output dataset. Pass NULL if no description is desired.
[in]contentsA string detailing the contents of the output dataset. Pass NULL if no contents are desired.
[in]filenameThe name of the file to which the dataset will be written. If NULL, the dataset will be written to standard output.
Returns
  • 1 on successful initialization.
  • 0 if an error occurred during initialization. In this case, an error message is set internally.
Precondition
  • The SDDS_dataset pointer must be valid and point to a properly allocated SDDS_DATASET structure.
Postcondition
  • The dataset is configured for output according to the specified parameters.
  • The output file is opened and locked if a filename is provided.
  • The dataset's internal state reflects the initialization status.
Note
  • When using compressed file formats (e.g., .gz, .lzma, .xz), the output mode is forced to binary.
  • Environment variable SDDS_OUTPUT_ENDIANESS can be set to "big" or "little" to declare the byte order.
  • For ASCII output, ensure that lines_per_row is set appropriately to match the data structure.
Warning
  • Appending to compressed files is not supported and will result in an error.
  • Ensure that the specified file is not locked by another process to avoid initialization failures.
  • Changing data mode after initialization is not supported and may lead to undefined behavior.

Definition at line 602 of file SDDS_output.c.

602 {
603 char s[SDDS_MAXLINE];
604 char *extension;
605 char *outputEndianess = NULL;
606
607 if (data_mode == SDDS_PARALLEL)
608 return SDDS_Parallel_InitializeOutput(SDDS_dataset, description, contents, filename);
609
610 if (sizeof(gzFile) != sizeof(void *)) {
611 SDDS_SetError("gzFile is not the same size as void *, possible corruption of the SDDS_LAYOUT structure");
612 return (0);
613 }
614 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_InitializeOutput"))
615 return 0;
616 if (!SDDS_ZeroMemory((void *)SDDS_dataset, sizeof(SDDS_DATASET))) {
617 sprintf(s, "Unable to initialize output for file %s--can't zero SDDS_DATASET structure (SDDS_InitializeOutput)", filename);
618 SDDS_SetError(s);
619 return 0;
620 }
621 SDDS_dataset->layout.popenUsed = SDDS_dataset->layout.gzipFile = SDDS_dataset->layout.lzmaFile = SDDS_dataset->layout.disconnected = 0;
622 SDDS_dataset->layout.depth = SDDS_dataset->layout.data_command_seen = SDDS_dataset->layout.commentFlags = SDDS_dataset->deferSavingLayout = 0;
623 if (!filename) {
624#if defined(_WIN32)
625 if (_setmode(_fileno(stdout), _O_BINARY) == -1) {
626 sprintf(s, "unable to set stdout to binary mode");
627 SDDS_SetError(s);
628 return 0;
629 }
630#endif
631 SDDS_dataset->layout.fp = stdout;
632 } else {
633 if (SDDS_FileIsLocked(filename)) {
634 sprintf(s, "unable to open file %s for writing--file is locked (SDDS_InitializeOutput)", filename);
635 SDDS_SetError(s);
636 return 0;
637 }
638 if ((extension = strrchr(filename, '.')) && ((strcmp(extension, ".xz") == 0) || (strcmp(extension, ".lzma") == 0))) {
639 SDDS_dataset->layout.lzmaFile = 1;
640 data_mode = SDDS_BINARY; /* force binary mode for output lzma files. The reading of ascii lzma files is flaky because of the lzma_gets command, plus the output files will be much smaller */
641 if (!(SDDS_dataset->layout.lzmafp = lzma_open(filename, FOPEN_WRITE_MODE))) {
642 sprintf(s, "Unable to open file %s for writing (SDDS_InitializeOutput)", filename);
643 SDDS_SetError(s);
644 return 0;
645 }
646 SDDS_dataset->layout.fp = SDDS_dataset->layout.lzmafp->fp;
647 } else {
648 if (!(SDDS_dataset->layout.fp = fopen(filename, FOPEN_WRITE_MODE))) {
649 sprintf(s, "Unable to open file %s for writing (SDDS_InitializeOutput)", filename);
650 SDDS_SetError(s);
651 return 0;
652 }
653 }
654 if (!SDDS_LockFile(SDDS_dataset->layout.fp, filename, "SDDS_InitializeOutput"))
655 return 0;
656#if defined(zLib)
657 if ((extension = strrchr(filename, '.')) && (strcmp(extension, ".gz") == 0)) {
658 SDDS_dataset->layout.gzipFile = 1;
659 if ((SDDS_dataset->layout.gzfp = gzdopen(fileno(SDDS_dataset->layout.fp), FOPEN_WRITE_MODE)) == NULL) {
660 sprintf(s, "Unable to open compressed file %s for writing (SDDS_InitializeOutput)", filename);
661 SDDS_SetError(s);
662 return 0;
663 }
664 }
665#endif
666 }
667 SDDS_dataset->page_number = SDDS_dataset->page_started = 0;
668 SDDS_dataset->file_had_data = SDDS_dataset->layout.layout_written = 0;
669 if (!filename)
670 SDDS_dataset->layout.filename = NULL;
671 else if (!SDDS_CopyString(&SDDS_dataset->layout.filename, filename)) {
672 sprintf(s, "Memory allocation failure initializing file %s (SDDS_InitializeOutput)", filename);
673 SDDS_SetError(s);
674 return 0;
675 }
676 if ((outputEndianess = getenv("SDDS_OUTPUT_ENDIANESS"))) {
677 if (strncmp(outputEndianess, "big", 3) == 0)
678 SDDS_dataset->layout.byteOrderDeclared = SDDS_BIGENDIAN;
679 else if (strncmp(outputEndianess, "little", 6) == 0)
680 SDDS_dataset->layout.byteOrderDeclared = SDDS_LITTLEENDIAN;
681 } else {
682 SDDS_dataset->layout.byteOrderDeclared = SDDS_IsBigEndianMachine() ? SDDS_BIGENDIAN : SDDS_LITTLEENDIAN;
683 }
684
685 if (data_mode < 0 || data_mode > SDDS_NUM_DATA_MODES) {
686 sprintf(s, "Invalid data mode for file %s (SDDS_InitializeOutput)", filename ? filename : "stdout");
687 SDDS_SetError(s);
688 return 0;
689 }
690 if (data_mode == SDDS_ASCII && lines_per_row <= 0) {
691 sprintf(s, "Invalid number of lines per row for file %s (SDDS_InitializeOutput)", filename ? filename : "stdout");
692 SDDS_SetError(s);
693 return 0;
694 }
695 SDDS_dataset->layout.version = SDDS_VERSION;
696 SDDS_dataset->layout.data_mode.mode = data_mode;
697 SDDS_dataset->layout.data_mode.lines_per_row = lines_per_row;
698 SDDS_dataset->layout.data_mode.no_row_counts = 0;
699 SDDS_dataset->layout.data_mode.fixed_row_count = 0;
700 SDDS_dataset->layout.data_mode.fsync_data = 0;
701 SDDS_dataset->layout.data_mode.column_memory_mode = DEFAULT_COLUMN_MEMORY_MODE;
702 /*This is only temporary, soon the default will be column major order */
703 SDDS_dataset->layout.data_mode.column_major = 0;
704 if (description && !SDDS_CopyString(&SDDS_dataset->layout.description, description)) {
705 sprintf(s, "Memory allocation failure initializing file %s (SDDS_InitializeOutput)", filename ? filename : "stdout");
706 SDDS_SetError(s);
707 return 0;
708 }
709 if (contents && !SDDS_CopyString(&SDDS_dataset->layout.contents, contents)) {
710 sprintf(s, "Memory allocation failure initializing file %s (SDDS_InitializeOutput)", filename ? filename : "stdout");
711 SDDS_SetError(s);
712 return 0;
713 }
714 SDDS_dataset->mode = SDDS_WRITEMODE; /*writing */
715 SDDS_dataset->pagecount_offset = NULL;
716 SDDS_dataset->parallel_io = 0;
717 return (1);
718}
int32_t SDDS_Parallel_InitializeOutput(SDDS_DATASET *SDDS_dataset, const char *description, const char *contents, const char *filename)
Initializes the SDDS output dataset for parallel processing.
int32_t SDDS_IsBigEndianMachine()
Determines whether the current machine uses big-endian byte ordering.

◆ SDDS_InterpretEscapes()

epicsShareFuncSDDS void SDDS_InterpretEscapes ( char * s)
extern

Interprets and converts escape sequences in a string.

This function processes a string containing escape sequences and converts them into their corresponding character representations. Supported escape sequences include:

  • Standard ANSI escape codes: \n, \t, \b, \r, \f, \v, \\, \', \", \a, \?
  • Octal values: \ddd
  • SDDS-specific escape codes: \!, \)

The function modifies the input string s in place, replacing escape sequences with their actual character values.

Parameters
[in,out]sPointer to the null-terminated string to be processed. The string will be modified in place.
Note
  • Ensure that the input string s has sufficient buffer space to accommodate the modified characters, especially when dealing with octal escape sequences that may reduce the overall string length.
Warning
  • The function does not perform bounds checking. Ensure that the input string is properly null-terminated to prevent undefined behavior.
  • Unrecognized escape sequences (other than the ones specified) will result in the backslash being retained in the string.
See also
SDDS_EscapeNewlines, SDDS_UnescapeNewlines

Definition at line 5173 of file SDDS_utils.c.

5178{
5179 char *ptr;
5180 int32_t count;
5181
5182 ptr = s;
5183 while (*s) {
5184 if (*s != '\\')
5185 *ptr++ = *s++;
5186 else {
5187 s++;
5188 if (!*s) {
5189 *ptr++ = '\\';
5190 *ptr++ = 0;
5191 return;
5192 }
5193 switch (*s) {
5194 case 'n':
5195 *ptr++ = '\n';
5196 s++;
5197 break;
5198 case 't':
5199 *ptr++ = '\t';
5200 s++;
5201 break;
5202 case 'b':
5203 *ptr++ = '\b';
5204 s++;
5205 break;
5206 case 'r':
5207 *ptr++ = '\r';
5208 s++;
5209 break;
5210 case 'f':
5211 *ptr++ = '\f';
5212 s++;
5213 break;
5214 case 'v':
5215 *ptr++ = '\v';
5216 s++;
5217 break;
5218 case '\\':
5219 *ptr++ = '\\';
5220 s++;
5221 break;
5222 case '\'':
5223 *ptr++ = '\'';
5224 s++;
5225 break;
5226 case '"':
5227 *ptr++ = '\"';
5228 s++;
5229 break;
5230 case 'a':
5231 *ptr++ = '\a';
5232 s++;
5233 break;
5234 case '?':
5235 *ptr++ = '\?';
5236 s++;
5237 break;
5238 case '!':
5239 *ptr++ = '!';
5240 s++;
5241 break;
5242 default:
5243 if (*s >= '0' && *s <= '9') {
5244 *ptr = 0;
5245 count = 0;
5246 while (++count <= 3 && *s >= '0' && *s <= '9')
5247 *ptr = 8 * (*ptr) + *s++ - '0';
5248 ptr++;
5249 } else {
5250 *ptr++ = '\\';
5251 }
5252 break;
5253 }
5254 }
5255 }
5256 *ptr = 0;
5257}

◆ SDDS_IsActive()

epicsShareFuncSDDS int32_t SDDS_IsActive ( SDDS_DATASET * SDDS_dataset)
extern

Checks whether an SDDS dataset is currently active.

This function determines the active status of the provided SDDS dataset by verifying if its file pointer is non-NULL.

Parameters
[in]SDDS_datasetPointer to the SDDS_DATASET structure to be checked.
Returns
  • 1 if the dataset is active (i.e., the file pointer is non-NULL).
  • 0 if the dataset is inactive (i.e., the file pointer is NULL).
  • -1 if a NULL pointer is passed, indicating an error.
Note
An inactive dataset does not have an associated open file, and certain operations may not be applicable.
See also
SDDS_ForceInactive, SDDS_SetError

Definition at line 3325 of file SDDS_utils.c.

3325 {
3326 if (!SDDS_dataset) {
3327 SDDS_SetError("NULL SDDS_DATASET passed (SDDS_IsActive)");
3328 return (-1);
3329 }
3330 if (!SDDS_dataset->layout.fp)
3331 return (0);
3332 return (1);
3333}

◆ SDDS_IsBigEndianMachine()

epicsShareFuncSDDS int32_t SDDS_IsBigEndianMachine ( )
extern

Determines whether the current machine uses big-endian byte ordering.

This function checks the byte order of the machine on which the program is running. It returns 1 if the machine is big-endian and 0 if it is little-endian.

Returns
  • 1 if the machine is big-endian.
  • 0 if the machine is little-endian.
Note
  • Endianness detection is based on inspecting the byte order of an integer value.
Warning
  • This function assumes that int32_t is 4 bytes in size. If compiled on a system where int32_t differs in size, the behavior may be incorrect.
See also
SDDS_SetDataMode

Definition at line 5374 of file SDDS_utils.c.

5374 {
5375 int32_t x = 1;
5376 if (*((char *)&x))
5377 return 0;
5378 return 1;
5379}

◆ SDDS_IsQuoted()

epicsShareFuncSDDS int32_t SDDS_IsQuoted ( char * string,
char * position,
char quotation_mark )
extern

Checks if a position in a string is within a quoted section.

Determines whether the specified position within a string falls inside a quoted section delimited by the given quotation mark.

Parameters
stringThe string to examine.
positionThe position within the string to check.
quotation_markThe character used as the quotation mark.
Returns
Returns 1 if the position is within a quoted section, 0 otherwise.

Definition at line 218 of file SDDS_input.c.

218 {
219 int32_t in_quoted_section;
220 char *string0;
221
222 if (*position == quotation_mark)
223 return (1);
224
225 in_quoted_section = 0;
226 string0 = string;
227 while (*string) {
228 if (*string == quotation_mark && (string == string0 || *(string - 1) != '\\'))
229 in_quoted_section = !in_quoted_section;
230 else if (string == position)
231 return (in_quoted_section);
232 string++;
233 }
234 return (0);
235}

◆ SDDS_IsValidName()

epicsShareFuncSDDS int32_t SDDS_IsValidName ( const char * name,
const char * class )
extern

Checks if a given name is valid for a specified class within the SDDS dataset.

This function validates whether the provided name adheres to the naming conventions and rules defined by the current name validity flags for the specified class (e.g., parameter, column). It ensures that the name contains only allowed characters and follows the required structure.

Parameters
[in]nameThe name to be validated. Must be a NULL-terminated string.
[in]classThe class type to which the name belongs (e.g., "parameter", "column"). This is used primarily for error reporting.
Returns
  • 1 if the name is valid for the specified class.
  • 0 if the name is invalid, with an error message set internally.
Precondition
  • The name must be a valid NULL-terminated string.
  • The class must be a valid NULL-terminated string representing a recognized class type.
Postcondition
  • If the name is invalid, an error message is recorded detailing the reason.
Note
  • The validation rules are influenced by the current name validity flags set via SDDS_SetNameValidityFlags.
  • Environment variables or other configuration settings may also affect name validity.
Warning
  • Using names that do not adhere to the validation rules will result in parameters or columns not being defined.
  • Ensure that all names meet the required standards before attempting to define dataset elements.

Definition at line 2099 of file SDDS_output.c.

2099 {
2100 char *ptr;
2101 int32_t isValid = 1;
2102 char s[SDDS_MAXLINE];
2103 static const char *const validChars = "@:#+%-._$&/[]";
2104 static const char *const startChars = ".:";
2105 uint32_t flags = SDDS_GetLockedNameValidityFlags();
2106
2107 if (flags & SDDS_ALLOW_ANY_NAME)
2108 return 1;
2109 ptr = (char *)name;
2110 if (strlen(name) == 0)
2111 isValid = 0;
2112 else if (!(flags & SDDS_ALLOW_V15_NAME)) {
2113 /* post V1.5 allows only alpha and startChars members as first character */
2114 /* V1.5 allows alpha, digits, and any validChars members */
2115 if (!(isalpha(*ptr) || strchr(startChars, *ptr)))
2116 isValid = 0;
2117 }
2118 while (isValid && *ptr) {
2119 if (!(isalnum(*ptr) || strchr(validChars, *ptr)))
2120 isValid = 0;
2121 ptr++;
2122 }
2123 if (!isValid) {
2124 sprintf(s, "The following %s name is invalid: >%s<\n(sddsconvert may be used to change the name)\n", class, name);
2125 SDDS_SetError(s);
2126 return 0;
2127 }
2128 return 1;
2129}

◆ SDDS_ItemInsideWindow()

epicsShareFuncSDDS int32_t SDDS_ItemInsideWindow ( void * data,
int64_t index,
int32_t type,
double lower_limit,
double upper_limit )
extern

Checks whether a data item is within a specified numeric window.

This function determines if the data item at the given index within the data array falls within the range defined by lower_limit and upper_limit. It handles various numeric data types and ensures that the value is neither NaN nor infinity.

Parameters
dataPointer to the data array.
indexThe index of the item within the data array to be checked.
typeThe data type of the item. Supported types include:
  • SDDS_SHORT
  • SDDS_USHORT
  • SDDS_LONG
  • SDDS_ULONG
  • SDDS_LONG64
  • SDDS_ULONG64
  • SDDS_FLOAT
  • SDDS_DOUBLE
  • SDDS_LONGDOUBLE
lower_limitThe lower bound of the numeric window.
upper_limitThe upper bound of the numeric window.
Returns
Returns 1 if the item is within the window and valid, otherwise returns 0.
Return values
1Indicates that the item is within the specified numeric window and is a valid number.
0Indicates that the item is outside the specified window, is NaN, is infinite, or the data type is non-numeric.
Note
  • The function sets an error message if the data type is non-numeric.
  • It is essential to ensure that the data array is properly initialized and contains valid data before calling this function.
See also
SDDS_FilterRowsOfInterest, SDDS_GetParameterAsDouble

Definition at line 4078 of file SDDS_extract.c.

4078 {
4079 short short_val;
4080 unsigned short ushort_val;
4081 int32_t long_val;
4082 uint32_t ulong_val;
4083 int64_t long64_val;
4084 uint64_t ulong64_val;
4085 long double ldouble_val;
4086 double double_val;
4087 float float_val;
4088
4089 switch (type) {
4090 case SDDS_SHORT:
4091 if ((short_val = *((short *)data + index)) < lower_limit || short_val > upper_limit)
4092 return (0);
4093 return (1);
4094 case SDDS_USHORT:
4095 if ((ushort_val = *((unsigned short *)data + index)) < lower_limit || ushort_val > upper_limit)
4096 return (0);
4097 return (1);
4098 case SDDS_LONG:
4099 if ((long_val = *((int32_t *)data + index)) < lower_limit || long_val > upper_limit)
4100 return (0);
4101 return (1);
4102 case SDDS_ULONG:
4103 if ((ulong_val = *((uint32_t *)data + index)) < lower_limit || ulong_val > upper_limit)
4104 return (0);
4105 return (1);
4106 case SDDS_LONG64:
4107 if ((long64_val = *((int64_t *)data + index)) < lower_limit || long64_val > upper_limit)
4108 return (0);
4109 return (1);
4110 case SDDS_ULONG64:
4111 if ((ulong64_val = *((uint64_t *)data + index)) < lower_limit || ulong64_val > upper_limit)
4112 return (0);
4113 return (1);
4114 case SDDS_FLOAT:
4115 if ((float_val = *((float *)data + index)) < lower_limit || float_val > upper_limit)
4116 return (0);
4117 if (isnan(float_val) || isinf(float_val))
4118 return 0;
4119 return (1);
4120 case SDDS_DOUBLE:
4121 if ((double_val = *((double *)data + index)) < lower_limit || double_val > upper_limit)
4122 return 0;
4123 if (isnan(double_val) || isinf(double_val))
4124 return 0;
4125 return (1);
4126 case SDDS_LONGDOUBLE:
4127 if ((ldouble_val = *((long double *)data + index)) < lower_limit || ldouble_val > upper_limit)
4128 return 0;
4129 if (isnan(ldouble_val) || isinf(ldouble_val))
4130 return 0;
4131 return (1);
4132 default:
4133 SDDS_SetError("Unable to complete window check--item type is non-numeric (SDDS_ItemInsideWindow)");
4134 return (0);
4135 }
4136}

◆ SDDS_LengthenTable()

epicsShareFuncSDDS int32_t SDDS_LengthenTable ( SDDS_DATASET * SDDS_dataset,
int64_t n_additional_rows )
extern

Increases the number of allocated rows in the SDDS dataset's data table.

This function extends the allocated memory for the data table in the specified SDDS dataset by adding the specified number of additional rows. It reallocates memory for each column's data array and the row flags, initializing the newly allocated memory to zero.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure whose table will be lengthened.
n_additional_rowsThe number of additional rows to allocate. If n_additional_rows is less than zero, it is treated as zero.
Returns
Returns 1 on successful reallocation and initialization. On failure, returns 0 and records an error message.
See also
SDDS_Realloc, SDDS_SetMemory, SDDS_ZeroMemory, SDDS_SetError

Definition at line 303 of file SDDS_dataprep.c.

303 {
304 SDDS_LAYOUT *layout;
305 int64_t i, size;
306 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_LengthenTable"))
307 return (0);
308 layout = &SDDS_dataset->layout;
309#if defined(DEBUG)
310 fprintf(stderr, "table size being increased from %" PRId64 " to %" PRId64 " rows\n", SDDS_dataset->n_rows_allocated, SDDS_dataset->n_rows_allocated + n_additional_rows);
311#endif
312 if (!SDDS_dataset->data && !(SDDS_dataset->data = (void **)calloc(layout->n_columns, sizeof(*SDDS_dataset->data)))) {
313 SDDS_SetError("Unable to start page--memory allocation failure1 (SDDS_LengthenTable)");
314 return (0);
315 }
316 if (n_additional_rows < 0)
317 n_additional_rows = 0;
318 for (i = 0; i < layout->n_columns; i++) {
319 size = SDDS_type_size[layout->column_definition[i].type - 1];
320 if (!(SDDS_dataset->data[i] = (void *)SDDS_Realloc(SDDS_dataset->data[i], (SDDS_dataset->n_rows_allocated + n_additional_rows) * size))) {
321 SDDS_SetError("Unable to lengthen page--memory allocation failure2 (SDDS_LengthenTable)");
322 return (0);
323 }
324 SDDS_ZeroMemory((char *)SDDS_dataset->data[i] + size * SDDS_dataset->n_rows_allocated, size * n_additional_rows);
325 }
326 if (!(SDDS_dataset->row_flag = (int32_t *)SDDS_Realloc(SDDS_dataset->row_flag, (SDDS_dataset->n_rows_allocated + n_additional_rows) * sizeof(int32_t)))) {
327 SDDS_SetError("Unable to lengthen page--memory allocation failure3 (SDDS_LengthenTable)");
328 return (0);
329 }
330 SDDS_dataset->n_rows_allocated += n_additional_rows;
331
332 if (!SDDS_SetMemory(SDDS_dataset->row_flag, SDDS_dataset->n_rows_allocated, SDDS_LONG, (int32_t)1, (int32_t)0) ||
333 !SDDS_SetMemory(SDDS_dataset->column_flag, SDDS_dataset->layout.n_columns, SDDS_LONG, (int32_t)1, (int32_t)0) ||
334 !SDDS_SetMemory(SDDS_dataset->column_order, SDDS_dataset->layout.n_columns, SDDS_LONG, (int32_t)0, (int32_t)1)) {
335 SDDS_SetError("Unable to lengthen page--memory initialization failure4 (SDDS_LengthenTable)");
336 return (0);
337 }
338 return (1);
339}

◆ SDDS_LockFile()

epicsShareFuncSDDS int32_t SDDS_LockFile ( FILE * fp,
const char * filename,
const char * caller )
extern

Attempts to lock a specified file.

This function tries to acquire a lock on the provided file using the given file pointer. If file locking is enabled via the F_TEST and ALLOW_FILE_LOCKING macros, it first tests whether the file can be locked and then attempts to establish an exclusive lock. If locking fails at any step, an error message is set, and the function returns 0.

If file locking is not enabled, the function assumes that the file is not locked and returns 1.

Parameters
[in]fpPointer to the open FILE stream associated with the file to be locked.
[in]filenameThe path to the file to be locked. Used primarily for error messaging.
[in]callerA string identifying the caller or the context in which the lock is being attempted. This is used in error messages to provide more information about the lock attempt.
Returns
  • 1 if the file lock is successfully acquired or if file locking is not enabled.
  • 0 if the file is already locked or if locking fails for another reason.
Note
The function relies on the lockf system call for file locking, which may not be supported on all platforms.
Warning
Proper error handling should be implemented by the caller to handle cases where file locking fails.
See also
SDDS_FileIsLocked, SDDS_SetError

Definition at line 3401 of file SDDS_utils.c.

3401 {
3402#if defined(F_TEST) && ALLOW_FILE_LOCKING
3403 char s[1024];
3404 if (lockf(fileno(fp), F_TEST, 0) == -1) {
3405 sprintf(s, "Unable to access file %s--file is locked (%s)", filename, caller);
3406 SDDS_SetError(s);
3407 return 0;
3408 }
3409 if (lockf(fileno(fp), F_TLOCK, 0) == -1) {
3410 sprintf(s, "Unable to establish lock on file %s (%s)", filename, caller);
3411 SDDS_SetError(s);
3412 return 0;
3413 }
3414 return 1;
3415#else
3416 return 1;
3417#endif
3418}

◆ SDDS_Logic()

epicsShareFuncSDDS int32_t SDDS_Logic ( int32_t previous,
int32_t match,
uint32_t logic )
extern

Applies logical operations to determine the new state of a row flag based on previous and current match conditions.

This function evaluates logical conditions between a previous flag (previous) and a current match flag (match) based on the provided logic flags. It supports various logical operations such as AND, OR, negation of previous flags, and negation of match results.

Parameters
previousThe previous state of the row flag (typically 0 or 1).
matchThe current match result to be combined with the previous flag.
logicAn unsigned integer representing logical operation flags. Supported flags include:
  • SDDS_0_PREVIOUS: Set the previous flag to 0.
  • SDDS_1_PREVIOUS: Set the previous flag to 1.
  • SDDS_NEGATE_PREVIOUS: Negate the previous flag.
  • SDDS_NEGATE_MATCH: Negate the current match result.
  • SDDS_AND: Perform a logical AND between the previous flag and the match result.
  • SDDS_OR: Perform a logical OR between the previous flag and the match result.
  • SDDS_NEGATE_EXPRESSION: Negate the final logical expression result.
Returns
Returns the result of the logical operation as an integer (0 or 1).
Return values
1Indicates that the final logical condition evaluates to true.
0Indicates that the final logical condition evaluates to false.
Note
  • Multiple logic flags can be combined using bitwise OR to perform complex logical operations.
  • The order of operations follows the precedence defined within the function implementation.
See also
SDDS_SetRowsOfInterest, SDDS_MatchRowsOfInterest

Definition at line 4166 of file SDDS_extract.c.

4166 {
4167 if (logic & SDDS_0_PREVIOUS)
4168 previous = 0;
4169 else if (logic & SDDS_1_PREVIOUS)
4170 previous = 1;
4171 if (logic & SDDS_NEGATE_PREVIOUS)
4172 previous = !previous;
4173 if (logic & SDDS_NEGATE_MATCH)
4174 match = !match;
4175 if (logic & SDDS_AND)
4176 match = match && previous;
4177 else if (logic & SDDS_OR)
4178 match = match || previous;
4179 else
4180 match = previous;
4181 if (logic & SDDS_NEGATE_EXPRESSION)
4182 match = !match;
4183 return (match);
4184}

◆ SDDS_MakePointerArray()

epicsShareFuncSDDS void * SDDS_MakePointerArray ( void * data,
int32_t type,
int32_t dimensions,
int32_t * dimension )
extern

Creates a multi-dimensional pointer array from a contiguous data block.

This function generates a multi-dimensional pointer array that maps to a contiguous block of data. It supports arrays with multiple dimensions by recursively creating pointer layers. The dimensions parameter specifies the number of dimensions, and the dimension array provides the size for each dimension.

Parameters
[in]dataPointer to the contiguous data block to be mapped.
[in]typeThe SDDS data type of the elements in the data block. Must be one of the SDDS type constants:
  • SDDS_SHORT
  • SDDS_USHORT
  • SDDS_LONG
  • SDDS_ULONG
  • SDDS_LONG64
  • SDDS_ULONG64
  • SDDS_FLOAT
  • SDDS_DOUBLE
  • SDDS_LONGDOUBLE
  • SDDS_CHARACTER
[in]dimensionsThe number of dimensions for the pointer array.
[in]dimensionAn array specifying the size of each dimension.
Returns
  • Returns a pointer to the newly created multi-dimensional pointer array on success.
  • Returns NULL if the input data is NULL, the dimension array is invalid, the type is unknown, or memory allocation fails.
Note
  • The function uses SDDS_MakePointerArrayRecursively to handle multi-dimensional allocations.
  • The caller is responsible for freeing the allocated pointer array using SDDS_FreePointerArray.
See also
SDDS_MakePointerArrayRecursively
SDDS_FreePointerArray
SDDS_SetError

Definition at line 3046 of file SDDS_utils.c.

3046 {
3047 int32_t i;
3048
3049 if (!data) {
3050 SDDS_SetError("Unable to make pointer array--NULL data array (SDDS_MakePointerArray)");
3051 return (NULL);
3052 }
3053 if (!dimension || !dimensions) {
3054 SDDS_SetError("Unable to make pointer array--NULL or zero-length dimension array (SDDS_MakePointerArray)");
3055 return (NULL);
3056 }
3057 if (type <= 0 || type > SDDS_NUM_TYPES) {
3058 SDDS_SetError("Unable to make pointer array--unknown data type (SDDS_MakePointerArray)");
3059 return (NULL);
3060 }
3061 for (i = 0; i < dimensions; i++)
3062 if (dimension[i] <= 0) {
3063 SDDS_SetError("Unable to make pointer array--number of elements invalid (SDDS_MakePointerArray)");
3064 return (NULL);
3065 }
3066 if (dimensions == 1)
3067 return (data);
3068 return (SDDS_MakePointerArrayRecursively(data, SDDS_type_size[type - 1], dimensions, dimension));
3069}
void * SDDS_MakePointerArrayRecursively(void *data, int32_t size, int32_t dimensions, int32_t *dimension)
Recursively creates a multi-dimensional pointer array from a contiguous data block.

◆ SDDS_Malloc()

epicsShareFuncSDDS void * SDDS_Malloc ( size_t size)
extern

Allocates memory of a specified size.

This function is a wrapper around the standard malloc function, used by SDDS routines to allocate memory. It ensures that a minimum allocation size is enforced.

Parameters
[in]sizeNumber of bytes to allocate.
Returns
Pointer to the allocated memory. If size is less than or equal to zero, it allocates memory for 4 bytes by default. Returns NULL if memory allocation fails.
Note
Users should always check the returned pointer for NULL before using it.
See also
SDDS_Calloc
SDDS_Free

Definition at line 705 of file SDDS_utils.c.

705 {
706 if (size <= 0)
707 size = 4;
708 return malloc(size);
709}

◆ SDDS_MatchArrays()

epicsShareFuncSDDS int32_t SDDS_MatchArrays ( SDDS_DATASET * SDDS_dataset,
char *** nameReturn,
int32_t matchMode,
int32_t typeMode,
... )
extern

Matches and retrieves array names from an SDDS dataset based on specified criteria.

This function selects arrays from the provided SDDS dataset according to the specified matching mode and type mode. It supports various calling conventions depending on the matching criteria.

The function supports the following matching modes:

  • SDDS_NAME_ARRAY:
    • Parameters: int32_t n_entries, char **name
    • Description: Matches arrays whose names are present in the provided array.
  • SDDS_NAMES_STRING:
    • Parameters: char *names
    • Description: Matches arrays whose names are specified in a single comma-separated string.
  • SDDS_NAME_STRINGS:
    • Parameters: char *name1, char *name2, ..., NULL
    • Description: Matches arrays whose names are specified as individual string arguments, terminated by a NULL pointer.
  • SDDS_MATCH_STRING:
    • Parameters: char *name, int32_t logic_mode
    • Description: Matches arrays based on a wildcard pattern provided in name, using the specified logical mode.
  • SDDS_MATCH_EXCLUDE_STRING:
    • Parameters: char *name, char *exclude, int32_t logic_mode
    • Description: Matches arrays based on a wildcard pattern provided in name, excluding those that match the exclude pattern, using the specified logical mode.

Additionally, the typeMode parameter allows filtering based on array types, such as numeric, floating, or integer types.

Parameters
[in]SDDS_datasetPointer to the SDDS_DATASET structure containing the dataset.
[out]nameReturnPointer to a char** that will be allocated and populated with the names of the matched arrays. The caller is responsible for freeing the allocated memory.
[in]matchModeSpecifies the matching mode (e.g., SDDS_NAME_ARRAY, SDDS_NAMES_STRING, etc.).
[in]typeModeSpecifies the type matching mode (e.g., FIND_SPECIFIED_TYPE, FIND_NUMERIC_TYPE, FIND_FLOATING_TYPE, FIND_INTEGER_TYPE).
[in]...Variable arguments depending on matchMode:
  • SDDS_NAME_ARRAY: int32_t n_entries, char **name
  • SDDS_NAMES_STRING: char *names
  • SDDS_NAME_STRINGS: char *name1, char *name2, ..., NULL
  • SDDS_MATCH_STRING: char *name, int32_t logic_mode
  • SDDS_MATCH_EXCLUDE_STRING: char *name, char *exclude, int32_t logic_mode
Returns
  • Returns the number of matched arrays on success.
  • Returns -1 if an error occurs (e.g., invalid parameters, memory allocation failure).
Note
  • The function internally manages memory for the matching process and allocates memory for nameReturn, which must be freed by the caller using appropriate memory deallocation functions.
  • The dataset must be properly initialized and contain a valid layout before calling this function.
Warning
  • Ensure that the variable arguments match the expected parameters for the specified matchMode.
  • The caller is responsible for freeing the memory allocated for nameReturn to avoid memory leaks.
See also
SDDS_MatchColumns, SDDS_MatchParameters, SDDS_SetError

Definition at line 4121 of file SDDS_utils.c.

4129{
4130 static MDB_THREAD_LOCAL int32_t flags = 0, *flag = NULL;
4131 char **name, *string, *match_string, *ptr, *exclude_string;
4132 va_list argptr;
4133 int32_t i, j, index, n_names, retval, requiredType, matches;
4134 /* int32_t type; */
4135 int32_t local_memory; /* (0,1,2) --> (none, pointer array, pointer array + strings) locally allocated */
4136 char buffer[SDDS_MAXLINE];
4137 int32_t logic;
4138
4139 name = NULL;
4140 match_string = exclude_string = NULL;
4141 n_names = requiredType = local_memory = logic = 0;
4142
4143 matches = -1;
4144 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_MatchArrays"))
4145 return -1;
4146 if (nameReturn)
4147 *nameReturn = NULL;
4148
4149 retval = 1;
4150 va_start(argptr, typeMode);
4151 if (typeMode == FIND_SPECIFIED_TYPE)
4152 requiredType = va_arg(argptr, int32_t);
4153 switch (matchMode) {
4154 case SDDS_NAME_ARRAY:
4155 local_memory = 0;
4156 n_names = va_arg(argptr, int32_t);
4157 name = va_arg(argptr, char **);
4158 break;
4159 case SDDS_NAMES_STRING:
4160 local_memory = 2;
4161 n_names = 0;
4162 name = NULL;
4163 ptr = va_arg(argptr, char *);
4164 SDDS_CopyString(&string, ptr);
4165 while ((ptr = strchr(string, ',')))
4166 *ptr = ' ';
4167 while ((SDDS_GetToken(string, buffer, SDDS_MAXLINE) > 0)) {
4168 if (!(name = SDDS_Realloc(name, sizeof(*name) * (n_names + 1))) || !SDDS_CopyString(name + n_names, buffer)) {
4169 SDDS_SetError("Unable to process array selection--memory allocation failure (SDDS_MatchArrays)");
4170 retval = 0;
4171 break;
4172 }
4173 n_names++;
4174 }
4175 free(string);
4176 break;
4177 case SDDS_NAME_STRINGS:
4178 local_memory = 1;
4179 n_names = 0;
4180 name = NULL;
4181 while ((string = va_arg(argptr, char *))) {
4182 if (!(name = SDDS_Realloc(name, sizeof(*name) * (n_names + 1)))) {
4183 SDDS_SetError("Unable to process array selection--memory allocation failure (SDDS_MatchArrays)");
4184 retval = 0;
4185 break;
4186 }
4187 name[n_names++] = string;
4188 }
4189 break;
4190 case SDDS_MATCH_STRING:
4191 local_memory = 0;
4192 n_names = 1;
4193 if (!(string = va_arg(argptr, char *))) {
4194 SDDS_SetError("Unable to process array selection--invalid matching string (SDDS_MatchArrays)");
4195 retval = 0;
4196 break;
4197 }
4198 match_string = expand_ranges(string);
4199 logic = va_arg(argptr, int32_t);
4200 break;
4201 case SDDS_MATCH_EXCLUDE_STRING:
4202 local_memory = 0;
4203 n_names = 1;
4204 if (!(string = va_arg(argptr, char *))) {
4205 SDDS_SetError("Unable to process array selection--invalid matching string (SDDS_MatchArrays)");
4206 retval = 0;
4207 break;
4208 }
4209 match_string = expand_ranges(string);
4210 if (!(string = va_arg(argptr, char *))) {
4211 SDDS_SetError("Unable to process array exclusion--invalid matching string (SDDS_MatchArrays)");
4212 retval = 0;
4213 break;
4214 }
4215 exclude_string = expand_ranges(string);
4216 logic = va_arg(argptr, int32_t);
4217 break;
4218 default:
4219 SDDS_SetError("Unable to process array selection--unknown match mode (SDDS_MatchArrays)");
4220 retval = 0;
4221 break;
4222 }
4223 va_end(argptr);
4224 if (retval == 0)
4225 return -1;
4226
4227 if (n_names == 0) {
4228 SDDS_SetError("Unable to process array selection--no names in call (SDDS_MatchArrays)");
4229 return -1;
4230 }
4231
4232 if (SDDS_dataset->layout.n_arrays != flags) {
4233 flags = SDDS_dataset->layout.n_arrays;
4234 if (flag)
4235 free(flag);
4236 flag = NULL;
4237 if (flags) {
4238 if (!(flag = (int32_t *)calloc(flags, sizeof(*flag)))) {
4239 SDDS_SetError("Memory allocation failure (SDDS_MatchArrays)");
4240 return -1;
4241 }
4242 }
4243 }
4244 if (flags && (matchMode != SDDS_MATCH_STRING) && (matchMode != SDDS_MATCH_EXCLUDE_STRING))
4245 memset(flag, 0, sizeof(*flag) * flags);
4246
4247 if ((matchMode != SDDS_MATCH_STRING) && (matchMode != SDDS_MATCH_EXCLUDE_STRING)) {
4248 for (i = 0; i < n_names; i++) {
4249 if ((index = SDDS_GetArrayIndex(SDDS_dataset, name[i])) >= 0)
4250 flag[index] = 1;
4251 }
4252 } else {
4253 for (i = 0; i < SDDS_dataset->layout.n_arrays; i++) {
4254 if (SDDS_Logic(flag[i], wild_match(SDDS_dataset->layout.array_definition[i].name, match_string), logic)) {
4255 if (exclude_string != NULL) {
4256 if (SDDS_Logic(flag[i], wild_match(SDDS_dataset->layout.array_definition[i].name, exclude_string), logic))
4257 flag[i] = 0;
4258 else
4259 flag[i] = 1;
4260 } else {
4261 flag[i] = 1;
4262 }
4263 } else {
4264#if defined(DEBUG)
4265 fprintf(stderr, "no logic match of %s to %s\n", SDDS_dataset->layout.array_definition[i].name, match_string);
4266#endif
4267 flag[i] = 0;
4268 }
4269 }
4270 }
4271 if (match_string)
4272 free(match_string);
4273 if (exclude_string)
4274 free(exclude_string);
4275#if defined(DEBUG)
4276 for (i = 0; i < SDDS_dataset->layout.n_arrays; i++)
4277 fprintf(stderr, "flag[%" PRId32 "] = %" PRId32 " : %s\n", i, flag[i], SDDS_dataset->layout.array_definition[i].name);
4278#endif
4279
4280 if (local_memory == 2) {
4281 for (i = 0; i < n_names; i++)
4282 free(name[i]);
4283 }
4284 if (local_memory >= 1)
4285 free(name);
4286
4287 switch (typeMode) {
4288 case FIND_SPECIFIED_TYPE:
4289 for (i = 0; i < SDDS_dataset->layout.n_arrays; i++)
4290 if (SDDS_dataset->layout.array_definition[i].type != requiredType)
4291 flag[i] = 0;
4292 break;
4293 case FIND_NUMERIC_TYPE:
4294 for (i = 0; i < SDDS_dataset->layout.n_arrays; i++)
4295 if (!SDDS_NUMERIC_TYPE(SDDS_dataset->layout.array_definition[i].type))
4296 flag[i] = 0;
4297 break;
4298 case FIND_FLOATING_TYPE:
4299 for (i = 0; i < SDDS_dataset->layout.n_arrays; i++)
4300 if (!SDDS_FLOATING_TYPE(SDDS_dataset->layout.array_definition[i].type))
4301 flag[i] = 0;
4302 break;
4303 case FIND_INTEGER_TYPE:
4304 for (i = 0; i < SDDS_dataset->layout.n_arrays; i++)
4305 if (!SDDS_INTEGER_TYPE(SDDS_dataset->layout.array_definition[i].type))
4306 flag[i] = 0;
4307 break;
4308 default:
4309 break;
4310 }
4311#if defined(DEBUG)
4312 for (i = 0; i < SDDS_dataset->layout.n_arrays; i++)
4313 if (flag[i])
4314 fprintf(stderr, "array %s matched\n", SDDS_dataset->layout.array_definition[i].name);
4315#endif
4316
4317 for (i = matches = 0; i < SDDS_dataset->layout.n_arrays; i++) {
4318 if (flag[i])
4319 matches++;
4320 }
4321 if (!matches || !nameReturn)
4322 return matches;
4323 if (!((*nameReturn) = (char **)SDDS_Malloc(matches * sizeof(**nameReturn)))) {
4324 SDDS_SetError("Memory allocation failure (SDDS_MatchArrays)");
4325 return -1;
4326 }
4327 for (i = j = 0; i < SDDS_dataset->layout.n_arrays; i++) {
4328 if (flag[i]) {
4329 if (!SDDS_CopyString((*nameReturn) + j, SDDS_dataset->layout.array_definition[i].name)) {
4330 SDDS_SetError("String copy failure (SDDS_MatchArrays)");
4331 return -1;
4332 }
4333 j++;
4334 }
4335 }
4336
4337 return matches;
4338}
int32_t SDDS_Logic(int32_t previous, int32_t match, uint32_t logic)
Applies logical operations to determine the new state of a row flag based on previous and current mat...
int32_t SDDS_GetToken(char *s, char *buffer, int32_t buflen)
Extracts the next token from a string, handling quoted substrings and escape characters.

◆ SDDS_MatchColumns()

epicsShareFuncSDDS int32_t SDDS_MatchColumns ( SDDS_DATASET * SDDS_dataset,
char *** nameReturn,
int32_t matchMode,
int32_t typeMode,
... )
extern

Matches and retrieves column names from an SDDS dataset based on specified criteria.

This function selects columns from the provided SDDS dataset according to the specified matching mode and type mode. It supports various calling conventions depending on the matching criteria.

The function supports the following matching modes:

  • SDDS_NAME_ARRAY:
    • Parameters: int32_t n_entries, char **name
    • Description: Matches columns whose names are present in the provided array.
  • SDDS_NAMES_STRING:
    • Parameters: char *names
    • Description: Matches columns whose names are specified in a single comma-separated string.
  • SDDS_NAME_STRINGS:
    • Parameters: char *name1, char *name2, ..., NULL
    • Description: Matches columns whose names are specified as individual string arguments, terminated by a NULL pointer.
  • SDDS_MATCH_STRING:
    • Parameters: char *name, int32_t logic_mode
    • Description: Matches columns based on a wildcard pattern provided in name, using the specified logical mode.
  • SDDS_MATCH_EXCLUDE_STRING:
    • Parameters: char *name, char *exclude, int32_t logic_mode
    • Description: Matches columns based on a wildcard pattern provided in name, excluding those that match the exclude pattern, using the specified logical mode.

Additionally, the typeMode parameter allows filtering based on column types, such as numeric, floating, or integer types.

Parameters
[in]SDDS_datasetPointer to the SDDS_DATASET structure containing the dataset.
[out]nameReturnPointer to a char** that will be allocated and populated with the names of the matched columns. The caller is responsible for freeing the allocated memory.
[in]matchModeSpecifies the matching mode (e.g., SDDS_NAME_ARRAY, SDDS_NAMES_STRING, etc.).
[in]typeModeSpecifies the type matching mode (e.g., FIND_SPECIFIED_TYPE, FIND_NUMERIC_TYPE, FIND_FLOATING_TYPE, FIND_INTEGER_TYPE).
[in]...Variable arguments depending on matchMode:
  • SDDS_NAME_ARRAY: int32_t n_entries, char **name
  • SDDS_NAMES_STRING: char *names
  • SDDS_NAME_STRINGS: char *name1, char *name2, ..., NULL
  • SDDS_MATCH_STRING: char *name, int32_t logic_mode
  • SDDS_MATCH_EXCLUDE_STRING: char *name, char *exclude, int32_t logic_mode
Returns
  • Returns the number of matched columns on success.
  • Returns -1 if an error occurs (e.g., invalid parameters, memory allocation failure).
Note
  • The function internally manages memory for the matching process and allocates memory for nameReturn, which must be freed by the caller using appropriate memory deallocation functions.
  • The dataset must be properly initialized and contain a valid layout before calling this function.
Warning
  • Ensure that the variable arguments match the expected parameters for the specified matchMode.
  • The caller is responsible for freeing the memory allocated for nameReturn to avoid memory leaks.
See also
SDDS_MatchParameters, SDDS_SetError

Definition at line 3559 of file SDDS_utils.c.

3567{
3568 static MDB_THREAD_LOCAL int32_t flags = 0;
3569 static MDB_THREAD_LOCAL int32_t *flag = NULL;
3570 char **name, *string, *match_string, *ptr, *exclude_string;
3571 va_list argptr;
3572 int32_t retval, requiredType;
3573 int32_t i, j, n_names, index, matches;
3574 int32_t local_memory; /* (0,1,2) --> (none, pointer array, pointer array + strings) locally allocated */
3575 char buffer[SDDS_MAXLINE];
3576 int32_t logic;
3577
3578 name = NULL;
3579 match_string = exclude_string = NULL;
3580 n_names = requiredType = local_memory = logic = 0;
3581
3582 matches = -1;
3583 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_MatchColumns"))
3584 return -1;
3585 if (nameReturn)
3586 *nameReturn = NULL;
3587
3588 retval = 1;
3589 va_start(argptr, typeMode);
3590 if (typeMode == FIND_SPECIFIED_TYPE)
3591 requiredType = va_arg(argptr, int32_t);
3592 switch (matchMode) {
3593 case SDDS_NAME_ARRAY:
3594 local_memory = 0;
3595 n_names = va_arg(argptr, int32_t);
3596 name = va_arg(argptr, char **);
3597 break;
3598 case SDDS_NAMES_STRING:
3599 local_memory = 2;
3600 n_names = 0;
3601 name = NULL;
3602 ptr = va_arg(argptr, char *);
3603 SDDS_CopyString(&string, ptr);
3604 while ((ptr = strchr(string, ',')))
3605 *ptr = ' ';
3606 while (SDDS_GetToken(string, buffer, SDDS_MAXLINE) > 0) {
3607 if (!(name = SDDS_Realloc(name, sizeof(*name) * (n_names + 1))) || !SDDS_CopyString(name + n_names, buffer)) {
3608 SDDS_SetError("Unable to process column selection--memory allocation failure (SDDS_MatchColumns)");
3609 retval = 0;
3610 break;
3611 }
3612 n_names++;
3613 }
3614 free(string);
3615 break;
3616 case SDDS_NAME_STRINGS:
3617 local_memory = 1;
3618 n_names = 0;
3619 name = NULL;
3620 while ((string = va_arg(argptr, char *))) {
3621 if (!(name = SDDS_Realloc(name, sizeof(*name) * (n_names + 1)))) {
3622 SDDS_SetError("Unable to process column selection--memory allocation failure (SDDS_MatchColumns)");
3623 retval = 0;
3624 break;
3625 }
3626 name[n_names++] = string;
3627 }
3628 break;
3629 case SDDS_MATCH_STRING:
3630 local_memory = 0;
3631 n_names = 1;
3632 if (!(string = va_arg(argptr, char *))) {
3633 SDDS_SetError("Unable to process column selection--invalid matching string (SDDS_MatchColumns)");
3634 retval = 0;
3635 break;
3636 }
3637 match_string = expand_ranges(string);
3638 logic = va_arg(argptr, int32_t);
3639 break;
3640 case SDDS_MATCH_EXCLUDE_STRING:
3641 local_memory = 0;
3642 n_names = 1;
3643 if (!(string = va_arg(argptr, char *))) {
3644 SDDS_SetError("Unable to process column selection--invalid matching string (SDDS_MatchColumns)");
3645 retval = 0;
3646 break;
3647 }
3648 match_string = expand_ranges(string);
3649 if (!(string = va_arg(argptr, char *))) {
3650 SDDS_SetError("Unable to process column exclusion--invalid matching string (SDDS_MatchColumns)");
3651 retval = 0;
3652 break;
3653 }
3654 exclude_string = expand_ranges(string);
3655 logic = va_arg(argptr, int32_t);
3656 break;
3657 default:
3658 SDDS_SetError("Unable to process column selection--unknown match mode (SDDS_MatchColumns)");
3659 retval = 0;
3660 break;
3661 }
3662 va_end(argptr);
3663 if (retval == 0)
3664 return -1;
3665
3666 if (n_names == 0) {
3667 SDDS_SetError("Unable to process column selection--no names in call (SDDS_MatchColumns)");
3668 return -1;
3669 }
3670
3671 if (SDDS_dataset->layout.n_columns != flags) {
3672 flags = SDDS_dataset->layout.n_columns;
3673 if (flag)
3674 free(flag);
3675 flag = NULL;
3676 if (flags) {
3677 if (!(flag = (int32_t *)calloc(flags, sizeof(*flag)))) {
3678 SDDS_SetError("Memory allocation failure (SDDS_MatchColumns)");
3679 return -1;
3680 }
3681 }
3682 }
3683 if (flags && (matchMode != SDDS_MATCH_STRING) && (matchMode != SDDS_MATCH_EXCLUDE_STRING))
3684 memset(flag, 0, sizeof(*flag) * flags);
3685
3686 if ((matchMode != SDDS_MATCH_STRING) && (matchMode != SDDS_MATCH_EXCLUDE_STRING)) {
3687 for (i = 0; i < n_names; i++) {
3688 if ((index = SDDS_GetColumnIndex(SDDS_dataset, name[i])) >= 0)
3689 flag[index] = 1;
3690 }
3691 } else {
3692 for (i = 0; i < SDDS_dataset->layout.n_columns; i++) {
3693 if (SDDS_Logic(flag[i], wild_match(SDDS_dataset->layout.column_definition[i].name, match_string), logic)) {
3694 if (exclude_string != NULL) {
3695 if (SDDS_Logic(flag[i], wild_match(SDDS_dataset->layout.column_definition[i].name, exclude_string), logic))
3696 flag[i] = 0;
3697 else
3698 flag[i] = 1;
3699 } else {
3700 flag[i] = 1;
3701 }
3702 } else {
3703#if defined(DEBUG)
3704 fprintf(stderr, "no logic match of %s to %s\n", SDDS_dataset->layout.column_definition[i].name, match_string);
3705#endif
3706 flag[i] = 0;
3707 }
3708 }
3709 }
3710 if (match_string)
3711 free(match_string);
3712 if (exclude_string)
3713 free(exclude_string);
3714#if defined(DEBUG)
3715 for (i = 0; i < SDDS_dataset->layout.n_columns; i++)
3716 fprintf(stderr, "flag[%" PRId32 "] = %" PRId32 " : %s\n", i, flag[i], SDDS_dataset->layout.column_definition[i].name);
3717#endif
3718
3719 if (local_memory == 2) {
3720 for (i = 0; i < n_names; i++)
3721 free(name[i]);
3722 }
3723 if (local_memory >= 1)
3724 free(name);
3725
3726 switch (typeMode) {
3727 case FIND_SPECIFIED_TYPE:
3728 for (i = 0; i < SDDS_dataset->layout.n_columns; i++)
3729 if (SDDS_dataset->layout.column_definition[i].type != requiredType)
3730 flag[i] = 0;
3731 break;
3732 case FIND_NUMERIC_TYPE:
3733 for (i = 0; i < SDDS_dataset->layout.n_columns; i++)
3734 if (!SDDS_NUMERIC_TYPE(SDDS_dataset->layout.column_definition[i].type))
3735 flag[i] = 0;
3736 break;
3737 case FIND_FLOATING_TYPE:
3738 for (i = 0; i < SDDS_dataset->layout.n_columns; i++)
3739 if (!SDDS_FLOATING_TYPE(SDDS_dataset->layout.column_definition[i].type))
3740 flag[i] = 0;
3741 break;
3742 case FIND_INTEGER_TYPE:
3743 for (i = 0; i < SDDS_dataset->layout.n_columns; i++)
3744 if (!SDDS_INTEGER_TYPE(SDDS_dataset->layout.column_definition[i].type))
3745 flag[i] = 0;
3746 break;
3747 default:
3748 break;
3749 }
3750#if defined(DEBUG)
3751 for (i = 0; i < SDDS_dataset->layout.n_columns; i++)
3752 if (flag[i])
3753 fprintf(stderr, "column %s matched\n", SDDS_dataset->layout.column_definition[i].name);
3754#endif
3755
3756 for (i = matches = 0; i < SDDS_dataset->layout.n_columns; i++) {
3757 if (flag[i])
3758 matches++;
3759 }
3760 if (!matches || !nameReturn)
3761 return matches;
3762 if (!((*nameReturn) = (char **)SDDS_Malloc(matches * sizeof(**nameReturn)))) {
3763 SDDS_SetError("Memory allocation failure (SDDS_MatchColumns)");
3764 return -1;
3765 }
3766 for (i = j = 0; i < SDDS_dataset->layout.n_columns; i++) {
3767 if (flag[i]) {
3768 if (!SDDS_CopyString((*nameReturn) + j, SDDS_dataset->layout.column_definition[i].name)) {
3769 SDDS_SetError("String copy failure (SDDS_MatchColumns)");
3770 return -1;
3771 }
3772 j++;
3773 }
3774 }
3775 return matches;
3776}

◆ SDDS_MatchParameters()

epicsShareFuncSDDS int32_t SDDS_MatchParameters ( SDDS_DATASET * SDDS_dataset,
char *** nameReturn,
int32_t matchMode,
int32_t typeMode,
... )
extern

Matches and retrieves parameter names from an SDDS dataset based on specified criteria.

This function selects parameters from the provided SDDS dataset according to the specified matching mode and type mode. It supports various calling conventions depending on the matching criteria.

The function supports the following matching modes:

  • SDDS_NAME_ARRAY:
    • Parameters: int32_t n_entries, char **name
    • Description: Matches parameters whose names are present in the provided array.
  • SDDS_NAMES_STRING:
    • Parameters: char *names
    • Description: Matches parameters whose names are specified in a single comma-separated string.
  • SDDS_NAME_STRINGS:
    • Parameters: char *name1, char *name2, ..., NULL
    • Description: Matches parameters whose names are specified as individual string arguments, terminated by a NULL pointer.
  • SDDS_MATCH_STRING:
    • Parameters: char *name, int32_t logic_mode
    • Description: Matches parameters based on a wildcard pattern provided in name, using the specified logical mode.
  • SDDS_MATCH_EXCLUDE_STRING:
    • Parameters: char *name, char *exclude, int32_t logic_mode
    • Description: Matches parameters based on a wildcard pattern provided in name, excluding those that match the exclude pattern, using the specified logical mode.

Additionally, the typeMode parameter allows filtering based on parameter types, such as numeric, floating, or integer types.

Parameters
[in]SDDS_datasetPointer to the SDDS_DATASET structure containing the dataset.
[out]nameReturnPointer to a char** that will be allocated and populated with the names of the matched parameters. The caller is responsible for freeing the allocated memory.
[in]matchModeSpecifies the matching mode (e.g., SDDS_NAME_ARRAY, SDDS_NAMES_STRING, etc.).
[in]typeModeSpecifies the type matching mode (e.g., FIND_SPECIFIED_TYPE, FIND_NUMERIC_TYPE, FIND_FLOATING_TYPE, FIND_INTEGER_TYPE).
[in]...Variable arguments depending on matchMode:
  • SDDS_NAME_ARRAY: int32_t n_entries, char **name
  • SDDS_NAMES_STRING: char *names
  • SDDS_NAME_STRINGS: char *name1, char *name2, ..., NULL
  • SDDS_MATCH_STRING: char *name, int32_t logic_mode
  • SDDS_MATCH_EXCLUDE_STRING: char *name, char *exclude, int32_t logic_mode
Returns
  • Returns the number of matched parameters on success.
  • Returns -1 if an error occurs (e.g., invalid parameters, memory allocation failure).
Note
  • The function internally manages memory for the matching process and allocates memory for nameReturn, which must be freed by the caller using appropriate memory deallocation functions.
  • The dataset must be properly initialized and contain a valid layout before calling this function.
Warning
  • Ensure that the variable arguments match the expected parameters for the specified matchMode.
  • The caller is responsible for freeing the memory allocated for nameReturn to avoid memory leaks.
See also
SDDS_MatchColumns, SDDS_SetError

Definition at line 3840 of file SDDS_utils.c.

3848{
3849 static MDB_THREAD_LOCAL int32_t flags = 0, *flag = NULL;
3850 char **name, *string, *match_string, *ptr, *exclude_string;
3851 va_list argptr;
3852 int32_t i, j, index, n_names, retval, requiredType, matches;
3853 /* int32_t type; */
3854 int32_t local_memory; /* (0,1,2) --> (none, pointer array, pointer array + strings) locally allocated */
3855 char buffer[SDDS_MAXLINE];
3856 int32_t logic;
3857
3858 name = NULL;
3859 match_string = exclude_string = NULL;
3860 n_names = requiredType = local_memory = logic = 0;
3861
3862 matches = -1;
3863 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_MatchParameters"))
3864 return -1;
3865 if (nameReturn)
3866 *nameReturn = NULL;
3867
3868 retval = 1;
3869 va_start(argptr, typeMode);
3870 if (typeMode == FIND_SPECIFIED_TYPE)
3871 requiredType = va_arg(argptr, int32_t);
3872 switch (matchMode) {
3873 case SDDS_NAME_ARRAY:
3874 local_memory = 0;
3875 n_names = va_arg(argptr, int32_t);
3876 name = va_arg(argptr, char **);
3877 break;
3878 case SDDS_NAMES_STRING:
3879 local_memory = 2;
3880 n_names = 0;
3881 name = NULL;
3882 ptr = va_arg(argptr, char *);
3883 SDDS_CopyString(&string, ptr);
3884 while ((ptr = strchr(string, ',')))
3885 *ptr = ' ';
3886 while (SDDS_GetToken(string, buffer, SDDS_MAXLINE) > 0) {
3887 if (!(name = SDDS_Realloc(name, sizeof(*name) * (n_names + 1))) || !SDDS_CopyString(name + n_names, buffer)) {
3888 SDDS_SetError("Unable to process parameter selection--memory allocation failure (SDDS_MatchParameters)");
3889 retval = 0;
3890 break;
3891 }
3892 n_names++;
3893 }
3894 free(string);
3895 break;
3896 case SDDS_NAME_STRINGS:
3897 local_memory = 1;
3898 n_names = 0;
3899 name = NULL;
3900 while ((string = va_arg(argptr, char *))) {
3901 if (!(name = SDDS_Realloc(name, sizeof(*name) * (n_names + 1)))) {
3902 SDDS_SetError("Unable to process parameter selection--memory allocation failure (SDDS_MatchParameters)");
3903 retval = 0;
3904 break;
3905 }
3906 name[n_names++] = string;
3907 }
3908 break;
3909 case SDDS_MATCH_STRING:
3910 local_memory = 0;
3911 n_names = 1;
3912 if (!(string = va_arg(argptr, char *))) {
3913 SDDS_SetError("Unable to process parameter selection--invalid matching string (SDDS_MatchParameters)");
3914 retval = 0;
3915 break;
3916 }
3917 match_string = expand_ranges(string);
3918 logic = va_arg(argptr, int32_t);
3919 break;
3920 case SDDS_MATCH_EXCLUDE_STRING:
3921 local_memory = 0;
3922 n_names = 1;
3923 if (!(string = va_arg(argptr, char *))) {
3924 SDDS_SetError("Unable to process parameter selection--invalid matching string (SDDS_MatchParameters)");
3925 retval = 0;
3926 break;
3927 }
3928 match_string = expand_ranges(string);
3929 if (!(string = va_arg(argptr, char *))) {
3930 SDDS_SetError("Unable to process parameter exclusion--invalid matching string (SDDS_MatchParameters)");
3931 retval = 0;
3932 break;
3933 }
3934 exclude_string = expand_ranges(string);
3935 logic = va_arg(argptr, int32_t);
3936 break;
3937 default:
3938 SDDS_SetError("Unable to process parameter selection--unknown match mode (SDDS_MatchParameters)");
3939 retval = 0;
3940 break;
3941 }
3942 va_end(argptr);
3943 if (retval == 0)
3944 return -1;
3945
3946 if (n_names == 0) {
3947 SDDS_SetError("Unable to process parameter selection--no names in call (SDDS_MatchParameters)");
3948 return -1;
3949 }
3950
3951 if (SDDS_dataset->layout.n_parameters != flags) {
3952 flags = SDDS_dataset->layout.n_parameters;
3953 if (flag)
3954 free(flag);
3955 flag = NULL;
3956 if (flags) {
3957 if (!(flag = (int32_t *)calloc(flags, sizeof(*flag)))) {
3958 SDDS_SetError("Memory allocation failure (SDDS_MatchParameters)");
3959 return -1;
3960 }
3961 }
3962 }
3963 if (flags && (matchMode != SDDS_MATCH_STRING) && (matchMode != SDDS_MATCH_EXCLUDE_STRING))
3964 memset(flag, 0, sizeof(*flag) * flags);
3965
3966 if ((matchMode != SDDS_MATCH_STRING) && (matchMode != SDDS_MATCH_EXCLUDE_STRING)) {
3967 for (i = 0; i < n_names; i++) {
3968 if ((index = SDDS_GetParameterIndex(SDDS_dataset, name[i])) >= 0)
3969 flag[index] = 1;
3970 }
3971 } else {
3972 for (i = 0; i < SDDS_dataset->layout.n_parameters; i++) {
3973 if (SDDS_Logic(flag[i], wild_match(SDDS_dataset->layout.parameter_definition[i].name, match_string), logic)) {
3974 if (exclude_string != NULL) {
3975 if (SDDS_Logic(flag[i], wild_match(SDDS_dataset->layout.parameter_definition[i].name, exclude_string), logic))
3976 flag[i] = 0;
3977 else
3978 flag[i] = 1;
3979 } else {
3980 flag[i] = 1;
3981 }
3982 } else {
3983#if defined(DEBUG)
3984 fprintf(stderr, "no logic match of %s to %s\n", SDDS_dataset->layout.parameter_definition[i].name, match_string);
3985#endif
3986 flag[i] = 0;
3987 }
3988 }
3989 }
3990 if (match_string)
3991 free(match_string);
3992 if (exclude_string)
3993 free(exclude_string);
3994#if defined(DEBUG)
3995 for (i = 0; i < SDDS_dataset->layout.n_parameters; i++)
3996 fprintf(stderr, "flag[%" PRId32 "] = %" PRId32 " : %s\n", i, flag[i], SDDS_dataset->layout.parameter_definition[i].name);
3997#endif
3998
3999 if (local_memory == 2) {
4000 for (i = 0; i < n_names; i++)
4001 free(name[i]);
4002 }
4003 if (local_memory >= 1)
4004 free(name);
4005
4006 switch (typeMode) {
4007 case FIND_SPECIFIED_TYPE:
4008 for (i = 0; i < SDDS_dataset->layout.n_parameters; i++)
4009 if (SDDS_dataset->layout.parameter_definition[i].type != requiredType)
4010 flag[i] = 0;
4011 break;
4012 case FIND_NUMERIC_TYPE:
4013 for (i = 0; i < SDDS_dataset->layout.n_parameters; i++)
4014 if (!SDDS_NUMERIC_TYPE(SDDS_dataset->layout.parameter_definition[i].type))
4015 flag[i] = 0;
4016 break;
4017 case FIND_FLOATING_TYPE:
4018 for (i = 0; i < SDDS_dataset->layout.n_parameters; i++)
4019 if (!SDDS_FLOATING_TYPE(SDDS_dataset->layout.parameter_definition[i].type))
4020 flag[i] = 0;
4021 break;
4022 case FIND_INTEGER_TYPE:
4023 for (i = 0; i < SDDS_dataset->layout.n_parameters; i++)
4024 if (!SDDS_INTEGER_TYPE(SDDS_dataset->layout.parameter_definition[i].type))
4025 flag[i] = 0;
4026 break;
4027 default:
4028 break;
4029 }
4030#if defined(DEBUG)
4031 for (i = 0; i < SDDS_dataset->layout.n_parameters; i++)
4032 if (flag[i])
4033 fprintf(stderr, "parameter %s matched\n", SDDS_dataset->layout.parameter_definition[i].name);
4034#endif
4035
4036 for (i = matches = 0; i < SDDS_dataset->layout.n_parameters; i++) {
4037 if (flag[i])
4038 matches++;
4039 }
4040 if (!matches || !nameReturn)
4041 return matches;
4042 if (!((*nameReturn) = (char **)SDDS_Malloc(matches * sizeof(**nameReturn)))) {
4043 SDDS_SetError("Memory allocation failure (SDDS_MatchParameters)");
4044 return -1;
4045 }
4046 for (i = j = 0; i < SDDS_dataset->layout.n_parameters; i++) {
4047 if (flag[i]) {
4048 if (!SDDS_CopyString((*nameReturn) + j, SDDS_dataset->layout.parameter_definition[i].name)) {
4049 SDDS_SetError("String copy failure (SDDS_MatchParameters)");
4050 return -1;
4051 }
4052 j++;
4053 }
4054 }
4055
4056 return matches;
4057}

◆ SDDS_MatchRowsOfInterest()

epicsShareFuncSDDS int64_t SDDS_MatchRowsOfInterest ( SDDS_DATASET * SDDS_dataset,
char * selection_column,
char * label_to_match,
int32_t logic )
extern

Matches and marks rows of interest in an SDDS dataset based on label matching.

This function marks rows in the provided SDDS dataset as "of interest" by matching labels in a specified column against a target label. It supports both direct and indirect matching, as well as case-sensitive and case-insensitive comparisons, based on the provided logic flags.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
selection_columnA null-terminated string specifying the name of the column used for label matching. This column must be of string or character type.
label_to_matchA null-terminated string specifying the label to match against the entries in the selection column. If logic includes SDDS_INDIRECT_MATCH, this parameter is treated as the name of another column used for indirect matching.
logicAn integer representing logical operation flags. Supported flags include:
  • SDDS_NOCASE_COMPARE: Perform case-insensitive comparison.
  • SDDS_INDIRECT_MATCH: Use indirect matching via another column.
Returns
On success, returns the number of rows marked as "of interest". On failure, returns -1 and sets an appropriate error message.
Return values
-1Indicates that an error occurred (e.g., invalid dataset, unrecognized selection column, type mismatch, unrecognized indirect column).
Non-negativeInteger representing the count of rows marked as "of interest".
Note
  • The selection column must exist and be of string or character type.
  • If using indirect matching (SDDS_INDIRECT_MATCH), the indirect column must exist and be of the same type as the selection column.
See also
SDDS_SetRowsOfInterest, SDDS_FilterRowsOfInterest, SDDS_DeleteUnsetRows

Definition at line 3507 of file SDDS_extract.c.

3507 {
3508 int32_t match, type, index, indirect_index;
3509 int64_t i, count;
3510 char *match_string;
3511#ifndef tolower
3512# if !defined(_MINGW)
3513 int tolower(int c);
3514# endif
3515#endif
3516
3517 index = type = indirect_index = 0;
3518
3519 match_string = NULL;
3520 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_MatchRowsOfInterest"))
3521 return (-1);
3522 if (selection_column) {
3523 if ((index = SDDS_GetColumnIndex(SDDS_dataset, selection_column)) < 0) {
3524 SDDS_SetError("Unable to select rows--column name is unrecognized (SDDS_MatchRowsOfInterest)");
3525 return (-1);
3526 }
3527 if ((type = SDDS_GetColumnType(SDDS_dataset, index)) != SDDS_STRING && type != SDDS_CHARACTER) {
3528 SDDS_SetError("Unable to select rows--selection column is not a string (SDDS_MatchRowsOfInterest)");
3529 return (-1);
3530 }
3531 if (!label_to_match) {
3532 SDDS_SetError("Unable to select rows--selection label is NULL (SDDS_MatchRowsOfInterest)");
3533 return (-1);
3534 }
3535 if (!(logic & SDDS_INDIRECT_MATCH))
3536 match_string = expand_ranges(label_to_match);
3537 else {
3538 if ((indirect_index = SDDS_GetColumnIndex(SDDS_dataset, label_to_match)) < 0) {
3539 SDDS_SetError("Unable to select rows--indirect column name is unrecognized (SDDS_MatchRowsOfInterest)");
3540 return (-1);
3541 }
3542 if (SDDS_GetColumnType(SDDS_dataset, indirect_index) != type) {
3543 SDDS_SetError("Unable to select rows--indirect column is not same type as main column (SDDS_MatchRowsOfInterest)");
3544 return (-1);
3545 }
3546 }
3547 }
3548 if (type == SDDS_STRING) {
3549 int (*stringCompare)(const char *s, const char *t);
3550 int (*wildMatch)(char *s, char *t);
3551 if (logic & SDDS_NOCASE_COMPARE) {
3552 stringCompare = strcmp_ci;
3553 wildMatch = wild_match_ci;
3554 } else {
3555 stringCompare = strcmp;
3556 wildMatch = wild_match;
3557 }
3558 for (i = count = 0; i < SDDS_dataset->n_rows; i++) {
3559 if (selection_column)
3560 match = SDDS_Logic(SDDS_dataset->row_flag[i], (logic & SDDS_INDIRECT_MATCH ? (*stringCompare)(*((char **)SDDS_dataset->data[index] + i), *((char **)SDDS_dataset->data[indirect_index] + i)) == 0 : (*wildMatch)(*((char **)SDDS_dataset->data[index] + i), match_string)), logic);
3561 else
3562 match = SDDS_Logic(SDDS_dataset->row_flag[i], 0, logic & ~(SDDS_AND | SDDS_OR));
3563 if ((SDDS_dataset->row_flag[i] = match))
3564 count++;
3565 }
3566 } else {
3567 char c1, c2;
3568 c2 = 0;
3569 if (!(logic & SDDS_INDIRECT_MATCH))
3570 c2 = *match_string;
3571 if (logic & SDDS_NOCASE_COMPARE) {
3572 c2 = tolower(c2);
3573 for (i = count = 0; i < SDDS_dataset->n_rows; i++) {
3574 c1 = tolower(*((char *)SDDS_dataset->data[index] + i));
3575 if (selection_column)
3576 match = SDDS_Logic(SDDS_dataset->row_flag[i], logic & SDDS_INDIRECT_MATCH ? c1 == tolower(*((char *)SDDS_dataset->data[indirect_index] + i)) : c1 == c2, logic);
3577 else
3578 match = SDDS_Logic(SDDS_dataset->row_flag[i], 0, logic & ~(SDDS_AND | SDDS_OR));
3579 if ((SDDS_dataset->row_flag[i] = match))
3580 count++;
3581 }
3582 } else {
3583 for (i = count = 0; i < SDDS_dataset->n_rows; i++) {
3584 c1 = *((char *)SDDS_dataset->data[index] + i);
3585 if (selection_column)
3586 match = SDDS_Logic(SDDS_dataset->row_flag[i], logic & SDDS_INDIRECT_MATCH ? c1 == *((char *)SDDS_dataset->data[indirect_index] + i) : c1 == c2, logic);
3587 else
3588 match = SDDS_Logic(SDDS_dataset->row_flag[i], 0, logic & ~(SDDS_AND | SDDS_OR));
3589 if ((SDDS_dataset->row_flag[i] = match))
3590 count++;
3591 }
3592 }
3593 }
3594 if (match_string)
3595 free(match_string);
3596 return (count);
3597}
int wild_match_ci(char *string, char *template)
Determine whether one string is a case-insensitive wildcard match for another.
Definition wild_match.c:220
int strcmp_ci(const char *s, const char *t)
Compare two strings case-insensitively.
Definition wild_match.c:396

◆ SDDS_NumberOfErrors()

epicsShareFuncSDDS int32_t SDDS_NumberOfErrors ( void )
extern

Retrieves the number of errors recorded by SDDS library routines.

This function returns the total number of errors that have been recorded by the SDDS library since the last invocation of SDDS_PrintErrors.

Returns
The number of recorded errors.
See also
SDDS_PrintErrors

Definition at line 340 of file SDDS_utils.c.

340 {
341 return (n_errors);
342}

◆ SDDS_PadToLength()

epicsShareFuncSDDS int32_t SDDS_PadToLength ( char * string,
int32_t length )
extern

Pads a string with spaces to reach a specified length.

This function appends space characters to the end of the input string string until it reaches the desired length. If the original string is longer than the specified length, the function returns an error without modifying the string.

Parameters
[in,out]stringPointer to the null-terminated string to be padded.
[in]lengthThe target length for the string after padding.
Returns
Returns 1 on successful padding. Returns 0 if the input string is NULL or if the original string length exceeds the specified length.
Note
The function ensures that the padded string is null-terminated. The caller must ensure that the buffer string has sufficient space to accommodate the additional padding.
See also
SDDS_RemovePadding

Definition at line 1945 of file SDDS_utils.c.

1945 {
1946 int32_t i;
1947 if (!string || (i = strlen(string)) > length)
1948 return (0);
1949 while (i < length)
1950 string[i++] = ' ';
1951 string[i] = 0;
1952 return (1);
1953}

◆ SDDS_Parallel_InitializeOutput()

epicsShareFuncSDDS int32_t SDDS_Parallel_InitializeOutput ( SDDS_DATASET * SDDS_dataset,
const char * description,
const char * contents,
const char * filename )
extern

Initializes the SDDS output dataset for parallel processing.

This function configures the SDDS dataset for parallel output operations. It sets the dataset's description, contents, and filename, ensuring that the output is in binary mode as parallel processing with compressed files is not supported. The function initializes necessary structures and prepares the dataset for efficient parallel data writing.

Parameters
[in,out]SDDS_datasetPointer to the SDDS_DATASET structure to be initialized for parallel output.
[in]descriptionA string containing the description of the dataset. Pass NULL if no description is desired.
[in]contentsA string detailing the contents of the dataset. Pass NULL if no contents are desired.
[in]filenameThe name of the file to which the dataset will be written. If NULL, the dataset will be written to standard output.
Returns
  • 1 on successful initialization.
  • 0 if an error occurred during initialization. In this case, an error message is set internally.
Precondition
  • The SDDS_dataset pointer must be valid and point to a properly allocated SDDS_DATASET structure.
  • The dataset memory should have been zeroed prior to calling this function (handled externally).
Postcondition
  • The dataset is configured for parallel binary output.
  • The dataset's internal state reflects the initialization status.
Note
  • Parallel output does not support compressed file formats.
  • The output mode is set to binary regardless of the specified data mode.
  • Environment variable SDDS_OUTPUT_ENDIANESS can be set to "big" or "little" to declare the byte order.
Warning
  • Attempting to use parallel initialization with compressed files will result in an error.
  • Ensure that no other processes are accessing the file simultaneously to prevent initialization failures.

Definition at line 755 of file SDDS_output.c.

755 {
756 /* SDDS_DATASET *SDDS_dataset; */
757 char s[SDDS_MAXLINE];
758 char *outputEndianess = NULL;
759
760 /* SDDS_dataset = &(MPI_dataset->sdds_dataset); */
761 if (sizeof(gzFile) != sizeof(void *)) {
762 SDDS_SetError("gzFile is not the same size as void *, possible corruption of the SDDS_LAYOUT structure");
763 return (0);
764 }
765 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_InitializeOutput"))
766 return 0;
767 /* if (!SDDS_ZeroMemory((void *)SDDS_dataset, sizeof(SDDS_DATASET))) {
768 sprintf(s,
769 "Unable to initialize output for file %s--can't zero SDDS_DATASET structure (SDDS_InitializeOutput)",
770 filename);
771 SDDS_SetError(s);
772 return 0;
773 } */
774 /*the sdds dataset memory has been zeroed in the SDDS_MPI_Setup */
775 SDDS_dataset->layout.popenUsed = SDDS_dataset->layout.gzipFile = SDDS_dataset->layout.lzmaFile = SDDS_dataset->layout.disconnected = 0;
776 SDDS_dataset->layout.depth = SDDS_dataset->layout.data_command_seen = SDDS_dataset->layout.commentFlags = SDDS_dataset->deferSavingLayout = 0;
777 SDDS_dataset->layout.fp = NULL;
778
779 SDDS_dataset->page_number = SDDS_dataset->page_started = 0;
780 SDDS_dataset->file_had_data = SDDS_dataset->layout.layout_written = 0;
781 if (!filename)
782 SDDS_dataset->layout.filename = NULL;
783 else if (!SDDS_CopyString(&SDDS_dataset->layout.filename, filename)) {
784 sprintf(s, "Memory allocation failure initializing file %s (SDDS_InitializeOutput)", filename);
785 SDDS_SetError(s);
786 return 0;
787 }
788 if ((outputEndianess = getenv("SDDS_OUTPUT_ENDIANESS"))) {
789 if (strncmp(outputEndianess, "big", 3) == 0)
790 SDDS_dataset->layout.byteOrderDeclared = SDDS_BIGENDIAN;
791 else if (strncmp(outputEndianess, "little", 6) == 0)
792 SDDS_dataset->layout.byteOrderDeclared = SDDS_LITTLEENDIAN;
793 } else {
794 SDDS_dataset->layout.byteOrderDeclared = SDDS_IsBigEndianMachine() ? SDDS_BIGENDIAN : SDDS_LITTLEENDIAN;
795 }
796 /* set big-endian for binary files, since it is the only type of MPI binary file.
797 SDDS_dataset->layout.byteOrderDeclared = SDDS_BIGENDIAN; */
798 SDDS_dataset->layout.version = SDDS_VERSION;
799 /* it turned out that hard to write ascii file in parallel, fixed it as SDDS_BINARY */
800 SDDS_dataset->layout.data_mode.mode = SDDS_BINARY;
801 SDDS_dataset->layout.data_mode.lines_per_row = 0;
802 SDDS_dataset->layout.data_mode.no_row_counts = 0;
803 SDDS_dataset->layout.data_mode.fixed_row_count = 0;
804 SDDS_dataset->layout.data_mode.fsync_data = 0;
805 SDDS_dataset->layout.data_mode.column_memory_mode = DEFAULT_COLUMN_MEMORY_MODE;
806 /*This is only temporary, soon the default will be column major order */
807 SDDS_dataset->layout.data_mode.column_major = 0;
808 if (description && !SDDS_CopyString(&SDDS_dataset->layout.description, description)) {
809 sprintf(s, "Memory allocation failure initializing file %s (SDDS_InitializeOutput)", filename ? filename : "stdout");
810 SDDS_SetError(s);
811 return 0;
812 }
813 if (contents && !SDDS_CopyString(&SDDS_dataset->layout.contents, contents)) {
814 sprintf(s, "Memory allocation failure initializing file %s (SDDS_InitializeOutput)", filename ? filename : "stdout");
815 SDDS_SetError(s);
816 return 0;
817 }
818 SDDS_dataset->layout.n_parameters = SDDS_dataset->layout.n_columns = SDDS_dataset->layout.n_arrays = SDDS_dataset->layout.n_associates = 0;
819 SDDS_dataset->mode = SDDS_WRITEMODE; /*writing */
820 SDDS_dataset->pagecount_offset = NULL;
821 SDDS_dataset->parallel_io = 1;
822 return (1);
823}

◆ SDDS_ParameterCount()

epicsShareFuncSDDS int32_t SDDS_ParameterCount ( SDDS_DATASET * page)
extern

Retrieves the number of parameters in the SDDS dataset.

This function returns the total count of parameters defined in the layout of the provided SDDS dataset.

Parameters
[in]pagePointer to the SDDS_DATASET structure representing the dataset.
Returns
  • The number of parameters (int32_t) in the dataset.
  • 0 if the provided dataset pointer is NULL.
Note
  • Ensure that the dataset is properly initialized before calling this function.
See also
SDDS_GetParameterIndex, SDDS_CheckParameter

Definition at line 5121 of file SDDS_utils.c.

5121 {
5122 if (!page)
5123 return 0;
5124 return page->layout.n_parameters;
5125}

◆ SDDS_ParseNamelist()

epicsShareFuncSDDS int32_t SDDS_ParseNamelist ( void * data,
SDDS_FIELD_INFORMATION * fieldInfo,
int32_t fieldInfos,
char * s )
extern

Parse a namelist string and populate the corresponding data structure.

This function parses a namelist string containing tag-value pairs and assigns the values to the appropriate fields in the provided data structure based on the field information provided.

Parameters
dataPointer to the data structure to populate.
fieldInfoArray of SDDS_FIELD_INFORMATION structures describing the fields.
fieldInfosNumber of elements in the fieldInfo array.
sPointer to the namelist string.
Returns
Returns 1 on success, 0 on failure.

Definition at line 588 of file SDDS_process.c.

588 {
589 char buffer[1024], *ptr, *tag, *value;
590 int32_t index, longValue;
591
593 while (*ptr && !SDDS_StringIsBlank(ptr) && (ptr = SDDS_GetTagValuePair(ptr, &tag, &value))) {
594 if (!tag)
595 break; /* normal termination */
596 if ((index = SDDS_FindFieldIndex(tag, fieldInfo, fieldInfos)) < 0) {
597 sprintf(buffer, "Unrecognized namelist tag given: %s", tag);
598 SDDS_SetError(buffer);
599 return 0;
600 } else {
601 if (fieldInfo[index].enumPair) {
602 if (fieldInfo[index].type != SDDS_LONG) {
603 fprintf(stderr, "SDDS_ParseNamelist: namelist setup problem---get expert help!\n");
604 exit(1);
605 }
606 /* map a string value into an integer */
607 if ((longValue = SDDS_MatchEnum(value, fieldInfo[index].enumPair)) < 0) {
608 sprintf(buffer, "Unrecognized value given for %s: %s", tag, value);
609 SDDS_SetError(buffer);
610 return 0;
611 } else
612 *((int32_t *)((char *)data + fieldInfo[index].offset)) = longValue;
613 } else {
614 switch (fieldInfo[index].type) {
615 case SDDS_STRING:
616 if (!(SDDS_CopyString((char **)((char *)data + fieldInfo[index].offset), value))) {
617 SDDS_SetError("Problem setting string value for namelist");
618 return 0;
619 }
620 break;
621 case SDDS_CHARACTER:
622 *((char *)data + fieldInfo[index].offset) = *value;
623 break;
624 case SDDS_SHORT:
625 if (!sscanf(value, "%hd", (short *)((char *)data + fieldInfo[index].offset))) {
626 SDDS_SetError("Problem scanning short value for namelist");
627 return 0;
628 }
629 break;
630 case SDDS_USHORT:
631 if (!sscanf(value, "%hu", (unsigned short *)((char *)data + fieldInfo[index].offset))) {
632 SDDS_SetError("Problem scanning unsigned short value for namelist");
633 return 0;
634 }
635 break;
636 case SDDS_LONG:
637 if (!sscanf(value, "%" SCNd32, (int32_t *)((char *)data + fieldInfo[index].offset))) {
638 SDDS_SetError("Problem scanning int32_t value for namelist");
639 return 0;
640 }
641 break;
642 case SDDS_ULONG:
643 if (!sscanf(value, "%" SCNu32, (uint32_t *)((char *)data + fieldInfo[index].offset))) {
644 SDDS_SetError("Problem scanning uint32_t value for namelist");
645 return 0;
646 }
647 break;
648 case SDDS_LONG64:
649 if (!sscanf(value, "%" SCNd64, (int64_t *)((char *)data + fieldInfo[index].offset))) {
650 SDDS_SetError("Problem scanning int64_t value for namelist");
651 return 0;
652 }
653 break;
654 case SDDS_ULONG64:
655 if (!sscanf(value, "%" SCNu64, (uint64_t *)((char *)data + fieldInfo[index].offset))) {
656 SDDS_SetError("Problem scanning uint64_t value for namelist");
657 return 0;
658 }
659 break;
660 case SDDS_LONGDOUBLE:
661 if (!sscanf(value, "%Lf", (long double *)((char *)data + fieldInfo[index].offset))) {
662 SDDS_SetError("Problem scanning long double value for namelist");
663 return 0;
664 }
665 break;
666 case SDDS_DOUBLE:
667 if (!sscanf(value, "%lf", (double *)((char *)data + fieldInfo[index].offset))) {
668 SDDS_SetError("Problem scanning double value for namelist");
669 return 0;
670 }
671 break;
672 case SDDS_FLOAT:
673 if (!sscanf(value, "%f", (float *)((char *)data + fieldInfo[index].offset))) {
674 SDDS_SetError("Problem scanning float value for namelist");
675 return 0;
676 }
677 break;
678 default:
679 SDDS_SetError("Internal error: unknown field information type");
680 return 0;
681 }
682 }
683 }
684 }
685 if (!ptr) {
686 SDDS_SetError("Problem parsing description namelist");
687 return 0;
688 }
689 return 1;
690}
int32_t SDDS_MatchEnum(char *value, SDDS_ENUM_PAIR *enumPair)
Match an enumeration string to its corresponding value.
char * SDDS_GetTagValuePair(char *ptr, char **tag, char **value)
Retrieve a tag-value pair from the input string.
char * SDDS_PrepareToParseTagValuePairs(char *s)
Prepare the string for parsing tag-value pairs.
int32_t SDDS_FindFieldIndex(char *tag, SDDS_FIELD_INFORMATION *fieldInfo, int32_t fieldInfos)
Find the index of a field based on its tag.

◆ SDDS_PrintCheckText()

epicsShareFuncSDDS int32_t SDDS_PrintCheckText ( FILE * fp,
char * name,
char * units,
int32_t type,
char * class_name,
int32_t error_code )
extern

Prints detailed error messages related to SDDS entity checks.

This function outputs error messages to the specified file pointer based on the provided error code. It is primarily used by functions like SDDS_CheckColumn, SDDS_CheckParameter, and SDDS_CheckArray to report issues during validation checks.

Parameters
[in]fpFile pointer where the error messages will be printed. Typically, this is stderr.
[in]nameThe name of the SDDS entity (e.g., column, parameter, array) being checked.
[in]unitsThe expected units of the SDDS entity. May be NULL if units are not relevant.
[in]typeThe expected type code of the SDDS entity. This can be a specific type or a general category like SDDS_ANY_NUMERIC_TYPE.
[in]class_nameA string representing the class of the SDDS entity (e.g., "column", "parameter", "array").
[in]error_codeThe specific error code indicating the type of error encountered. Valid values include:
  • SDDS_CHECK_OKAY
  • SDDS_CHECK_NONEXISTENT
  • SDDS_CHECK_WRONGTYPE
  • SDDS_CHECK_WRONGUNITS
Returns
Returns the same error_code that was passed as an argument.
Note
  • This function assumes that registeredProgramName is a globally accessible string containing the name of the program for contextual error messages.
  • Ensure that fp, name, and class_name are not NULL to prevent undefined behavior.
Warning
  • Passing invalid error_code values that are not handled in the switch statement will result in a generic error message being printed to stderr.
See also
SDDS_CheckColumn, SDDS_CheckParameter, SDDS_CheckArray

Definition at line 4914 of file SDDS_utils.c.

4914 {
4915 char *programName;
4916 const char *programNameText;
4917
4918 if (!fp || !name || !class_name)
4919 return (error_code);
4920 programName = SDDS_GetRegisteredProgramNameCopy();
4921 programNameText = programName ? programName : "?";
4922 switch (error_code) {
4923 case SDDS_CHECK_OKAY:
4924 break;
4925 case SDDS_CHECK_NONEXISTENT:
4926 fprintf(fp, "Problem with %s %s: nonexistent (%s)\n", class_name, name, programNameText);
4927 break;
4928 case SDDS_CHECK_WRONGTYPE:
4929 if (SDDS_VALID_TYPE(type))
4930 fprintf(fp, "Problem with %s %s: wrong data type--expected %s (%s)\n", class_name, name, SDDS_type_name[type - 1], programNameText);
4931 else if (type == SDDS_ANY_NUMERIC_TYPE)
4932 fprintf(fp, "Problem with %s %s: wrong data type--expected numeric data (%s)\n", class_name, name, programNameText);
4933 else if (type == SDDS_ANY_FLOATING_TYPE)
4934 fprintf(fp, "Problem with %s %s: wrong data type--expected floating point data (%s)\n", class_name, name, programNameText);
4935 else if (type == SDDS_ANY_INTEGER_TYPE)
4936 fprintf(fp, "Problem with %s %s: wrong data type--expected integer data (%s)\n", class_name, name, programNameText);
4937 else if (type)
4938 fprintf(fp, "Problem with %s %s: invalid data type code seen---may be a programming error (%s)\n", class_name, name, programNameText);
4939 break;
4940 case SDDS_CHECK_WRONGUNITS:
4941 fprintf(fp, "Problem with %s %s: wrong units--expected %s (%s)\n", class_name, name, units ? units : "none", programNameText);
4942 break;
4943 default:
4944 fprintf(stderr, "Problem with call to SDDS_PrintCheckText--invalid error code (%s)\n", programNameText);
4945 free(programName);
4946 return (SDDS_CHECK_OKAY);
4947 }
4948 free(programName);
4949 return (error_code);
4950}

◆ SDDS_PrintErrors()

epicsShareFuncSDDS void SDDS_PrintErrors ( FILE * fp,
int32_t mode )
extern

Prints recorded error messages to a specified file stream.

This function outputs the errors that have been recorded by SDDS library routines to the given file stream. Depending on the mode parameter, it can print a single error, all recorded errors, and optionally terminate the program after printing.

Parameters
[in]fpPointer to the FILE stream where errors will be printed. Typically stderr.
[in]modeFlags controlling the error printing behavior:
  • 0: Print only the first recorded error.
  • SDDS_VERBOSE_PrintErrors: Print all recorded errors.
  • SDDS_EXIT_PrintErrors: After printing errors, terminate the program by calling exit(1).
Note
After printing, the error stack is cleared. If mode includes SDDS_EXIT_PrintErrors, the program will terminate.
See also
SDDS_SetError
SDDS_NumberOfErrors
SDDS_ClearErrors

Definition at line 474 of file SDDS_utils.c.

474 {
475 int32_t i, depth;
476 char *programName;
477
478 if (!n_errors)
479 return;
480 if (!fp) {
482 return;
483 }
484 if (mode & SDDS_VERBOSE_PrintErrors)
485 depth = n_errors;
486 else
487 depth = 1;
488 programName = SDDS_GetRegisteredProgramNameCopy();
489 if (programName)
490 fprintf(fp, "Error for %s:\n", programName);
491 else
492 fputs("Error:\n", fp);
493 free(programName);
494 if (!error_description)
495 fprintf(stderr, "warning: internal error: error_description pointer is unexpectedly NULL\n");
496 else
497 for (i = 0; i < depth; i++) {
498 if (!error_description[i])
499 fprintf(stderr, "warning: internal error: error_description[%" PRId32 "] is unexpectedly NULL\n", i);
500 else
501 fprintf(fp, "%s", error_description[i]);
502 }
503 fflush(fp);
505 if (mode & SDDS_EXIT_PrintErrors)
506 exit(1);
507}
void SDDS_ClearErrors()
Clears all recorded error messages from the SDDS error stack.
Definition SDDS_utils.c:354

◆ SDDS_PrintTypedValue()

epicsShareFuncSDDS int32_t SDDS_PrintTypedValue ( void * data,
int64_t index,
int32_t type,
char * format,
FILE * fp,
uint32_t mode )
extern

Prints a data value of a specified type using an optional printf format string.

This function prints a single data value from a data array based on the specified type and index. It supports various data types defined by SDDS constants and allows customization of the output format.

Parameters
[in]dataPointer to the base address of the data array to be printed.
[in]indexThe index of the item within the data array to be printed.
[in]typeThe data type of the value to be printed, specified by one of the SDDS constants:
  • SDDS_LONGDOUBLE
  • SDDS_DOUBLE
  • SDDS_FLOAT
  • SDDS_LONG
  • SDDS_ULONG
  • SDDS_LONG64
  • SDDS_ULONG64
  • SDDS_SHORT
  • SDDS_USHORT
  • SDDS_CHARACTER
  • SDDS_STRING
[in]format(Optional) NULL-terminated string specifying a printf format. If NULL, a default format is used based on the data type.
[in]fpPointer to the FILE stream where the data will be printed.
[in]modeFlags controlling the printing behavior. Valid values are:
  • 0: Default behavior.
  • SDDS_PRINT_NOQUOTES: When printing strings, do not enclose them in quotes.
Returns
Returns 1 on success. On failure, returns 0 and records an error message.
Note
This function assumes that the data pointer points to an array of the specified type, and index is within the bounds of this array.
See also
SDDS_SetError

Definition at line 67 of file SDDS_utils.c.

67 {
68 char buffer[SDDS_PRINT_BUFLEN], *s;
69
70 if (!data) {
71 SDDS_SetError("Unable to print value--data pointer is NULL (SDDS_PrintTypedValue)");
72 return (0);
73 }
74 if (!fp) {
75 SDDS_SetError("Unable to print value--file pointer is NULL (SDDS_PrintTypedValue)");
76 return (0);
77 }
78 switch (type) {
79 case SDDS_SHORT:
80 fprintf(fp, format ? format : "%hd", *((short *)data + index));
81 break;
82 case SDDS_USHORT:
83 fprintf(fp, format ? format : "%hu", *((unsigned short *)data + index));
84 break;
85 case SDDS_LONG:
86 fprintf(fp, format ? format : "%" PRId32, *((int32_t *)data + index));
87 break;
88 case SDDS_ULONG:
89 fprintf(fp, format ? format : "%" PRIu32, *((uint32_t *)data + index));
90 break;
91 case SDDS_LONG64:
92 fprintf(fp, format ? format : "%" PRId64, *((int64_t *)data + index));
93 break;
94 case SDDS_ULONG64:
95 fprintf(fp, format ? format : "%" PRIu64, *((uint64_t *)data + index));
96 break;
97 case SDDS_FLOAT:
98 fprintf(fp, format ? format : "%15.8e", *((float *)data + index));
99 break;
100 case SDDS_DOUBLE:
101 fprintf(fp, format ? format : "%21.15e", *((double *)data + index));
102 break;
103 case SDDS_LONGDOUBLE:
104 if (LDBL_DIG == 18) {
105 fprintf(fp, format ? format : "%21.18Le", *((long double *)data + index));
106 } else {
107 fprintf(fp, format ? format : "%21.15Le", *((long double *)data + index));
108 }
109 break;
110 case SDDS_STRING:
111 s = *((char **)data + index);
112 if ((int32_t)strlen(s) > SDDS_PRINT_BUFLEN - 3) {
113 SDDS_SetError("Buffer size overflow (SDDS_PrintTypedValue)");
114 return 0;
115 }
116 SDDS_SprintTypedValue(data, index, type, format, buffer, mode);
117 fputs(buffer, fp);
118 break;
119 case SDDS_CHARACTER:
120 fprintf(fp, format ? format : "%c", *((char *)data + index));
121 break;
122 default:
123 SDDS_SetError("Unable to print value--unknown data type (SDDS_PrintTypedValue)");
124 return (0);
125 }
126 return (1);
127}

◆ SDDS_ProcessArrayString()

epicsShareFuncSDDS int32_t SDDS_ProcessArrayString ( SDDS_DATASET * SDDS_dataset,
char * string )
extern

Process an array definition string.

This function parses a string containing array definition information and updates the SDDS dataset accordingly.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure.
stringPointer to the array definition string.
Returns
Returns 1 on success, 0 on failure.

Definition at line 362 of file SDDS_process.c.

362 {
363 char *ptr1, *ptr2;
364 char *s;
365 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_ProcessArrayString"))
366 return (0);
367 if (!string)
368 return (0);
369 if (!SDDS_CopyString(&s, string))
370 return 0;
371 if (!(ptr1 = strchr(s, '&')) || !(ptr2 = strchr(ptr1, ' '))) {
372 free(s);
373 return 0;
374 }
375 *ptr2 = 0;
376 if (strcmp(ptr1, "&array") != 0) {
377 free(s);
378 return (0);
379 }
380 if (SDDS_ProcessArrayDefinition(SDDS_dataset, ptr2 + 1)) {
381 free(s);
382 if (!SDDS_SaveLayout(SDDS_dataset))
383 return (0);
384 return (1);
385 }
386 free(s);
387 return (0);
388}
int32_t SDDS_ProcessArrayDefinition(SDDS_DATASET *SDDS_dataset, char *s)
Process the array definition section of the SDDS dataset.

◆ SDDS_ProcessAssociateString()

epicsShareFuncSDDS int32_t SDDS_ProcessAssociateString ( SDDS_DATASET * SDDS_dataset,
char * string )
extern

Process an associate definition string.

This function parses a string containing associate definition information and updates the SDDS dataset accordingly.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure.
stringPointer to the associate definition string.
Returns
Returns 1 on success, 0 on failure.

Definition at line 400 of file SDDS_process.c.

400 {
401 char *ptr1, *ptr2;
402 char *s;
403
404 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_ProcessAssociateString"))
405 return (0);
406 if (!string)
407 return (0);
408 if (!SDDS_CopyString(&s, string))
409 return 0;
410 if (!(ptr1 = strchr(s, '&')) || !(ptr2 = strchr(ptr1, ' '))) {
411 free(s);
412 return 0;
413 }
414 *ptr2 = 0;
415 if (strcmp(ptr1, "&associate") != 0) {
416 free(s);
417 return (0);
418 }
419 *ptr2 = ' ';
420 if (SDDS_ProcessAssociateDefinition(SDDS_dataset, ptr2 + 1)) {
421 free(s);
422 if (!SDDS_SaveLayout(SDDS_dataset))
423 return (0);
424 return (1);
425 }
426 free(s);
427 return (0);
428}
int32_t SDDS_ProcessAssociateDefinition(SDDS_DATASET *SDDS_dataset, char *s)
Process the associate definition section of the SDDS dataset.

◆ SDDS_ProcessColumnString()

epicsShareFuncSDDS int32_t SDDS_ProcessColumnString ( SDDS_DATASET * SDDS_dataset,
char * string,
int32_t mode )
extern

Process a column definition string.

This function parses a string containing column definition information and updates the SDDS dataset accordingly.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure.
stringPointer to the column definition string.
modeMode indicating how the column is defined.
Returns
Returns 1 on success, 0 on failure.

Definition at line 283 of file SDDS_process.c.

283 {
284 char *ptr1, *ptr2;
285 char *s;
286 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_ProcessColumnString"))
287 return (0);
288 if (!string)
289 return (0);
290 if (!SDDS_CopyString(&s, string))
291 return 0;
292 if (!(ptr1 = strchr(s, '&')) || !(ptr2 = strchr(ptr1, ' '))) {
293 free(s);
294 return 0;
295 }
296 *ptr2 = 0;
297 if (strcmp(ptr1, "&column") != 0) {
298 free(s);
299 return (0);
300 }
301 if (SDDS_ProcessColumnDefinition(SDDS_dataset, ptr2 + 1)) {
302 free(s);
303 SDDS_dataset->layout.column_definition[SDDS_dataset->layout.n_columns - 1].definition_mode = mode;
304 if (!SDDS_SaveLayout(SDDS_dataset))
305 return (0);
306 return (1);
307 }
308 free(s);
309 return (0);
310}
int32_t SDDS_ProcessColumnDefinition(SDDS_DATASET *SDDS_dataset, char *s)
Process the column definition section of the SDDS dataset.

◆ SDDS_ProcessParameterString()

epicsShareFuncSDDS int32_t SDDS_ProcessParameterString ( SDDS_DATASET * SDDS_dataset,
char * string,
int32_t mode )
extern

Process a parameter definition string.

This function parses a string containing parameter definition information and updates the SDDS dataset accordingly.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure.
stringPointer to the parameter definition string.
modeMode indicating how the parameter is defined.
Returns
Returns 1 on success, 0 on failure.

Definition at line 323 of file SDDS_process.c.

323 {
324 char *ptr1, *ptr2;
325 char *s;
326 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_ProcessParameterString"))
327 return (0);
328 if (!string)
329 return (0);
330 if (!SDDS_CopyString(&s, string))
331 return 0;
332 if (!(ptr1 = strchr(s, '&')) || !(ptr2 = strchr(ptr1, ' '))) {
333 free(s);
334 return 0;
335 }
336 *ptr2 = 0;
337 if (strcmp(ptr1, "&parameter") != 0) {
338 free(s);
339 return (0);
340 }
341 if (SDDS_ProcessParameterDefinition(SDDS_dataset, ptr2 + 1)) {
342 free(s);
343 SDDS_dataset->layout.parameter_definition[SDDS_dataset->layout.n_parameters - 1].definition_mode = mode;
344 if (!SDDS_SaveLayout(SDDS_dataset))
345 return (0);
346 return (1);
347 }
348 free(s);
349 return (0);
350}
int32_t SDDS_ProcessParameterDefinition(SDDS_DATASET *SDDS_dataset, char *s)
Process the parameter definition section of the SDDS dataset.

◆ SDDS_ReadAsciiPage()

epicsShareFuncSDDS int32_t SDDS_ReadAsciiPage ( SDDS_DATASET * SDDS_dataset,
int64_t sparse_interval,
int64_t sparse_offset,
int32_t sparse_statistics )
extern

Reads the next SDDS ASCII page into memory with optional data sparsity and statistics.

This function reads the next page of data from an ASCII SDDS file into the provided dataset. It supports reading data with specified sparsity (interval and offset) and can compute statistics such as average, median, minimum, or maximum over the sparse data.

Parameters
SDDS_datasetPointer to the SDDS dataset where the data will be stored.
sparse_intervalInterval for sparsity; read every nth row if greater than 1.
sparse_offsetOffset for sparsity; number of initial rows to skip.
sparse_statisticsStatistic to compute over the sparse data:
  • 0: None
  • 1: Average
  • 2: Median
  • 3: Minimum
  • 4: Maximum
Returns
Returns the page number on success, -1 if end-of-file is reached, or 0 on error.
Note
The function utilizes SDDS_ReadAsciiPageDetailed() to perform the actual reading.

Definition at line 1225 of file SDDS_ascii.c.

1225 {
1226 return SDDS_ReadAsciiPageDetailed(SDDS_dataset, sparse_interval, sparse_offset, 0, sparse_statistics);
1227}
int32_t SDDS_ReadAsciiPageDetailed(SDDS_DATASET *SDDS_dataset, int64_t sparse_interval, int64_t sparse_offset, int64_t last_rows, int32_t sparse_statistics)
Reads a detailed page of data from an ASCII file into an SDDS dataset with optional sparsity and stat...

◆ SDDS_ReadLayout()

epicsShareFuncSDDS int32_t SDDS_ReadLayout ( SDDS_DATASET * SDDS_dataset,
FILE * fp )
extern

Reads the header layout of an SDDS dataset from a file.

Parameters
SDDS_datasetThe SDDS dataset structure to store the layout information.
fpThe file pointer to the SDDS file.
Returns
Returns 1 on success, 0 on failure.

Definition at line 518 of file SDDS_input.c.

518 {
519 char buffer[SDDS_MAXLINE];
520 char *groupName, *ptr;
521 FILE *fp1;
522 int32_t retval, bigEndianMachine;
523 uint32_t commentFlags;
524
525 if (!fp) {
526 SDDS_SetError("Unable to read layout--NULL file pointer (SDDS_ReadLayout)");
527 return (0);
528 }
529 if (SDDS_dataset->layout.depth == 0) {
530 if (SDDS_dataset->layout.disconnected) {
531 SDDS_SetError("Can't read layout--file is disconnected (SDDS_ReadLayout)");
532 return 0;
533 }
534 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_ReadLayout")) {
535 fclose(fp);
536 return (0);
537 }
538 SDDS_dataset->layout.layout_written = 1; /* it is already in the file */
539 if (!fgets(SDDS_dataset->layout.s, SDDS_MAXLINE, fp)) {
540 fclose(fp);
541 SDDS_SetError("Unable to read layout--no header lines found (SDDS_ReadLayout)");
542 return (0);
543 }
544 if (strncmp(SDDS_dataset->layout.s, "SDDS", 4) != 0) {
545 fclose(fp);
546 SDDS_SetError("Unable to read layout--no header lines found (SDDS_ReadLayout)");
547 return (0);
548 }
549 if (sscanf(SDDS_dataset->layout.s + 4, "%" SCNd32, &SDDS_dataset->layout.version) != 1) {
550 fclose(fp);
551 SDDS_SetError("Unable to read layout--no version number on first line (SDDS_ReadLayout)");
552 return (0);
553 }
554 SDDS_ResetSpecialCommentsModes(SDDS_dataset);
555 SDDS_dataset->layout.data_command_seen = 0;
556 }
557 while (SDDS_GetNamelist(SDDS_dataset, SDDS_dataset->layout.s, SDDS_MAXLINE, fp)) {
558#if DEBUG
559 strcpy(buffer, SDDS_dataset->layout.s);
560#endif
561 groupName = SDDS_dataset->layout.s + 1;
562 if (!(ptr = strpbrk(SDDS_dataset->layout.s, " \t"))) {
563 SDDS_SetError("Unable to read layout---no groupname in namelist (SDDS_ReadLayout)");
564 return 0;
565 }
566 *ptr = 0;
567 switch (match_string(groupName, SDDS_command, SDDS_NUM_COMMANDS, EXACT_MATCH)) {
568 case SDDS_DESCRIPTION_COMMAND:
569 if (!SDDS_ProcessDescription(SDDS_dataset, ptr + 1)) {
570 fclose(fp);
571 SDDS_SetError("Unable to process description (SDDS_ReadLayout)");
572 return (0);
573 }
574 break;
575 case SDDS_COLUMN_COMMAND:
576 if (!SDDS_ProcessColumnDefinition(SDDS_dataset, ptr + 1)) {
577 fclose(fp);
578 SDDS_SetError("Unable to process column definition (SDDS_ReadLayout)");
579 return (0);
580 }
581 break;
582 case SDDS_PARAMETER_COMMAND:
583 if (!SDDS_ProcessParameterDefinition(SDDS_dataset, ptr + 1)) {
584 fclose(fp);
585 SDDS_SetError("Unable to process parameter definition (SDDS_ReadLayout)");
586 return (0);
587 }
588 break;
589 case SDDS_ASSOCIATE_COMMAND:
590#if RW_ASSOCIATES != 0
591 if (!SDDS_ProcessAssociateDefinition(SDDS_dataset, ptr + 1)) {
592 fclose(fp);
593 SDDS_SetError("Unable to process associate definition (SDDS_ReadLayout)");
594 return (0);
595 }
596#endif
597 break;
598 case SDDS_DATA_COMMAND:
599 if (!SDDS_ProcessDataMode(SDDS_dataset, ptr + 1)) {
600 fclose(fp);
601 SDDS_SetError("Unable to process data mode (SDDS_ReadLayout)");
602 return (0);
603 }
604 if (SDDS_dataset->layout.data_command_seen) {
605 /* should never happen */
606 fclose(fp);
607 SDDS_SetError("Unable to read layout--multiple data commands (SDDS_ReadLayout)");
608 return (0);
609 }
610 if (!SDDS_SaveLayout(SDDS_dataset)) {
611 SDDS_SetError("Unable to read layout--couldn't save layout (SDDS_ReadLayout)");
612 return (0);
613 }
614 SDDS_dataset->layout.data_command_seen = 1;
615 commentFlags = SDDS_GetSpecialCommentsModes(SDDS_dataset);
616 if ((commentFlags & SDDS_BIGENDIAN_SEEN) && (commentFlags & SDDS_LITTLEENDIAN_SEEN)) {
617 SDDS_SetError("Unable to read data as it says it is both big and little endian (SDDS_ReadLayout)");
618 return (0);
619 }
620 bigEndianMachine = SDDS_IsBigEndianMachine();
621 SDDS_dataset->swapByteOrder = SDDS_dataset->layout.byteOrderDeclared = 0;
622 SDDS_dataset->autoRecover = 0;
623 if ((commentFlags & SDDS_BIGENDIAN_SEEN) || (SDDS_dataset->layout.data_mode.endian == SDDS_BIGENDIAN)) {
624 SDDS_dataset->layout.byteOrderDeclared = SDDS_BIGENDIAN_SEEN;
625 if (!bigEndianMachine)
626 SDDS_dataset->swapByteOrder = 1;
627 }
628 if ((commentFlags & SDDS_LITTLEENDIAN_SEEN) || (SDDS_dataset->layout.data_mode.endian == SDDS_LITTLEENDIAN)) {
629 SDDS_dataset->layout.byteOrderDeclared = SDDS_LITTLEENDIAN_SEEN;
630 if (bigEndianMachine)
631 SDDS_dataset->swapByteOrder = 1;
632 }
633 if ((commentFlags & SDDS_FIXED_ROWCOUNT_SEEN) || (SDDS_dataset->layout.data_mode.fixed_row_count))
634 if (!SDDS_SetAutoReadRecovery(SDDS_dataset, SDDS_AUTOREADRECOVER))
635 return (0);
636 return (1);
637 case SDDS_INCLUDE_COMMAND:
638 if (!(fp1 = SDDS_ProcessIncludeCommand(SDDS_dataset, ptr + 1))) {
639 fclose(fp);
640 SDDS_SetError("Unable to process include command (SDDS_ReadLayout)");
641 return (0);
642 }
643 SDDS_dataset->layout.depth += 1;
644 retval = SDDS_ReadLayout(SDDS_dataset, fp1);
645 SDDS_dataset->layout.depth -= 1;
646 fclose(fp1);
647 if (retval == 0) {
648 return (0);
649 }
650 if (SDDS_dataset->layout.data_command_seen) {
651 return (1);
652 }
653 break;
654 case SDDS_ARRAY_COMMAND:
655 if (!SDDS_ProcessArrayDefinition(SDDS_dataset, ptr + 1)) {
656 fclose(fp);
657 SDDS_SetError("Unable to process array definition (SDDS_ReadLayout)");
658 return (0);
659 }
660 break;
661 default:
662 fclose(fp);
663 sprintf(buffer, "Unknown layout entry %s given (SDDS_ReadLayout)", groupName);
664 SDDS_SetError(buffer);
665 return (0);
666 }
667 }
668 /* on recursive calls, it's okay to hit EOF */
669 if ((feof(fp) && SDDS_dataset->layout.depth != 0) || SDDS_dataset->layout.data_command_seen)
670 return (1);
671 return (0);
672}
char * SDDS_command[SDDS_NUM_COMMANDS]
Array of supported SDDS command names.
Definition SDDS_data.c:81
int32_t SDDS_SetAutoReadRecovery(SDDS_DATASET *SDDS_dataset, uint32_t mode)
int32_t SDDS_GetNamelist(SDDS_DATASET *SDDS_dataset, char *buffer, int32_t buflen, FILE *fp)
Reads a namelist from a file into a buffer.
Definition SDDS_input.c:249
int32_t SDDS_ProcessArrayDefinition(SDDS_DATASET *SDDS_dataset, char *s)
Process the array definition section of the SDDS dataset.
int32_t SDDS_ProcessParameterDefinition(SDDS_DATASET *SDDS_dataset, char *s)
Process the parameter definition section of the SDDS dataset.
int32_t SDDS_ProcessAssociateDefinition(SDDS_DATASET *SDDS_dataset, char *s)
Process the associate definition section of the SDDS dataset.
FILE * SDDS_ProcessIncludeCommand(SDDS_DATASET *SDDS_dataset, char *s)
Process the include command within the SDDS dataset.
int32_t SDDS_ProcessDataMode(SDDS_DATASET *SDDS_dataset, char *s)
Process the data mode section of the SDDS dataset.
uint32_t SDDS_GetSpecialCommentsModes(SDDS_DATASET *SDDS_dataset)
Retrieves the current special comments modes set in the SDDS dataset.
int32_t SDDS_ProcessDescription(SDDS_DATASET *SDDS_dataset, char *s)
Process the description section of the SDDS dataset.
void SDDS_ResetSpecialCommentsModes(SDDS_DATASET *SDDS_dataset)
Resets the special comments modes in the SDDS dataset.
int32_t SDDS_ProcessColumnDefinition(SDDS_DATASET *SDDS_dataset, char *s)
Process the column definition section of the SDDS dataset.

◆ SDDS_ReadNewBinaryRows()

epicsShareFuncSDDS int32_t SDDS_ReadNewBinaryRows ( SDDS_DATASET * SDDS_dataset)
extern

Reads new binary rows from the SDDS dataset.

This function updates the SDDS dataset by reading any new rows that have been added to the underlying file since the last read operation. It verifies that the dataset is in a compatible binary format and ensures that byte order and compression settings are supported. If the number of rows in the file exceeds the currently allocated rows in memory, the function expands the dataset's internal storage to accommodate the new rows.

Parameters
[in,out]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset to read from.
Returns
int32_t Returns the number of new rows successfully read on success, or -1 if an error occurred.
Return values
>0The number of new rows read and added to the dataset.
-1An error occurred during the read operation, such as unsupported file format, I/O errors, or memory allocation failures.
Note
This function does not support MPI parallel I/O, ASCII files, column-major order binary files, non-native byte orders, or compressed files (gzip or lzma). Attempts to use these features will result in an error.

Definition at line 2962 of file SDDS_binary.c.

2962 {
2963 int64_t row, offset, newRows = 0;
2964 int32_t rowsPresent32;
2965 int64_t rowsPresent;
2966
2967#if SDDS_MPI_IO
2968 if (SDDS_dataset->parallel_io) {
2969 SDDS_SetError("Error: MPI mode not supported yet in SDDS_ReadNewBinaryRows");
2970 return -1;
2971 }
2972#endif
2973 if (SDDS_dataset->original_layout.data_mode.mode == SDDS_ASCII) {
2974 SDDS_SetError("Error: ASCII files not supported in SDDS_ReadNewBinaryRows");
2975 return -1;
2976 }
2977 if (SDDS_dataset->layout.data_mode.column_major) {
2978 SDDS_SetError("Error: column-major order binary files not supported in SDDS_ReadNewBinaryRows");
2979 return -1;
2980 }
2981 if (SDDS_dataset->swapByteOrder) {
2982 SDDS_SetError("Error: Non-native endian not supported yet in SDDS_ReadNewBinaryRows");
2983 return -1;
2984 }
2985#if defined(zLib)
2986 if (SDDS_dataset->layout.gzipFile) {
2987 SDDS_SetError("Error: gzip compressed files not supported yet in SDDS_ReadNewBinaryRows");
2988 return -1;
2989 } else {
2990#endif
2991 if (SDDS_dataset->layout.lzmaFile) {
2992 SDDS_SetError("Error: lzma compressed files not supported yet in SDDS_ReadNewBinaryRows");
2993 return -1;
2994 }
2995#if defined(zLib)
2996 }
2997#endif
2998
2999 // Read how many rows we have now
3000 offset = ftell(SDDS_dataset->layout.fp);
3001 fseek(SDDS_dataset->layout.fp, SDDS_dataset->rowcount_offset, 0);
3002 if (SDDS_dataset->layout.data_mode.mode == SDDS_BINARY) {
3003 if (fread(&rowsPresent32, sizeof(rowsPresent32), 1, SDDS_dataset->layout.fp) == 0) {
3004 SDDS_SetError("Error: row count not present or not correct length");
3005 return -1;
3006 }
3007 if (SDDS_dataset->swapByteOrder) {
3008 SDDS_SwapLong(&rowsPresent32);
3009 }
3010 if (rowsPresent32 == INT32_MIN) {
3011 if (fread(&rowsPresent, sizeof(rowsPresent), 1, SDDS_dataset->layout.fp) == 0) {
3012 SDDS_SetError("Error: row count not present or not correct length");
3013 return -1;
3014 }
3015 if (SDDS_dataset->swapByteOrder) {
3016 SDDS_SwapLong64(&rowsPresent);
3017 }
3018 } else {
3019 rowsPresent = rowsPresent32;
3020 }
3021 } else {
3022 char buffer[30];
3023 if (!fgets(buffer, 30, SDDS_dataset->layout.fp) || strlen(buffer) != 21 || sscanf(buffer, "%" SCNd64, &rowsPresent) != 1) {
3024 SDDS_SetError("Error: row count not present or not correct length");
3025 return -1;
3026 }
3027 }
3028 fseek(SDDS_dataset->layout.fp, offset, 0);
3029
3030 // If the row count listed in the file is greather than the allocated rows, then lengthen the table in memory
3031 if (rowsPresent > SDDS_dataset->n_rows_allocated) {
3032 if (!SDDS_LengthenTable(SDDS_dataset, rowsPresent + 3)) {
3033 return -1;
3034 }
3035 }
3036
3037 for (row = SDDS_dataset->n_rows; row < rowsPresent; row++) {
3038 if (!SDDS_ReadBinaryRow(SDDS_dataset, row, 0)) {
3039 if (SDDS_dataset->autoRecover) {
3040 row--;
3041 SDDS_dataset->autoRecovered = 1;
3043 break;
3044 }
3045 SDDS_SetError("Unable to read page--error reading data row");
3046 return -1;
3047 }
3048 }
3049 newRows = row + 1 - SDDS_dataset->n_rows;
3050 SDDS_dataset->n_rows = row + 1;
3051 return newRows;
3052}
int32_t SDDS_ReadBinaryRow(SDDS_DATASET *SDDS_dataset, int64_t row, int32_t skip)
Reads a binary row from the specified SDDS dataset.

◆ SDDS_ReadNonNativeBinaryArrays()

int32_t SDDS_ReadNonNativeBinaryArrays ( SDDS_DATASET * SDDS_dataset)

Reads non-native endian binary arrays from an SDDS dataset.

This function iterates through all array definitions in the specified SDDS dataset and reads their binary data from the underlying file. It handles various data types, including short, unsigned short, long, unsigned long, long long, unsigned long long, float, double, and long double. For string arrays, it reads each string individually, ensuring proper memory allocation and byte order conversion. The function supports different compression formats, including uncompressed, LZMA-compressed, and GZIP-compressed files. After reading, it swaps the endianness of the array data to match the system's native byte order.

Parameters
[in,out]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset to read from.
Returns
int32_t Returns 1 on successful reading and byte-swapping of all arrays, or 0 if an error occurred.
Return values
1All non-native endian arrays were successfully read and byte-swapped.
0An error occurred during the read or byte-swapping process, such as I/O failures, memory allocation issues, or corrupted array definitions.
Note
This function modifies the dataset's array data in place. It should be called after successfully opening and preparing the dataset for reading. Ensure that the dataset structure is properly initialized to prevent undefined behavior.

Definition at line 4708 of file SDDS_binary.c.

4708 {
4709 int32_t i, j;
4710 SDDS_LAYOUT *layout;
4711 /* char *predefined_format; */
4712 /* static char buffer[SDDS_MAXLINE]; */
4713#if defined(zLib)
4714 gzFile gzfp = NULL;
4715#endif
4716 FILE *fp = NULL;
4717 struct lzmafile *lzmafp = NULL;
4718 SDDS_ARRAY *array;
4719 SDDS_FILEBUFFER *fBuffer;
4720
4721 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_ReadNonNativeBinaryArrays"))
4722 return (0);
4723 layout = &SDDS_dataset->layout;
4724 if (!layout->n_arrays)
4725 return (1);
4726#if defined(zLib)
4727 if (SDDS_dataset->layout.gzipFile) {
4728 gzfp = layout->gzfp;
4729 } else {
4730#endif
4731 if (SDDS_dataset->layout.lzmaFile) {
4732 lzmafp = layout->lzmafp;
4733 } else {
4734 fp = layout->fp;
4735 }
4736#if defined(zLib)
4737 }
4738#endif
4739 fBuffer = &SDDS_dataset->fBuffer;
4740 if (!SDDS_dataset->array) {
4741 SDDS_SetError("Unable to read array--pointer to structure storage area is NULL (SDDS_ReadNonNativeBinaryArrays)");
4742 return (0);
4743 }
4744 for (i = 0; i < layout->n_arrays; i++) {
4745 array = SDDS_dataset->array + i;
4746 if (array->definition && !SDDS_FreeArrayDefinition(array->definition)) {
4747 SDDS_SetError("Unable to get array--array definition corrupted (SDDS_ReadNonNativeBinaryArrays)");
4748 return (0);
4749 }
4750 if (!SDDS_CopyArrayDefinition(&array->definition, layout->array_definition + i)) {
4751 SDDS_SetError("Unable to read array--definition copy failed (SDDS_ReadNonNativeBinaryArrays)");
4752 return (0);
4753 }
4754 /*if (array->dimension) free(array->dimension); */
4755 if (!(array->dimension = SDDS_Realloc(array->dimension, sizeof(*array->dimension) * array->definition->dimensions))) {
4756 SDDS_SetError("Unable to read array--allocation failure (SDDS_ReadNonNativeBinaryArrays)");
4757 return (0);
4758 }
4759#if defined(zLib)
4760 if (SDDS_dataset->layout.gzipFile) {
4761 if (!SDDS_GZipBufferedRead(array->dimension, sizeof(*array->dimension) * array->definition->dimensions, gzfp, fBuffer, SDDS_LONG, SDDS_dataset->layout.byteOrderDeclared)) {
4762 SDDS_SetError("Unable to read arrays--failure reading dimensions (SDDS_ReadNonNativeBinaryArrays)");
4763 return (0);
4764 }
4765 } else {
4766#endif
4767 if (SDDS_dataset->layout.lzmaFile) {
4768 if (!SDDS_LZMABufferedRead(array->dimension, sizeof(*array->dimension) * array->definition->dimensions, lzmafp, fBuffer, SDDS_LONG, SDDS_dataset->layout.byteOrderDeclared)) {
4769 SDDS_SetError("Unable to read arrays--failure reading dimensions (SDDS_ReadNonNativeBinaryArrays)");
4770 return (0);
4771 }
4772 } else {
4773 if (!SDDS_BufferedRead(array->dimension, sizeof(*array->dimension) * array->definition->dimensions, fp, fBuffer, SDDS_LONG, SDDS_dataset->layout.byteOrderDeclared)) {
4774 SDDS_SetError("Unable to read arrays--failure reading dimensions (SDDS_ReadNonNativeBinaryArrays)");
4775 return (0);
4776 }
4777 }
4778#if defined(zLib)
4779 }
4780#endif
4781 array->elements = 1;
4782 for (j = 0; j < array->definition->dimensions; j++) {
4783 SDDS_SwapLong(&(array->dimension[j]));
4784 array->elements *= array->dimension[j];
4785 }
4786 if (array->data)
4787 free(array->data);
4788 array->data = array->pointer = NULL;
4789 if (array->elements == 0)
4790 continue;
4791 if (array->elements < 0) {
4792 SDDS_SetError("Unable to read array--number of elements is negative (SDDS_ReadNonNativeBinaryArrays)");
4793 return (0);
4794 }
4795 if (!(array->data = SDDS_Realloc(array->data, array->elements * SDDS_type_size[array->definition->type - 1]))) {
4796 SDDS_SetError("Unable to read array--allocation failure (SDDS_ReadNonNativeBinaryArrays)");
4797 return (0);
4798 }
4799 if (array->definition->type == SDDS_STRING) {
4800#if defined(zLib)
4801 if (SDDS_dataset->layout.gzipFile) {
4802 for (j = 0; j < array->elements; j++) {
4803 if (!(((char **)(array->data))[j] = SDDS_ReadNonNativeGZipBinaryString(gzfp, fBuffer, 0))) {
4804 SDDS_SetError("Unable to read arrays--failure reading string (SDDS_ReadNonNativeBinaryArrays)");
4805 return (0);
4806 }
4807 }
4808 } else {
4809#endif
4810 if (SDDS_dataset->layout.lzmaFile) {
4811 for (j = 0; j < array->elements; j++) {
4812 if (!(((char **)(array->data))[j] = SDDS_ReadNonNativeLZMABinaryString(lzmafp, fBuffer, 0))) {
4813 SDDS_SetError("Unable to read arrays--failure reading string (SDDS_ReadNonNativeBinaryArrays)");
4814 return (0);
4815 }
4816 }
4817 } else {
4818 for (j = 0; j < array->elements; j++) {
4819 if (!(((char **)(array->data))[j] = SDDS_ReadNonNativeBinaryString(fp, fBuffer, 0))) {
4820 SDDS_SetError("Unable to read arrays--failure reading string (SDDS_ReadNonNativeBinaryArrays)");
4821 return (0);
4822 }
4823 }
4824 }
4825#if defined(zLib)
4826 }
4827#endif
4828 } else {
4829#if defined(zLib)
4830 if (SDDS_dataset->layout.gzipFile) {
4831 if (!SDDS_GZipBufferedRead(array->data, SDDS_type_size[array->definition->type - 1] * array->elements, gzfp, fBuffer, array->definition->type, SDDS_dataset->layout.byteOrderDeclared)) {
4832 SDDS_SetError("Unable to read arrays--failure reading values (SDDS_ReadNonNativeBinaryArrays)");
4833 return (0);
4834 }
4835 } else {
4836#endif
4837 if (SDDS_dataset->layout.lzmaFile) {
4838 if (!SDDS_LZMABufferedRead(array->data, SDDS_type_size[array->definition->type - 1] * array->elements, lzmafp, fBuffer, array->definition->type, SDDS_dataset->layout.byteOrderDeclared)) {
4839 SDDS_SetError("Unable to read arrays--failure reading values (SDDS_ReadNonNativeBinaryArrays)");
4840 return (0);
4841 }
4842 } else {
4843 if (!SDDS_BufferedRead(array->data, SDDS_type_size[array->definition->type - 1] * array->elements, fp, fBuffer, array->definition->type, SDDS_dataset->layout.byteOrderDeclared)) {
4844 SDDS_SetError("Unable to read arrays--failure reading values (SDDS_ReadNonNativeBinaryArrays)");
4845 return (0);
4846 }
4847 }
4848#if defined(zLib)
4849 }
4850#endif
4851 }
4852 }
4853 SDDS_SwapEndsArrayData(SDDS_dataset);
4854 return (1);
4855}
char * SDDS_ReadNonNativeLZMABinaryString(struct lzmafile *lzmafp, SDDS_FILEBUFFER *fBuffer, int32_t skip)
Reads a non-native endian binary string from an LZMA-compressed file.
int32_t SDDS_LZMABufferedRead(void *target, int64_t targetSize, struct lzmafile *lzmafp, SDDS_FILEBUFFER *fBuffer, int32_t type, int32_t byteOrder)
int32_t SDDS_BufferedRead(void *target, int64_t targetSize, FILE *fp, SDDS_FILEBUFFER *fBuffer, int32_t type, int32_t byteOrder)
int32_t SDDS_SwapEndsArrayData(SDDS_DATASET *SDDSin)
Swaps the endianness of the array data in an SDDS dataset.
char * SDDS_ReadNonNativeBinaryString(FILE *fp, SDDS_FILEBUFFER *fBuffer, int32_t skip)
Reads a non-native endian binary string from a file.

◆ SDDS_ReadNonNativeBinaryPage()

int32_t SDDS_ReadNonNativeBinaryPage ( SDDS_DATASET * SDDS_dataset,
int64_t sparse_interval,
int64_t sparse_offset )

Reads a non-native endian binary page from an SDDS dataset.

This function reads a binary page from the specified SDDS dataset, handling data with non-native endianness. It performs necessary byte order conversions to ensure correct data interpretation on the host system. The function supports sparse reading based on the provided interval and offset.

Parameters
[in,out]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset to read from.
[in]sparse_intervalInterval between rows to be read for sparsity.
[in]sparse_offsetOffset to start reading rows for sparsity.
Returns
int32_t Returns the number of rows read on success, or 0 on failure.
Return values
>0Number of rows successfully read.
0An error occurred during the read operation, such as I/O failures, data corruption, or unsupported data modes.
Note
This function is a wrapper for SDDS_ReadNonNativeBinaryPageDetailed with specific parameters.

Definition at line 4312 of file SDDS_binary.c.

4312 {
4313 return SDDS_ReadNonNativeBinaryPageDetailed(SDDS_dataset, sparse_interval, sparse_offset, 0);
4314}
int32_t SDDS_ReadNonNativeBinaryPageDetailed(SDDS_DATASET *SDDS_dataset, int64_t sparse_interval, int64_t sparse_offset, int64_t last_rows)
Reads a detailed non-native endian binary page from an SDDS dataset.

◆ SDDS_ReadNonNativeBinaryParameters()

int32_t SDDS_ReadNonNativeBinaryParameters ( SDDS_DATASET * SDDS_dataset)

Reads non-native endian binary parameters from an SDDS dataset.

This function iterates through all parameter definitions in the specified SDDS dataset and reads their binary data from the underlying file. It handles various data types, including short, unsigned short, long, unsigned long, long long, unsigned long long, float, double, and long double. For string parameters, it reads each string individually, ensuring proper memory allocation and byte order conversion. Parameters with fixed values are processed by scanning the fixed value strings into the appropriate data types. The function supports different compression formats, including uncompressed, LZMA-compressed, and GZIP-compressed files.

Parameters
[in,out]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset to read from.
Returns
int32_t Returns 1 on successful reading and byte-swapping of all parameters, or 0 if an error occurred.
Return values
1All non-native endian parameters were successfully read and byte-swapped.
0An error occurred during the read or byte-swapping process, such as I/O failures, memory allocation issues, or corrupted parameter definitions.
Note
This function modifies the dataset's parameter data in place. It should be called after successfully opening and preparing the dataset for reading. Ensure that the dataset structure is properly initialized to prevent undefined behavior.

Definition at line 4592 of file SDDS_binary.c.

4592 {
4593 int32_t i;
4594 SDDS_LAYOUT *layout;
4595 /* char *predefined_format; */
4596 char buffer[SDDS_MAXLINE];
4597#if defined(zLib)
4598 gzFile gzfp = NULL;
4599#endif
4600 FILE *fp = NULL;
4601 struct lzmafile *lzmafp = NULL;
4602 SDDS_FILEBUFFER *fBuffer;
4603
4604 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_ReadNonNativeBinaryParameters"))
4605 return (0);
4606 layout = &SDDS_dataset->layout;
4607 if (!layout->n_parameters)
4608 return (1);
4609#if defined(zLib)
4610 if (SDDS_dataset->layout.gzipFile) {
4611 gzfp = layout->gzfp;
4612 } else {
4613#endif
4614 if (SDDS_dataset->layout.lzmaFile) {
4615 lzmafp = layout->lzmafp;
4616 } else {
4617 fp = layout->fp;
4618 }
4619#if defined(zLib)
4620 }
4621#endif
4622 fBuffer = &SDDS_dataset->fBuffer;
4623 for (i = 0; i < layout->n_parameters; i++) {
4624 if (layout->parameter_definition[i].definition_mode & SDDS_WRITEONLY_DEFINITION)
4625 continue;
4626 if (layout->parameter_definition[i].fixed_value) {
4627 strcpy(buffer, layout->parameter_definition[i].fixed_value);
4628 if (!SDDS_ScanData(buffer, layout->parameter_definition[i].type, 0, SDDS_dataset->parameter[i], 0, 1)) {
4629 SDDS_SetError("Unable to read page--parameter scanning error (SDDS_ReadNonNativeBinaryParameters)");
4630 return (0);
4631 }
4632 } else if (layout->parameter_definition[i].type == SDDS_STRING) {
4633 if (*(char **)SDDS_dataset->parameter[i])
4634 free(*(char **)SDDS_dataset->parameter[i]);
4635#if defined(zLib)
4636 if (SDDS_dataset->layout.gzipFile) {
4637 if (!(*((char **)SDDS_dataset->parameter[i]) = SDDS_ReadNonNativeGZipBinaryString(gzfp, fBuffer, 0))) {
4638 SDDS_SetError("Unable to read parameters--failure reading string (SDDS_ReadNonNativeBinaryParameters)");
4639 return (0);
4640 }
4641 } else {
4642#endif
4643 if (SDDS_dataset->layout.lzmaFile) {
4644 if (!(*((char **)SDDS_dataset->parameter[i]) = SDDS_ReadNonNativeLZMABinaryString(lzmafp, fBuffer, 0))) {
4645 SDDS_SetError("Unable to read parameters--failure reading string (SDDS_ReadNonNativeBinaryParameters)");
4646 return (0);
4647 }
4648 } else {
4649 if (!(*((char **)SDDS_dataset->parameter[i]) = SDDS_ReadNonNativeBinaryString(fp, fBuffer, 0))) {
4650 SDDS_SetError("Unable to read parameters--failure reading string (SDDS_ReadNonNativeBinaryParameters)");
4651 return (0);
4652 }
4653 }
4654#if defined(zLib)
4655 }
4656#endif
4657 } else {
4658#if defined(zLib)
4659 if (SDDS_dataset->layout.gzipFile) {
4660 if (!SDDS_GZipBufferedRead(SDDS_dataset->parameter[i], SDDS_type_size[layout->parameter_definition[i].type - 1], gzfp, fBuffer, layout->parameter_definition[i].type, SDDS_dataset->layout.byteOrderDeclared)) {
4661 SDDS_SetError("Unable to read parameters--failure reading value (SDDS_ReadNonNativeBinaryParameters)");
4662 return (0);
4663 }
4664 } else {
4665#endif
4666 if (SDDS_dataset->layout.lzmaFile) {
4667 if (!SDDS_LZMABufferedRead(SDDS_dataset->parameter[i], SDDS_type_size[layout->parameter_definition[i].type - 1], lzmafp, fBuffer, layout->parameter_definition[i].type, SDDS_dataset->layout.byteOrderDeclared)) {
4668 SDDS_SetError("Unable to read parameters--failure reading value (SDDS_ReadNonNativeBinaryParameters)");
4669 return (0);
4670 }
4671 } else {
4672 if (!SDDS_BufferedRead(SDDS_dataset->parameter[i], SDDS_type_size[layout->parameter_definition[i].type - 1], fp, fBuffer, layout->parameter_definition[i].type, SDDS_dataset->layout.byteOrderDeclared)) {
4673 SDDS_SetError("Unable to read parameters--failure reading value (SDDS_ReadNonNativeBinaryParameters)");
4674 return (0);
4675 }
4676 }
4677#if defined(zLib)
4678 }
4679#endif
4680 }
4681 }
4682 SDDS_SwapEndsParameterData(SDDS_dataset);
4683 return (1);
4684}
int32_t SDDS_SwapEndsParameterData(SDDS_DATASET *SDDSin)
Swaps the endianness of the parameter data in an SDDS dataset.

◆ SDDS_ReadNonNativeBinaryRow()

int32_t SDDS_ReadNonNativeBinaryRow ( SDDS_DATASET * SDDS_dataset,
int64_t row,
int32_t skip )

Reads a non-native endian binary row from an SDDS dataset.

This function reads a single row of data from the specified SDDS dataset, handling data with non-native endianness. It iterates through all column definitions and reads each column's data for the given row. For string columns, it ensures proper memory allocation and byte order conversion. For other data types, it reads the binary data and performs necessary byte swapping. The function supports different compression formats, including uncompressed, LZMA-compressed, and GZIP-compressed files.

Parameters
[in,out]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset to read from.
[in]rowThe index of the row to read.
[in]skipIf non-zero, the function will skip reading the row data, useful for sparse reading.
Returns
int32_t Returns 1 on successful reading of the row, or 0 if an error occurred.
Return values
1The row was successfully read and byte-swapped.
0An error occurred during the read or byte-swapping process, such as I/O failures or corrupted data.
Note
This function modifies the dataset's data in place. It should be called after successfully opening and preparing the dataset for reading. Ensure that the dataset structure is properly initialized to prevent undefined behavior.

Definition at line 4878 of file SDDS_binary.c.

4878 {
4879 int64_t i, type, size;
4880 SDDS_LAYOUT *layout;
4881#if defined(zLib)
4882 gzFile gzfp;
4883#endif
4884 FILE *fp;
4885 struct lzmafile *lzmafp;
4886 SDDS_FILEBUFFER *fBuffer;
4887
4888 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_ReadNonNativeBinaryRow"))
4889 return (0);
4890 layout = &SDDS_dataset->layout;
4891 fBuffer = &SDDS_dataset->fBuffer;
4892
4893#if defined(zLib)
4894 if (SDDS_dataset->layout.gzipFile) {
4895 gzfp = layout->gzfp;
4896 for (i = 0; i < layout->n_columns; i++) {
4897 if (layout->column_definition[i].definition_mode & SDDS_WRITEONLY_DEFINITION)
4898 continue;
4899 if ((type = layout->column_definition[i].type) == SDDS_STRING) {
4900 if (!skip) {
4901 if (((char ***)SDDS_dataset->data)[i][row])
4902 free((((char ***)SDDS_dataset->data)[i][row]));
4903 if (!(((char ***)SDDS_dataset->data)[i][row] = SDDS_ReadNonNativeGZipBinaryString(gzfp, fBuffer, 0))) {
4904 SDDS_SetError("Unable to read rows--failure reading string (SDDS_ReadNonNativeBinaryRow)");
4905 return (0);
4906 }
4907 } else {
4908 if (!SDDS_ReadNonNativeGZipBinaryString(gzfp, fBuffer, 1)) {
4909 SDDS_SetError("Unable to read rows--failure reading string (SDDS_ReadNonNativeBinaryRow)");
4910 return 0;
4911 }
4912 }
4913 } else {
4914 size = SDDS_type_size[type - 1];
4915 if (!SDDS_GZipBufferedRead(skip ? NULL : (char *)SDDS_dataset->data[i] + row * size, size, gzfp, fBuffer, type, SDDS_dataset->layout.byteOrderDeclared)) {
4916 SDDS_SetError("Unable to read row--failure reading value (SDDS_ReadNonNativeBinaryRow)");
4917 return (0);
4918 }
4919 }
4920 }
4921 } else {
4922#endif
4923 if (SDDS_dataset->layout.lzmaFile) {
4924 lzmafp = layout->lzmafp;
4925 for (i = 0; i < layout->n_columns; i++) {
4926 if (layout->column_definition[i].definition_mode & SDDS_WRITEONLY_DEFINITION)
4927 continue;
4928 if ((type = layout->column_definition[i].type) == SDDS_STRING) {
4929 if (!skip) {
4930 if (((char ***)SDDS_dataset->data)[i][row])
4931 free((((char ***)SDDS_dataset->data)[i][row]));
4932 if (!(((char ***)SDDS_dataset->data)[i][row] = SDDS_ReadNonNativeLZMABinaryString(lzmafp, fBuffer, 0))) {
4933 SDDS_SetError("Unable to read rows--failure reading string (SDDS_ReadNonNativeBinaryRow)");
4934 return (0);
4935 }
4936 } else {
4937 if (!SDDS_ReadNonNativeLZMABinaryString(lzmafp, fBuffer, 1)) {
4938 SDDS_SetError("Unable to read rows--failure reading string (SDDS_ReadNonNativeBinaryRow)");
4939 return 0;
4940 }
4941 }
4942 } else {
4943 size = SDDS_type_size[type - 1];
4944 if (!SDDS_LZMABufferedRead(skip ? NULL : (char *)SDDS_dataset->data[i] + row * size, size, lzmafp, fBuffer, type, SDDS_dataset->layout.byteOrderDeclared)) {
4945 SDDS_SetError("Unable to read row--failure reading value (SDDS_ReadNonNativeBinaryRow)");
4946 return (0);
4947 }
4948 }
4949 }
4950 } else {
4951 fp = layout->fp;
4952 for (i = 0; i < layout->n_columns; i++) {
4953 if (layout->column_definition[i].definition_mode & SDDS_WRITEONLY_DEFINITION)
4954 continue;
4955 if ((type = layout->column_definition[i].type) == SDDS_STRING) {
4956 if (!skip) {
4957 if (((char ***)SDDS_dataset->data)[i][row])
4958 free((((char ***)SDDS_dataset->data)[i][row]));
4959 if (!(((char ***)SDDS_dataset->data)[i][row] = SDDS_ReadNonNativeBinaryString(fp, fBuffer, 0))) {
4960 SDDS_SetError("Unable to read rows--failure reading string (SDDS_ReadNonNativeBinaryRow)");
4961 return (0);
4962 }
4963 } else {
4964 if (!SDDS_ReadNonNativeBinaryString(fp, fBuffer, 1)) {
4965 SDDS_SetError("Unable to read rows--failure reading string (SDDS_ReadNonNativeBinaryRow)");
4966 return 0;
4967 }
4968 }
4969 } else {
4970 size = SDDS_type_size[type - 1];
4971 if (!SDDS_BufferedRead(skip ? NULL : (char *)SDDS_dataset->data[i] + row * size, size, fp, fBuffer, type, SDDS_dataset->layout.byteOrderDeclared)) {
4972 SDDS_SetError("Unable to read row--failure reading value (SDDS_ReadNonNativeBinaryRow)");
4973 return (0);
4974 }
4975 }
4976 }
4977 }
4978#if defined(zLib)
4979 }
4980#endif
4981 return (1);
4982}

◆ SDDS_ReadNonNativeBinaryString()

char * SDDS_ReadNonNativeBinaryString ( FILE * fp,
SDDS_FILEBUFFER * fBuffer,
int32_t skip )

Reads a non-native endian binary string from a file.

This function reads a binary string from the specified file pointer, handling non-native endianness. It first reads the length of the string, swaps its byte order if necessary, allocates memory for the string, reads the string data, and null-terminates it.

Parameters
[in]fpPointer to the FILE from which to read the string.
[in,out]fBufferPointer to the SDDS_FILEBUFFER structure used for buffered reading.
[in]skipIf non-zero, the function will skip reading the string data, useful for sparse reading.
Returns
char* Returns a pointer to the read string on success, or NULL if an error occurred.
Return values
Non-NULLPointer to the newly allocated string.
NULLAn error occurred during reading or memory allocation.
Note
The caller is responsible for freeing the returned string to prevent memory leaks.

Definition at line 5001 of file SDDS_binary.c.

5001 {
5002 int32_t length;
5003 char *string;
5004
5005 if (!SDDS_BufferedRead(&length, sizeof(length), fp, fBuffer, SDDS_LONG, 0))
5006 return (0);
5007 SDDS_SwapLong(&length);
5008 if (length < 0)
5009 return (0);
5010 if (!(string = SDDS_Malloc(sizeof(*string) * (length + 1))))
5011 return (NULL);
5012 if (length && !SDDS_BufferedRead(skip ? NULL : string, sizeof(*string) * length, fp, fBuffer, SDDS_STRING, 0))
5013 return (NULL);
5014 string[length] = 0;
5015 return (string);
5016}

◆ SDDS_ReadNonNativePage()

epicsShareFuncSDDS int32_t SDDS_ReadNonNativePage ( SDDS_DATASET * SDDS_dataset)
extern

Reads a non-native endian page from an SDDS dataset.

This function reads a page of data from the specified SDDS dataset, handling data with non-native endianness. It supports both ASCII and binary data modes, performing necessary byte order conversions to ensure correct data interpretation on the host system.

Parameters
[in,out]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset to read from.
Returns
int32_t Returns the number of rows read on success, or 0 on failure.
Return values
>0Number of rows successfully read.
0An error occurred during the read operation, such as I/O failures, data corruption, or unsupported data modes.
Note
This function is a wrapper for SDDS_ReadNonNativePageDetailed with default parameters. It should be used when no specific mode, sparse interval, or offset is required.

Definition at line 4133 of file SDDS_binary.c.

4133 {
4134 return SDDS_ReadNonNativePageDetailed(SDDS_dataset, 0, 1, 0, 0);
4135}
int32_t SDDS_ReadNonNativePageDetailed(SDDS_DATASET *SDDS_dataset, uint32_t mode, int64_t sparse_interval, int64_t sparse_offset, int64_t last_rows)
Reads a detailed non-native endian page from an SDDS dataset.

◆ SDDS_ReadNonNativePageSparse()

int32_t SDDS_ReadNonNativePageSparse ( SDDS_DATASET * SDDS_dataset,
uint32_t mode,
int64_t sparse_interval,
int64_t sparse_offset )

Reads a sparse non-native endian page from an SDDS dataset.

This function reads a sparse page of data from the specified SDDS dataset, handling data with non-native endianness. Sparse reading allows for selective row retrieval based on the provided interval and offset.

Parameters
[in,out]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset to read from.
[in]modeMode flag to support future expansion.
[in]sparse_intervalInterval between rows to be read for sparsity.
[in]sparse_offsetOffset to start reading rows for sparsity.
Returns
int32_t Returns the number of rows read on success, or 0 on failure.
Return values
>0Number of rows successfully read.
0An error occurred during the read operation, such as I/O failures, data corruption, or unsupported data modes.
Note
This function is a wrapper for SDDS_ReadNonNativePageDetailed with specific parameters to enable sparse reading. It should be used when selective row retrieval is desired.

Definition at line 4155 of file SDDS_binary.c.

4155 {
4156 return SDDS_ReadNonNativePageDetailed(SDDS_dataset, mode, sparse_interval, sparse_offset, 0);
4157}

◆ SDDS_ReadPage()

epicsShareFuncSDDS int32_t SDDS_ReadPage ( SDDS_DATASET * SDDS_dataset)
extern

Reads a page of an SDDS file. Usually called after SDDS_InitializeInput.

Parameters
SDDS_datasetAddress of the SDDS_DATASET structure for the data set.
Returns
Page number on success, -1 if it is the end-of-file, 0 on error.

Definition at line 1007 of file SDDS_input.c.

1007 {
1008#if SDDS_MPI_IO
1009 if (SDDS_dataset->parallel_io)
1010 return SDDS_MPI_ReadPage(SDDS_dataset);
1011#endif
1012 return SDDS_ReadPageSparse(SDDS_dataset, 0, 1, 0, 0);
1013}
int32_t SDDS_MPI_ReadPage(SDDS_DATASET *SDDS_dataset)
Reads a page from an SDDS dataset using MPI.

◆ SDDS_ReadPageLastRows()

epicsShareFuncSDDS int32_t SDDS_ReadPageLastRows ( SDDS_DATASET * SDDS_dataset,
int64_t last_rows )
extern

Reads the last specified number of rows from the SDDS dataset.

Parameters
SDDS_datasetThe pointer to the SDDS dataset structure.
last_rowsThe number of rows to read from the end of the dataset.
Returns
Page number on success, -1 if it is the end-of-file, 0 on error.

Definition at line 1157 of file SDDS_input.c.

1157 {
1158 int32_t retval;
1159
1160 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_ReadPageLastRows"))
1161 return (0);
1162 if (SDDS_dataset->layout.disconnected) {
1163 SDDS_SetError("Can't read page--file is disconnected (SDDS_ReadPageLastRows)");
1164 return 0;
1165 }
1166#if defined(zLib)
1167 if (SDDS_dataset->layout.gzipFile) {
1168 if (!SDDS_dataset->layout.gzfp) {
1169 SDDS_SetError("Unable to read page--NULL file pointer (SDDS_ReadPageLastRows)");
1170 return (0);
1171 }
1172 } else {
1173#endif
1174 if (SDDS_dataset->layout.lzmaFile) {
1175 if (!SDDS_dataset->layout.lzmafp) {
1176 SDDS_SetError("Unable to read page--NULL file pointer (SDDS_ReadPageLastRows)");
1177 return (0);
1178 }
1179 } else {
1180 if (!SDDS_dataset->layout.fp) {
1181 SDDS_SetError("Unable to read page--NULL file pointer (SDDS_ReadPageLastRows)");
1182 return (0);
1183 }
1184 }
1185#if defined(zLib)
1186 }
1187#endif
1188 if (SDDS_dataset->original_layout.data_mode.mode == SDDS_ASCII) {
1189 if ((retval = SDDS_ReadAsciiPageLastRows(SDDS_dataset, last_rows)) < 1) {
1190 return (retval);
1191 }
1192 } else if (SDDS_dataset->original_layout.data_mode.mode == SDDS_BINARY) {
1193 if ((retval = SDDS_ReadBinaryPageLastRows(SDDS_dataset, last_rows)) < 1) {
1194 return (retval);
1195 }
1196 } else {
1197 SDDS_SetError("Unable to read page--unrecognized data mode (SDDS_ReadPageLastRows)");
1198 return (0);
1199 }
1200 if (!SDDS_dataset->layout.gzipFile && !SDDS_dataset->layout.lzmaFile && !SDDS_dataset->layout.popenUsed && SDDS_dataset->layout.filename && SDDS_dataset->pagecount_offset) {
1201 /* Data is not:
1202 1. from a gzip file
1203 2. from a file that is being internally decompressed by a command executed with popen()
1204 3. from a pipe set up externally (e.g., -pipe=in on commandline)
1205 and pagecount_offset has been allocate memory from SDDS_initializeInput()
1206 */
1207 if (SDDS_dataset->pagecount_offset[SDDS_dataset->pages_read] < SDDS_dataset->endOfFile_offset) {
1208 SDDS_dataset->pages_read++;
1209 if (!(SDDS_dataset->pagecount_offset = realloc(SDDS_dataset->pagecount_offset, sizeof(int64_t) * (SDDS_dataset->pages_read + 1)))) {
1210 SDDS_SetError("Unable to allocate memory for pagecount_offset (SDDS_ReadPageLastRows)");
1211 exit(1);
1212 }
1213 SDDS_dataset->pagecount_offset[SDDS_dataset->pages_read] = ftell(SDDS_dataset->layout.fp);
1214 }
1215 } else {
1216 SDDS_dataset->pages_read++;
1217 }
1218 return (retval);
1219}
int32_t SDDS_ReadAsciiPageLastRows(SDDS_DATASET *SDDS_dataset, int64_t last_rows)
Reads the last specified number of rows from an ASCII page of an SDDS dataset.
int32_t SDDS_ReadBinaryPageLastRows(SDDS_DATASET *SDDS_dataset, int64_t last_rows)
Reads the last specified number of rows from a binary page of an SDDS dataset.

◆ SDDS_ReadPageSparse()

epicsShareFuncSDDS int32_t SDDS_ReadPageSparse ( SDDS_DATASET * SDDS_dataset,
uint32_t mode,
int64_t sparse_interval,
int64_t sparse_offset,
int32_t sparse_statistics )
extern

Reads a sparsed page of an SDDS file. Usually called after SDDS_InitializeInput.

Parameters
SDDS_datasetA pointer to an SDDS dataset.
modeNot used.
sparse_intervalThe column data can be sparsified over row intervals if this is greater than 1.
sparse_offsetThis is used to skip the initial rows of the column data.
sparse_statisticsNot used.
Returns
Page number on success, -1 if it is the end-of-file, 0 on error.

Definition at line 1083 of file SDDS_input.c.

1085{
1086 int32_t retval;
1087 /* SDDS_LAYOUT layout_copy; */
1088
1089 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_ReadPageSparse"))
1090 return (0);
1091 if (SDDS_dataset->layout.disconnected) {
1092 SDDS_SetError("Can't read page--file is disconnected (SDDS_ReadPageSparse)");
1093 return 0;
1094 }
1095#if defined(zLib)
1096 if (SDDS_dataset->layout.gzipFile) {
1097 if (!SDDS_dataset->layout.gzfp) {
1098 SDDS_SetError("Unable to read page--NULL file pointer (SDDS_ReadPageSparse)");
1099 return (0);
1100 }
1101 } else {
1102#endif
1103 if (SDDS_dataset->layout.lzmaFile) {
1104 if (!SDDS_dataset->layout.lzmafp) {
1105 SDDS_SetError("Unable to read page--NULL file pointer (SDDS_ReadPageSparse)");
1106 return (0);
1107 }
1108 } else {
1109 if (!SDDS_dataset->layout.fp) {
1110 SDDS_SetError("Unable to read page--NULL file pointer (SDDS_ReadPageSparse)");
1111 return (0);
1112 }
1113 }
1114#if defined(zLib)
1115 }
1116#endif
1117 if (SDDS_dataset->original_layout.data_mode.mode == SDDS_ASCII) {
1118 if ((retval = SDDS_ReadAsciiPage(SDDS_dataset, sparse_interval, sparse_offset, sparse_statistics)) < 1) {
1119 return (retval);
1120 }
1121 } else if (SDDS_dataset->original_layout.data_mode.mode == SDDS_BINARY) {
1122 if ((retval = SDDS_ReadBinaryPage(SDDS_dataset, sparse_interval, sparse_offset, sparse_statistics)) < 1) {
1123 return (retval);
1124 }
1125 } else {
1126 SDDS_SetError("Unable to read page--unrecognized data mode (SDDS_ReadPageSparse)");
1127 return (0);
1128 }
1129 if (!SDDS_dataset->layout.gzipFile && !SDDS_dataset->layout.lzmaFile && !SDDS_dataset->layout.popenUsed && SDDS_dataset->layout.filename && SDDS_dataset->pagecount_offset) {
1130 /* Data is not:
1131 1. from a gzip file
1132 2. from a file that is being internally decompressed by a command executed with popen()
1133 3. from a pipe set up externally (e.g., -pipe=in on commandline)
1134 and pagecount_offset has been allocate memory from SDDS_initializeInput()
1135 */
1136 if (SDDS_dataset->pagecount_offset[SDDS_dataset->pages_read] < SDDS_dataset->endOfFile_offset) {
1137 SDDS_dataset->pages_read++;
1138 if (!(SDDS_dataset->pagecount_offset = realloc(SDDS_dataset->pagecount_offset, sizeof(int64_t) * (SDDS_dataset->pages_read + 1)))) {
1139 SDDS_SetError("Unable to allocate memory for pagecount_offset (SDDS_ReadPageSparse)");
1140 exit(1);
1141 }
1142 SDDS_dataset->pagecount_offset[SDDS_dataset->pages_read] = ftell(SDDS_dataset->layout.fp);
1143 }
1144 } else {
1145 SDDS_dataset->pages_read++;
1146 }
1147 return (retval);
1148}
int32_t SDDS_ReadAsciiPage(SDDS_DATASET *SDDS_dataset, int64_t sparse_interval, int64_t sparse_offset, int32_t sparse_statistics)
Reads the next SDDS ASCII page into memory with optional data sparsity and statistics.
int32_t SDDS_ReadBinaryPage(SDDS_DATASET *SDDS_dataset, int64_t sparse_interval, int64_t sparse_offset, int32_t sparse_statistics)
Reads a binary page from an SDDS dataset.

◆ SDDS_ReadRecoveryPossible()

epicsShareFuncSDDS int32_t SDDS_ReadRecoveryPossible ( SDDS_DATASET * SDDS_dataset)
extern

Checks if any data in an SDDS page was recovered after an error was detected.

This function inspects the SDDS dataset to determine if any data recovery was possible following an error during data reading. It resets the recovery flag after checking.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
Returns
  • Returns 1 if recovery was possible.
  • Returns 0 if no recovery was performed or if recovery was not possible.

The function performs the following steps:

  • Retrieves the current state of the readRecoveryPossible flag from the dataset.
  • Resets the readRecoveryPossible flag to 0.
  • Returns the original state of the readRecoveryPossible flag.
Note
  • This function is typically used after attempting to recover from a read error to verify if any partial data was successfully recovered.
  • The recovery flag is automatically managed by other functions within the SDDS library.

Definition at line 2075 of file SDDS_binary.c.

2075 {
2076 int32_t returnValue;
2077
2078 returnValue = SDDS_dataset->readRecoveryPossible;
2079 SDDS_dataset->readRecoveryPossible = 0;
2080 return returnValue;
2081}

◆ SDDS_Realloc()

epicsShareFuncSDDS void * SDDS_Realloc ( void * old_ptr,
size_t new_size )
extern

Reallocates memory to a new size.

This function extends the standard realloc functionality by zero-initializing any newly allocated memory beyond the original size. It ensures that memory is consistently reallocated and initialized across different build configurations.

Parameters
[in]old_ptrPointer to the original memory block. If NULL, the function behaves like SDDS_Malloc.
[in]new_sizeNew size in bytes for the memory block.
Returns
Pointer to the reallocated memory block with the new size. If new_size is less than or equal to zero, a minimum of 4 bytes is allocated. Returns NULL if memory reallocation fails.
See also
SDDS_Malloc
SDDS_Free

Definition at line 743 of file SDDS_utils.c.

743 {
744 /* this is required because some realloc's don't behave properly when asked to return a
745 * pointer to 0 memory. They return NULL.
746 */
747 if (new_size <= 0)
748 new_size = 4;
749 /* this is required because some realloc's don't behave properly when given a NULL pointer */
750 if (!old_ptr)
751 return (SDDS_Malloc(new_size));
752 else
753 return (realloc(old_ptr, new_size));
754}

◆ SDDS_ReconnectFile()

epicsShareFuncSDDS int32_t SDDS_ReconnectFile ( SDDS_DATASET * SDDS_dataset)
extern

Reconnects the SDDS dataset to its previously associated file.

This function re-establishes the connection between the SDDS dataset and the file it was previously linked to before being disconnected. It opens the file in read/write mode, seeks to the appropriate position, and updates the dataset's internal state to reflect that it is connected.

Parameters
[in,out]SDDS_datasetPointer to the SDDS_DATASET structure to be reconnected.
Returns
  • 1 on successful reconnection.
  • 0 if an error occurred during reconnection. In this case, an error message is set internally.
Precondition
  • The dataset must have been previously disconnected using SDDS_DisconnectFile.
  • The dataset must have a valid filename set.
Note
  • Reconnection will fail if the file is not accessible or if the dataset was not properly disconnected.
Warning
  • Ensure that the file has not been modified externally in a way that could disrupt the dataset's state.

Definition at line 127 of file SDDS_output.c.

127 {
128#if SDDS_MPI_IO
129 if (SDDS_dataset->parallel_io)
130 return SDDS_MPI_ReconnectFile(SDDS_dataset);
131#endif
132 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_ReconnectFile"))
133 return 0;
134 if (!SDDS_dataset->layout.disconnected || !SDDS_dataset->layout.filename) {
135 SDDS_SetError("Can't reconnect file. Not disconnected or missing filename. (SDDS_ReconnectFile)");
136 return 0;
137 }
138 if (!(SDDS_dataset->layout.fp = fopen(SDDS_dataset->layout.filename, FOPEN_READ_AND_WRITE_MODE))) {
139 char s[1024];
140 sprintf(s, "Unable to open file %s (SDDS_ReconnectFile)", SDDS_dataset->layout.filename);
141 SDDS_SetError(s);
142 return 0;
143 }
144 if (fseek(SDDS_dataset->layout.fp, 0, 2) == -1) {
145 SDDS_SetError("Can't reconnect file. Fseek failed. (SDDS_ReconnectFile)");
146 return 0;
147 }
148 SDDS_dataset->original_layout.fp = SDDS_dataset->layout.fp;
149 SDDS_dataset->layout.disconnected = 0;
150 return 1;
151}
int32_t SDDS_MPI_ReconnectFile(SDDS_DATASET *SDDS_dataset)
Reconnects the MPI file associated with the SDDS dataset.

◆ SDDS_ReconnectInputFile()

epicsShareFuncSDDS int32_t SDDS_ReconnectInputFile ( SDDS_DATASET * SDDS_dataset,
long position )
extern

Reconnects the input file for the SDDS dataset at a specified position.

This function re-establishes the connection between the SDDS dataset and its input file, positioning the file pointer at the specified byte offset. This allows the dataset to resume reading from a specific location within the input file.

Parameters
[in,out]SDDS_datasetPointer to the SDDS_DATASET structure to reconnect.
[in]positionThe byte offset position in the input file where reconnection should occur.
Returns
  • 1 on successful reconnection.
  • 0 on failure. In this case, an internal error message is set.
Precondition
  • The dataset must have been previously disconnected using SDDS_DisconnectInputFile.
  • The dataset must have a valid filename set.
  • The specified position must be valid within the input file.
Note
  • Reconnection will fail if the input file is compressed (gzip, lzma, xz).
  • The function seeks to the specified position after opening the file.
Warning
  • Ensure that the specified position does not disrupt the dataset's data integrity.

Definition at line 230 of file SDDS_output.c.

230 {
231#if SDDS_MPI_IO
232 if (SDDS_dataset->parallel_io) {
233 SDDS_SetError("Error: MPI mode not supported yet in SDDS_ReconnectInputFile");
234 return 0;
235 }
236#endif
237 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_ReconnectInputFile"))
238 return 0;
239 if (!SDDS_dataset->layout.disconnected || !SDDS_dataset->layout.filename) {
240 SDDS_SetError("Can't reconnect file. Not disconnected or missing filename. (SDDS_ReconnectInputFile)");
241 return 0;
242 }
243 if (!(SDDS_dataset->layout.fp = fopen(SDDS_dataset->layout.filename, FOPEN_READ_MODE))) {
244 char s[1024];
245 sprintf(s, "Unable to open file %s (SDDS_ReconnectInputFile)", SDDS_dataset->layout.filename);
246 SDDS_SetError(s);
247 return 0;
248 }
249 if (fseek(SDDS_dataset->layout.fp, position, SEEK_SET) == -1) {
250 SDDS_SetError("Can't reconnect file. Fseek failed. (SDDS_ReconnectInputFile)");
251 return 0;
252 }
253 SDDS_dataset->original_layout.fp = SDDS_dataset->layout.fp;
254 SDDS_dataset->layout.disconnected = 0;
255 return 1;
256}

◆ SDDS_RegisterProgramName()

epicsShareFuncSDDS void SDDS_RegisterProgramName ( const char * name)
extern

Registers the executable program name for use in error messages.

This function stores the name of the executing program, which is included in various error and warning messages generated by the SDDS library routines.

Parameters
[in]nameThe name of the program. If NULL, the registered program name is cleared.
Note
This function should be called at the beginning of the program to provide context in error messages.
See also
SDDS_Bomb
SDDS_Warning

Definition at line 318 of file SDDS_utils.c.

318 {
319 char *newProgramName = NULL;
320
321 if (name) {
322 if (!(newProgramName = SDDS_DuplicateProgramName(name)))
323 return;
324 }
325 mdb_thread_lock(&registeredProgramNameLock);
326 free(registeredProgramName);
327 registeredProgramName = newProgramName;
328 mdb_thread_unlock(&registeredProgramNameLock);
329}

◆ SDDS_RemovePadding()

epicsShareFuncSDDS void SDDS_RemovePadding ( char * s)
extern

Removes leading and trailing whitespace from a string.

This function trims all leading and trailing whitespace characters from the input string s. It modifies the string in place, ensuring that any padding spaces are removed while preserving the internal content.

Parameters
[in,out]sPointer to the null-terminated string to be trimmed. The string will be modified in place.
Note
The function handles all standard whitespace characters as defined by the isspace function. If the string consists entirely of whitespace, the function will result in an empty string.
See also
isspace

Definition at line 2445 of file SDDS_utils.c.

2445 {
2446 char *ptr;
2447 ptr = s;
2448 while (isspace(*ptr))
2449 ptr++;
2450 if (ptr != s)
2451 strcpy(s, ptr);
2452 ptr = s + strlen(s) - 1;
2453 while (isspace(*ptr))
2454 *ptr-- = 0;
2455}

◆ SDDS_RestoreLayout()

epicsShareFuncSDDS int32_t SDDS_RestoreLayout ( SDDS_DATASET * SDDS_dataset)
extern

Restores a previously saved layout of the SDDS_DATASET.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure whose layout is to be restored.
Returns
Returns 1 on success; 0 on failure, with an error message recorded.

Definition at line 697 of file SDDS_copy.c.

697 {
698 SDDS_LAYOUT *source, *target;
699
700 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_RestoreLayout"))
701 return (0);
702
703 source = &SDDS_dataset->original_layout;
704 target = &SDDS_dataset->layout;
705
706 /* copy pointer elements of structure into new memory */
707 if (source->n_columns) {
708 if (target->column_definition == source->column_definition) {
709 SDDS_SetError("Unable to restore layout--column definition pointers are the same (SDDS_RestoreLayout)");
710 return (0);
711 }
712 if (!(target->column_definition = (COLUMN_DEFINITION *)SDDS_Realloc((void *)target->column_definition, sizeof(COLUMN_DEFINITION) * source->n_columns))) {
713 SDDS_SetError("Unable to restore layout--allocation failure (SDDS_RestoreLayout)");
714 return (0);
715 }
716 memcpy((char *)target->column_definition, (char *)source->column_definition, sizeof(COLUMN_DEFINITION) * source->n_columns);
717 }
718 if (source->n_parameters) {
719 if (target->parameter_definition == source->parameter_definition) {
720 SDDS_SetError("Unable to restore layout--parameter definition pointers are the same (SDDS_RestoreLayout)");
721 return (0);
722 }
723 if (!(target->parameter_definition = (PARAMETER_DEFINITION *)SDDS_Realloc((void *)target->parameter_definition, sizeof(PARAMETER_DEFINITION) * source->n_parameters))) {
724 SDDS_SetError("Unable to restore layout--allocation failure (SDDS_RestoreLayout)");
725 return (0);
726 }
727 memcpy((char *)target->parameter_definition, (char *)source->parameter_definition, sizeof(PARAMETER_DEFINITION) * source->n_parameters);
728 }
729 if (source->n_arrays) {
730 if (target->array_definition == source->array_definition) {
731 SDDS_SetError("Unable to restore layout--array definition pointers are the same (SDDS_RestoreLayout)");
732 return (0);
733 }
734 if (!(target->array_definition = (ARRAY_DEFINITION *)SDDS_Realloc((void *)target->array_definition, sizeof(ARRAY_DEFINITION) * source->n_arrays))) {
735 SDDS_SetError("Unable to restore layout--allocation failure (SDDS_RestoreLayout)");
736 return (0);
737 }
738 memcpy((char *)target->array_definition, (char *)source->array_definition, sizeof(ARRAY_DEFINITION) * source->n_arrays);
739 }
740 if (source->n_associates) {
741 if (target->associate_definition == source->associate_definition) {
742 SDDS_SetError("Unable to restore layout--associate definition pointers are the same (SDDS_RestoreLayout)");
743 return (0);
744 }
745 if (!(target->associate_definition = (ASSOCIATE_DEFINITION *)SDDS_Realloc((void *)target->associate_definition, sizeof(ASSOCIATE_DEFINITION) * source->n_associates))) {
746 SDDS_SetError("Unable to restore layout--allocation failure (SDDS_RestoreLayout)");
747 return (0);
748 }
749 memcpy((char *)target->associate_definition, (char *)source->associate_definition, sizeof(ASSOCIATE_DEFINITION) * source->n_associates);
750 }
751
752 target->n_columns = source->n_columns;
753 target->n_parameters = source->n_parameters;
754 target->n_associates = source->n_associates;
755 target->n_arrays = source->n_arrays;
756 target->description = source->description;
757 target->contents = source->contents;
758 target->version = source->version;
759 target->data_mode = source->data_mode;
760 target->filename = source->filename;
761 target->fp = source->fp;
762
763 return (1);
764}

◆ SDDS_SaveLayout()

epicsShareFuncSDDS int32_t SDDS_SaveLayout ( SDDS_DATASET * SDDS_dataset)
extern

Saves the current layout of the SDDS_DATASET. The layout is stored internally for future restoration if needed.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure whose layout is to be saved.
Returns
Returns 1 on success; 0 on failure, with an error message recorded.

Definition at line 615 of file SDDS_copy.c.

615 {
616 SDDS_LAYOUT *source, *target;
617
618 if (SDDS_dataset->deferSavingLayout)
619 return 1;
620
621 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_SaveLayout"))
622 return (0);
623
624 if ((source = &SDDS_dataset->layout) == (target = &SDDS_dataset->original_layout)) {
625 SDDS_SetError("\"original\" and working page layouts share memory!");
626 SDDS_PrintErrors(stderr, SDDS_EXIT_PrintErrors | SDDS_VERBOSE_PrintErrors);
627 }
628
629 /* copy pointer elements of structure into new memory */
630 if (source->n_columns) {
631 if (!(target->column_definition = (COLUMN_DEFINITION *)SDDS_Realloc((void *)target->column_definition, sizeof(COLUMN_DEFINITION) * source->n_columns)) || !(target->column_index = (SORTED_INDEX **)SDDS_Realloc((void *)target->column_index, sizeof(SORTED_INDEX *) * source->n_columns))) {
632 SDDS_SetError("Unable to save layout--allocation failure (SDDS_SaveLayout)");
633 return (0);
634 }
635 memcpy((char *)target->column_definition, (char *)source->column_definition, sizeof(COLUMN_DEFINITION) * source->n_columns);
636 memcpy((char *)target->column_index, (char *)source->column_index, sizeof(SORTED_INDEX *) * source->n_columns);
637 }
638 if (source->n_parameters) {
639 if (!(target->parameter_definition =
640 (PARAMETER_DEFINITION *)SDDS_Realloc((void *)target->parameter_definition, sizeof(PARAMETER_DEFINITION) * source->n_parameters)) ||
641 !(target->parameter_index = (SORTED_INDEX **)SDDS_Realloc((void *)target->parameter_index, sizeof(SORTED_INDEX *) * source->n_parameters))) {
642 SDDS_SetError("Unable to save layout--allocation failure (SDDS_SaveLayout)");
643 return (0);
644 }
645 memcpy((char *)target->parameter_definition, (char *)source->parameter_definition, sizeof(PARAMETER_DEFINITION) * source->n_parameters);
646 memcpy((char *)target->parameter_index, (char *)source->parameter_index, sizeof(SORTED_INDEX *) * source->n_parameters);
647 }
648 if (source->n_arrays) {
649 if (!(target->array_definition = (ARRAY_DEFINITION *)SDDS_Realloc((void *)target->array_definition, sizeof(ARRAY_DEFINITION) * source->n_arrays)) || !(target->array_index = (SORTED_INDEX **)SDDS_Realloc((void *)target->array_index, sizeof(SORTED_INDEX *) * source->n_arrays))) {
650 SDDS_SetError("Unable to save layout--allocation failure (SDDS_SaveLayout)");
651 return (0);
652 }
653 memcpy((char *)target->array_definition, (char *)source->array_definition, sizeof(ARRAY_DEFINITION) * source->n_arrays);
654 memcpy((char *)target->array_index, (char *)source->array_index, sizeof(SORTED_INDEX *) * source->n_arrays);
655 }
656 if (source->n_associates) {
657 if (!(target->associate_definition = (ASSOCIATE_DEFINITION *)SDDS_Realloc((void *)target->associate_definition, sizeof(ASSOCIATE_DEFINITION) * source->n_associates))) {
658 SDDS_SetError("Unable to save layout--allocation failure (SDDS_SaveLayout)");
659 return (0);
660 }
661 memcpy((char *)target->associate_definition, (char *)source->associate_definition, sizeof(ASSOCIATE_DEFINITION) * source->n_associates);
662 }
663
664 target->n_columns = source->n_columns;
665 target->n_parameters = source->n_parameters;
666 target->n_associates = source->n_associates;
667 target->n_arrays = source->n_arrays;
668 target->description = source->description;
669 target->contents = source->contents;
670 target->version = source->version;
671 target->data_mode = source->data_mode;
672 target->filename = source->filename;
673 target->fp = source->fp;
674 target->popenUsed = source->popenUsed;
675
676 if (SDDS_dataset->layout.n_columns) {
677 if (!(SDDS_dataset->column_track_memory = (short *)SDDS_Realloc(SDDS_dataset->column_track_memory, sizeof(short) * SDDS_dataset->layout.n_columns))) {
678 SDDS_SetError("memory allocation failure (SDDS_SaveLayout)");
679 return(0);
680 }
681 if (!SDDS_SetMemory(SDDS_dataset->column_track_memory, SDDS_dataset->layout.n_columns, SDDS_SHORT, (short)1, (short)0)) {
682 SDDS_SetError("Unable to initialize memory (SDDS_SaveLayout)");
683 return (0);
684 }
685 }
686
687 return (1);
688}

◆ SDDS_ScanData()

epicsShareFuncSDDS int32_t SDDS_ScanData ( char * string,
int32_t type,
int32_t field_length,
void * data,
int64_t index,
int32_t is_parameter )
extern

Scans a string and saves the parsed value into a data pointer according to the specified data type.

This function extracts data from a string and stores it in the provided data pointer. It handles various SDDS data types, including integers, floating-point numbers, strings, and characters. The function supports both fixed-field and variable-field formats and can process parameters and column data.

Parameters
stringPointer to the input string containing the data to be scanned.
typeThe SDDS data type to interpret the scanned data as. Valid types include:
  • SDDS_SHORT
  • SDDS_USHORT
  • SDDS_LONG
  • SDDS_ULONG
  • SDDS_LONG64
  • SDDS_ULONG64
  • SDDS_FLOAT
  • SDDS_DOUBLE
  • SDDS_LONGDOUBLE
  • SDDS_STRING
  • SDDS_CHARACTER
field_lengthField length for fixed-field formats. Set to 0 for variable-field formats. If negative, indicates left-padding should be removed.
dataVoid pointer to the data storage where the scanned value will be saved. Must be pre-allocated and appropriate for the specified data type.
indexThe index within the data array where the value should be stored.
is_parameterSet to 1 if the data is from an SDDS parameter; set to 0 for column data.
Returns
Returns 1 on success, or 0 on error. If an error occurs, an error message is set via SDDS_SetError().
Note
The function allocates a buffer internally to process the input string. It handles escape sequences for strings and characters using SDDS_InterpretEscapes(). For string data types, the function manages memory allocation for the data array elements.

Definition at line 1748 of file SDDS_ascii.c.

1748 {
1749 char *buffer = NULL;
1750 int32_t abs_field_length, length;
1751 int32_t bufferSize = 0;
1752
1753 abs_field_length = abs(field_length);
1754 if (!string) {
1755 SDDS_SetError("Unable to scan data--input string is NULL (SDDS_ScanData)");
1756 return (0);
1757 }
1758 if (!data) {
1759 SDDS_SetError("Unable to scan data--data pointer is NULL (SDDS_ScanData)");
1760 return (0);
1761 }
1762 if (!(buffer = SDDS_Malloc(sizeof(*buffer) * (bufferSize = SDDS_MAXLINE)))) {
1763 SDDS_SetError("Unable to scan data--allocation failure (SDDS_ScanData)");
1764 return (0);
1765 }
1766 if ((length = strlen(string)) < abs_field_length)
1767 length = abs_field_length;
1768 if (bufferSize <= length) {
1769 if (!(buffer = SDDS_Realloc(buffer, sizeof(*buffer) * (bufferSize = 2 * length)))) {
1770 /* I allocate 2*length in the hopes that I won't need to realloc too often if I do this */
1771 SDDS_SetError("Unable to scan data--allocation failure (SDDS_ScanData)");
1772 return (0);
1773 }
1774 }
1775 if (type != SDDS_STRING) {
1776 /* for non-string data, fill buffer with string to be scanned */
1777 if (field_length) {
1778 /* fill with fixed number of characters */
1779 if (abs_field_length > (int32_t)strlen(string)) {
1780 strcpy(buffer, string);
1781 *string = 0;
1782 } else {
1783 strncpy(buffer, string, abs_field_length);
1784 buffer[field_length] = 0;
1785 memmove(string, string + abs_field_length, strlen(string + abs_field_length) + 1);
1786 }
1787 } else if (SDDS_GetToken(string, buffer, bufferSize) < 0) {
1788 SDDS_SetError("Unable to scan data--tokenizing error (SDDS_ScanData)");
1789 return (0);
1790 }
1791 }
1792 switch (type) {
1793 case SDDS_SHORT:
1794 if (sscanf(buffer, "%hd", ((short *)data) + index) == 1) {
1795 if (buffer)
1796 free(buffer);
1797 return (1);
1798 }
1799 break;
1800 case SDDS_USHORT:
1801 if (sscanf(buffer, "%hu", ((unsigned short *)data) + index) == 1) {
1802 if (buffer)
1803 free(buffer);
1804 return (1);
1805 }
1806 break;
1807 case SDDS_LONG:
1808 if (sscanf(buffer, "%" SCNd32, ((int32_t *)data) + index) == 1) {
1809 if (buffer)
1810 free(buffer);
1811 return (1);
1812 }
1813 break;
1814 case SDDS_ULONG:
1815 if (sscanf(buffer, "%" SCNu32, ((uint32_t *)data) + index) == 1) {
1816 if (buffer)
1817 free(buffer);
1818 return (1);
1819 }
1820 break;
1821 case SDDS_LONG64:
1822 if (sscanf(buffer, "%" SCNd64, ((int64_t *)data) + index) == 1) {
1823 if (buffer)
1824 free(buffer);
1825 return (1);
1826 }
1827 break;
1828 case SDDS_ULONG64:
1829 if (sscanf(buffer, "%" SCNu64, ((uint64_t *)data) + index) == 1) {
1830 if (buffer)
1831 free(buffer);
1832 return (1);
1833 }
1834 break;
1835 case SDDS_FLOAT:
1836 if (sscanf(buffer, "%f", ((float *)data) + index) == 1) {
1837 if (buffer)
1838 free(buffer);
1839 return (1);
1840 }
1841 break;
1842 case SDDS_DOUBLE:
1843 if (sscanf(buffer, "%lf", ((double *)data) + index) == 1) {
1844 if (buffer)
1845 free(buffer);
1846 return (1);
1847 }
1848 break;
1849 case SDDS_LONGDOUBLE:
1850 if (sscanf(buffer, "%Lf", ((long double *)data) + index) == 1) {
1851 if (buffer)
1852 free(buffer);
1853 return (1);
1854 }
1855 break;
1856 case SDDS_STRING:
1857 if (is_parameter) {
1858 int32_t len;
1859 if (((char **)data)[index]) {
1860 free(((char **)data)[index]);
1861 ((char **)data)[index] = NULL;
1862 }
1863 if ((len = strlen(string)) > 0) {
1864 if (string[len - 1] == '\r')
1865 string[len - 1] = 0;
1866 }
1867 if (string[0] == '"')
1868 SDDS_GetToken(string, buffer, bufferSize);
1869 else
1870 strcpy(buffer, string);
1871 SDDS_InterpretEscapes(buffer);
1872 if (SDDS_CopyString(((char **)data) + index, buffer)) {
1873 if (buffer)
1874 free(buffer);
1875 return (1);
1876 }
1877 } else {
1878 if (field_length) {
1879 if (abs_field_length > (int32_t)strlen(string)) {
1880 strcpy(buffer, string);
1881 *string = 0;
1882 } else {
1883 strncpy(buffer, string, abs_field_length);
1884 buffer[abs_field_length] = 0;
1885 memmove(string, string + abs_field_length, strlen(string + abs_field_length) + 1);
1886 }
1887 if (field_length < 0)
1888 SDDS_RemovePadding(buffer);
1889 } else if (SDDS_GetToken(string, buffer, bufferSize) < 0)
1890 break;
1891 if (((char **)data)[index]) {
1892 free(((char **)data)[index]);
1893 ((char **)data)[index] = NULL;
1894 }
1895 SDDS_InterpretEscapes(buffer);
1896 if (SDDS_CopyString(((char **)data) + index, buffer)) {
1897 if (buffer)
1898 free(buffer);
1899 return (1);
1900 }
1901 }
1902 break;
1903 case SDDS_CHARACTER:
1904 SDDS_InterpretEscapes(buffer);
1905 *(((char *)data) + index) = buffer[0];
1906 if (buffer)
1907 free(buffer);
1908 return (1);
1909 default:
1910 SDDS_SetError("Unknown data type encountered (SDDS_ScanData)");
1911 return (0);
1912 }
1913 SDDS_SetError("Unable to scan data--scanning or allocation error (SDDS_ScanData)");
1914 return (0);
1915}
void SDDS_InterpretEscapes(char *s)
Interprets and converts escape sequences in a string.
void SDDS_RemovePadding(char *s)
Removes leading and trailing whitespace from a string.

◆ SDDS_ScanData2()

epicsShareFuncSDDS int32_t SDDS_ScanData2 ( char * string,
char ** pstring,
int32_t * strlength,
int32_t type,
int32_t field_length,
void * data,
int64_t index,
int32_t is_parameter )
extern

Scans a string and saves the parsed value into a data pointer, optimized for long strings.

This function is similar to SDDS_ScanData but optimized for very long strings. It modifies the input string by advancing the string pointer and reducing its length after each call, which can improve performance when processing large amounts of data.

Parameters
stringPointer to the input string containing the data to be scanned.
pstringPointer to the string pointer; this is updated to point to the next unread character.
strlengthPointer to the length of the string; this is updated as the string is consumed.
typeThe SDDS data type to interpret the scanned data as. Valid types include:
  • SDDS_SHORT
  • SDDS_USHORT
  • SDDS_LONG
  • SDDS_ULONG
  • SDDS_LONG64
  • SDDS_ULONG64
  • SDDS_FLOAT
  • SDDS_DOUBLE
  • SDDS_LONGDOUBLE
  • SDDS_STRING
  • SDDS_CHARACTER
field_lengthField length for fixed-field formats. Set to 0 for variable-field formats. If negative, indicates left-padding should be removed.
dataVoid pointer to the data storage where the scanned value will be saved. Must be pre-allocated and appropriate for the specified data type.
indexThe index within the data array where the value should be stored.
is_parameterSet to 1 if the data is from an SDDS parameter; set to 0 for column data.
Returns
Returns 1 on success, or 0 on error. If an error occurs, an error message is set via SDDS_SetError().
Note
This function modifies the input string by advancing the pointer and reducing the length, which can lead to the original string being altered after each call. It is more efficient for processing very long strings compared to SDDS_ScanData.

Definition at line 1953 of file SDDS_ascii.c.

1953 {
1954 char *buffer = NULL;
1955 int32_t abs_field_length, length;
1956 int32_t bufferSize = 0;
1957
1958 abs_field_length = abs(field_length);
1959 if (!string) {
1960 SDDS_SetError("Unable to scan data--input string is NULL (SDDS_ScanData2)");
1961 return (0);
1962 }
1963 if (!data) {
1964 SDDS_SetError("Unable to scan data--data pointer is NULL (SDDS_ScanData2)");
1965 return (0);
1966 }
1967 if (!(buffer = SDDS_Malloc(sizeof(*buffer) * (bufferSize = SDDS_MAXLINE)))) {
1968 SDDS_SetError("Unable to scan data--allocation failure (SDDS_ScanData2)");
1969 return (0);
1970 }
1971 length = *strlength;
1972 if (length < abs_field_length)
1973 length = abs_field_length;
1974 if (bufferSize <= length) {
1975 if (!(buffer = SDDS_Realloc(buffer, sizeof(*buffer) * (bufferSize = 2 * length)))) {
1976 /* I allocate 2*length in the hopes that I won't need to realloc too often if I do this */
1977 SDDS_SetError("Unable to scan data--allocation failure (SDDS_ScanData2)");
1978 return (0);
1979 }
1980 }
1981 if (type != SDDS_STRING) {
1982 /* for non-string data, fill buffer with string to be scanned */
1983 if (field_length) {
1984 /* fill with fixed number of characters */
1985 if (abs_field_length > *strlength) {
1986 strcpy(buffer, string);
1987 **pstring = 0;
1988 *strlength = 0;
1989 } else {
1990 strncpy(buffer, string, abs_field_length);
1991 buffer[abs_field_length] = 0;
1992 *pstring += abs_field_length;
1993 *strlength -= abs_field_length;
1994 }
1995 } else if (SDDS_GetToken2(string, pstring, strlength, buffer, bufferSize) < 0) {
1996 SDDS_SetError("Unable to scan data--tokenizing error (SDDS_ScanData2)");
1997 return (0);
1998 }
1999 }
2000 switch (type) {
2001 case SDDS_SHORT:
2002 if (sscanf(buffer, "%hd", ((short *)data) + index) == 1) {
2003 if (buffer)
2004 free(buffer);
2005 return (1);
2006 }
2007 break;
2008 case SDDS_USHORT:
2009 if (sscanf(buffer, "%hu", ((unsigned short *)data) + index) == 1) {
2010 if (buffer)
2011 free(buffer);
2012 return (1);
2013 }
2014 break;
2015 case SDDS_LONG:
2016 if (sscanf(buffer, "%" SCNd32, ((int32_t *)data) + index) == 1) {
2017 if (buffer)
2018 free(buffer);
2019 return (1);
2020 }
2021 break;
2022 case SDDS_ULONG:
2023 if (sscanf(buffer, "%" SCNu32, ((uint32_t *)data) + index) == 1) {
2024 if (buffer)
2025 free(buffer);
2026 return (1);
2027 }
2028 break;
2029 case SDDS_LONG64:
2030 if (sscanf(buffer, "%" SCNd64, ((int64_t *)data) + index) == 1) {
2031 if (buffer)
2032 free(buffer);
2033 return (1);
2034 }
2035 break;
2036 case SDDS_ULONG64:
2037 if (sscanf(buffer, "%" SCNu64, ((uint64_t *)data) + index) == 1) {
2038 if (buffer)
2039 free(buffer);
2040 return (1);
2041 }
2042 break;
2043 case SDDS_FLOAT:
2044 if (sscanf(buffer, "%f", ((float *)data) + index) == 1) {
2045 if (buffer)
2046 free(buffer);
2047 return (1);
2048 }
2049 break;
2050 case SDDS_DOUBLE:
2051 if (sscanf(buffer, "%lf", ((double *)data) + index) == 1) {
2052 if (buffer)
2053 free(buffer);
2054 return (1);
2055 }
2056 break;
2057 case SDDS_LONGDOUBLE:
2058 if (sscanf(buffer, "%Lf", ((long double *)data) + index) == 1) {
2059 if (buffer)
2060 free(buffer);
2061 return (1);
2062 }
2063 break;
2064 case SDDS_STRING:
2065 if (is_parameter) {
2066 int32_t len;
2067 if (((char **)data)[index]) {
2068 free(((char **)data)[index]);
2069 ((char **)data)[index] = NULL;
2070 }
2071 if ((len = *strlength) > 0) {
2072 if (*pstring[len - 1] == '\r') {
2073 *pstring[len - 1] = 0;
2074 *strlength -= 1;
2075 }
2076 }
2077 if (*pstring[0] == '"')
2078 SDDS_GetToken2(*pstring, pstring, strlength, buffer, bufferSize);
2079 else
2080 strcpy(buffer, string);
2081 SDDS_InterpretEscapes(buffer);
2082 if (SDDS_CopyString(((char **)data) + index, buffer)) {
2083 if (buffer)
2084 free(buffer);
2085 return (1);
2086 }
2087 } else {
2088 if (field_length) {
2089 if (abs_field_length > *strlength) {
2090 strcpy(buffer, string);
2091 **pstring = 0;
2092 *strlength = 0;
2093 } else {
2094 strncpy(buffer, string, abs_field_length);
2095 buffer[abs_field_length] = 0;
2096 *pstring += abs_field_length;
2097 *strlength -= abs_field_length;
2098 }
2099 if (field_length < 0)
2100 SDDS_RemovePadding(buffer);
2101 } else if (SDDS_GetToken2(string, pstring, strlength, buffer, bufferSize) < 0)
2102 break;
2103 if (((char **)data)[index]) {
2104 free(((char **)data)[index]);
2105 ((char **)data)[index] = NULL;
2106 }
2107 SDDS_InterpretEscapes(buffer);
2108 if (SDDS_CopyString(((char **)data) + index, buffer)) {
2109 if (buffer)
2110 free(buffer);
2111 return (1);
2112 }
2113 }
2114 break;
2115 case SDDS_CHARACTER:
2116 SDDS_InterpretEscapes(buffer);
2117 *(((char *)data) + index) = buffer[0];
2118 if (buffer)
2119 free(buffer);
2120 return 1;
2121 default:
2122 SDDS_SetError("Unknown data type encountered (SDDS_ScanData2)");
2123 return (0);
2124 }
2125 SDDS_SetError("Unable to scan data--scanning or allocation error (SDDS_ScanData2)");
2126 return (0);
2127}
int32_t SDDS_GetToken2(char *s, char **st, int32_t *strlength, char *buffer, int32_t buflen)
Extracts the next token from a string, handling quoted substrings and escape characters,...

◆ SDDS_SetArray()

epicsShareFuncSDDS int32_t SDDS_SetArray ( SDDS_DATASET * SDDS_dataset,
char * array_name,
int32_t mode,
void * data_pointer,
int32_t * dimension )
extern

Sets the values of an array variable in the SDDS dataset using specified dimensions.

This function assigns data to a specified array within the current SDDS dataset. The dimensions of the array are provided as an array of integers, allowing for the assignment of multi-dimensional arrays. The mode parameter controls how the data is interpreted and stored. This function handles both pointer arrays and contiguous data.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the data set.
array_nameThe name of the array to set within the dataset.
modeBitwise flags that determine how the array is set. Valid flags include:
  • SDDS_POINTER_ARRAY: Indicates that the array is a pointer array.
  • SDDS_CONTIGUOUS_DATA: Indicates that the data is contiguous in memory.
data_pointerPointer to the data to be assigned to the array. The data must match the type defined for the array.
dimensionPointer to an array of integers specifying the dimensions of the array. The number of dimensions should match the array definition.
Returns
Returns 1 on successful assignment of the array data. On failure, returns 0 and records an appropriate error message.
See also
SDDS_Realloc, SDDS_CopyStringArray, SDDS_SetError, SDDS_GetArrayIndex, SDDS_ZeroMemory, SDDS_AdvanceCounter

Definition at line 1284 of file SDDS_dataprep.c.

1284 {
1285 int32_t index, i, size;
1286 int32_t *counter = NULL;
1287 SDDS_LAYOUT *layout;
1288 SDDS_ARRAY *array;
1289 void *ptr;
1290
1291 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_SetArray"))
1292 return (0);
1293 if (!(mode & SDDS_POINTER_ARRAY) && !(mode & SDDS_CONTIGUOUS_DATA)) {
1294 SDDS_SetError("Unable to set array--invalid mode (SDDS_SetArray)");
1295 return (0);
1296 }
1297 if ((index = SDDS_GetArrayIndex(SDDS_dataset, array_name)) < 0) {
1298 SDDS_SetError("Unable to set array--unknown array name given (SDDS_SetArray)");
1299 return (0);
1300 }
1301
1302 if (!dimension) {
1303 SDDS_SetError("Unable to set array--dimension pointer is NULL (SDDS_SetArray)");
1304 return (0);
1305 }
1306 if (!SDDS_dataset->array) {
1307 SDDS_SetError("Unable to set array--internal array pointer is NULL (SDDS_SetArray)");
1308 return (0);
1309 }
1310
1311 layout = &SDDS_dataset->layout;
1312 array = SDDS_dataset->array + index;
1313 if (!layout->array_definition) {
1314 SDDS_SetError("Unable to set array--internal array definition pointer is NULL (SDDS_SetArray)");
1315 return (0);
1316 }
1317 array->definition = layout->array_definition + index;
1318 if (!array->dimension && !(array->dimension = (int32_t *)SDDS_Malloc(sizeof(*array->dimension) * array->definition->dimensions))) {
1319 SDDS_SetError("Unable to set array--allocation failure (SDDS_SetArray)");
1320 return (0);
1321 }
1322 array->elements = 1;
1323 for (i = 0; i < array->definition->dimensions; i++) {
1324 if ((array->dimension[i] = dimension[i]) < 0) {
1325 SDDS_SetError("Unable to set array--negative dimension specified (SDDS_SetArray)");
1326 return (0);
1327 }
1328 array->elements *= dimension[i];
1329 if (array->elements && !data_pointer) {
1330 SDDS_SetError("Unable to set array--data pointer is NULL (SDDS_SetArray)");
1331 return (0);
1332 }
1333 }
1334 if (!array->elements)
1335 return (1);
1336
1337 size = SDDS_type_size[array->definition->type - 1];
1338 if (!(array->data = SDDS_Realloc(array->data, size * array->elements))) {
1339 SDDS_SetError("Unable to set array--allocation failure (SDDS_SetArray)");
1340 return (0);
1341 }
1342
1343 /* handle 1-d arrays and contiguous data as a special case */
1344 if (array->definition->dimensions == 1 || mode & SDDS_CONTIGUOUS_DATA) {
1345 if (array->definition->type != SDDS_STRING)
1346 memcpy(array->data, data_pointer, size * array->elements);
1347 else if (!SDDS_CopyStringArray(array->data, data_pointer, array->elements)) {
1348 SDDS_SetError("Unable to set array--string copy failure (SDDS_SetArrayVararg");
1349 return (0);
1350 }
1351 return (1);
1352 }
1353
1354 if (!(counter = SDDS_Realloc(counter, sizeof(*counter) * (array->elements - 1)))) {
1355 SDDS_SetError("Unable to set array--allocation failure (SDDS_SetArray)");
1356 return (0);
1357 }
1358 SDDS_ZeroMemory(counter, sizeof(*counter) * (array->elements - 1));
1359 index = 0;
1360 do {
1361 ptr = data_pointer;
1362 for (i = 0; i < array->definition->dimensions - 1; i++)
1363 ptr = ((void **)ptr)[counter[i]];
1364 if (array->definition->type != SDDS_STRING)
1365 memcpy((char *)array->data + size * index, ptr, size * array->dimension[i]);
1366 else if (!SDDS_CopyStringArray(((char **)array->data) + index, ptr, array->dimension[i])) {
1367 SDDS_SetError("Unable to set array--string copy failure (SDDS_SetArray)");
1368 return (0);
1369 }
1370 index += array->dimension[i];
1371 } while (SDDS_AdvanceCounter(counter, array->dimension, array->definition->dimensions - 1) != -1);
1372 if (counter)
1373 free(counter);
1374 return (1);
1375}
int32_t SDDS_AdvanceCounter(int32_t *counter, int32_t *max_count, int32_t n_indices)
Advances a multi-dimensional counter based on maximum counts for each dimension.

◆ SDDS_SetArrayUnitsConversion()

epicsShareFuncSDDS int32_t SDDS_SetArrayUnitsConversion ( SDDS_DATASET * SDDS_dataset,
char * array_name,
char * new_units,
char * old_units,
double factor )
extern

Sets unit conversions for a specified array in an SDDS dataset.

This function updates the units of the specified array within the SDDS dataset and applies a conversion factor to all its elements if the dataset has already been read (i.e., pages_read > 0). The function ensures that the new units are consistent with the old units if provided.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
array_nameA null-terminated string specifying the name of the array to update.
new_unitsA null-terminated string specifying the new units to assign to the array. This parameter must not be NULL.
old_unitsA null-terminated string specifying the expected current units of the array. If NULL, the function does not verify the existing units.
factorA double representing the conversion factor to apply to each element of the array. Each element will be multiplied by this factor.
Returns
Returns 1 on successful unit conversion and update. On failure, returns 0 and sets an appropriate error message.
Return values
1Indicates that the unit conversion was successfully applied.
0Indicates that an error occurred (e.g., invalid dataset, unrecognized array name, type undefined, memory allocation failure).
Note
  • The new_units parameter must not be NULL. Passing NULL will result in an error.
  • If the dataset has not been read yet (pages_read == 0), the conversion factor is stored but not applied immediately.
  • The function handles various data types, ensuring that the conversion factor is appropriately applied based on the array's type.
See also
SDDS_SetColumnUnitsConversion, SDDS_SetParameterUnitsConversion, SDDS_GetArray

Definition at line 4676 of file SDDS_extract.c.

4676 {
4677 int32_t index, type;
4678 int64_t i;
4679 void *rawData;
4680 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_SetArrayUnitsConversion"))
4681 return(0);
4682 if (new_units == NULL) {
4683 SDDS_SetError("new_units is NULL (SDDS_SetArrayUnitsConversion)");
4684 return(0);
4685 }
4686 if ((index = SDDS_GetArrayIndex(SDDS_dataset, array_name)) < 0) {
4687 SDDS_SetError("Unable to get array--name is not recognized (SDDS_SetArrayUnitsConversion)");
4688 return(0);
4689 }
4690 if (!(type = SDDS_GetArrayType(SDDS_dataset, index))) {
4691 SDDS_SetError("Unable to get array--data type undefined (SDDS_SetArrayUnitsConversion)");
4692 return(0);
4693 }
4694 if (SDDS_dataset->layout.array_definition[index].units != NULL) {
4695 if (strcmp(new_units, SDDS_dataset->layout.array_definition[index].units) != 0) {
4696 if ((old_units != NULL) && (strcmp(old_units, SDDS_dataset->layout.array_definition[index].units) != 0)) {
4697 SDDS_SetError("Unexpected units value found (SDDS_SetArrayUnitsConversion)");
4698 return(0);
4699 }
4700 /* free(SDDS_dataset->layout.array_definition[index].units); */
4701 cp_str(&(SDDS_dataset->layout.array_definition[index].units), new_units);
4702 }
4703 } else {
4704 cp_str(&(SDDS_dataset->layout.array_definition[index].units), new_units);
4705 }
4706
4707 if (SDDS_dataset->pages_read == 0) {
4708 return(1);
4709 }
4710 rawData = SDDS_dataset->array[index].data;
4711 switch (type) {
4712 case SDDS_LONGDOUBLE:
4713 for (i = 0; i < SDDS_dataset->array[index].elements; i++) {
4714 ((long double *)rawData)[i] *= factor;
4715 }
4716 break;
4717 case SDDS_DOUBLE:
4718 for (i = 0; i < SDDS_dataset->array[index].elements; i++) {
4719 ((double *)rawData)[i] *= factor;
4720 }
4721 break;
4722 case SDDS_FLOAT:
4723 for (i = 0; i < SDDS_dataset->array[index].elements; i++) {
4724 ((float *)rawData)[i] *= factor;
4725 }
4726 break;
4727 case SDDS_LONG:
4728 for (i = 0; i < SDDS_dataset->array[index].elements; i++) {
4729 ((int32_t *)rawData)[i] *= factor;
4730 }
4731 break;
4732 case SDDS_ULONG:
4733 for (i = 0; i < SDDS_dataset->array[index].elements; i++) {
4734 ((uint32_t *)rawData)[i] *= factor;
4735 }
4736 break;
4737 case SDDS_LONG64:
4738 for (i = 0; i < SDDS_dataset->array[index].elements; i++) {
4739 ((int64_t *)rawData)[i] *= factor;
4740 }
4741 break;
4742 case SDDS_ULONG64:
4743 for (i = 0; i < SDDS_dataset->array[index].elements; i++) {
4744 ((uint64_t *)rawData)[i] *= factor;
4745 }
4746 break;
4747 case SDDS_SHORT:
4748 for (i = 0; i < SDDS_dataset->array[index].elements; i++) {
4749 ((short *)rawData)[i] *= factor;
4750 }
4751 break;
4752 case SDDS_USHORT:
4753 for (i = 0; i < SDDS_dataset->array[index].elements; i++) {
4754 ((unsigned short *)rawData)[i] *= factor;
4755 }
4756 break;
4757 }
4758 return(1);
4759}
char * cp_str(char **s, char *t)
Copies a string, allocating memory for storage.
Definition cp_str.c:28

◆ SDDS_SetArrayVararg()

epicsShareFuncSDDS int32_t SDDS_SetArrayVararg ( SDDS_DATASET * SDDS_dataset,
char * array_name,
int32_t mode,
void * data_pointer,
... )
extern

Sets the values of an array variable in the SDDS dataset using variable arguments for dimensions.

This function assigns data to a specified array within the current SDDS dataset. The dimensions of the array are provided as variable arguments, allowing for flexible assignment of multi-dimensional arrays. The mode parameter controls how the data is interpreted and stored. This function handles both pointer arrays and contiguous data.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the data set.
array_nameThe name of the array to set within the dataset.
modeBitwise flags that determine how the array is set. Valid flags include:
  • SDDS_POINTER_ARRAY: Indicates that the array is a pointer array.
  • SDDS_CONTIGUOUS_DATA: Indicates that the data is contiguous in memory.
data_pointerPointer to the data to be assigned to the array. The data must match the type defined for the array.
...Variable arguments specifying the dimensions of the array. The number of dimensions should match the array definition.
Returns
Returns 1 on successful assignment of the array data. On failure, returns 0 and records an appropriate error message.
See also
SDDS_Realloc, SDDS_CopyStringArray, SDDS_SetError, SDDS_GetArrayIndex, SDDS_ZeroMemory, SDDS_AdvanceCounter

Definition at line 1163 of file SDDS_dataprep.c.

1163 {
1164 va_list argptr;
1165 int32_t index, retval, i, size;
1166 int32_t *counter = NULL;
1167 SDDS_LAYOUT *layout;
1168 SDDS_ARRAY *array;
1169 void *ptr;
1170
1171 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_SetArrayVararg"))
1172 return (0);
1173 if (!(mode & SDDS_POINTER_ARRAY) && !(mode & SDDS_CONTIGUOUS_DATA)) {
1174 SDDS_SetError("Unable to set array--invalid mode (SDDS_SetArrayVararg)");
1175 return (0);
1176 }
1177 if ((index = SDDS_GetArrayIndex(SDDS_dataset, array_name)) < 0) {
1178 SDDS_SetError("Unable to set array--unknown array name given (SDDS_SetArrayVararg)");
1179 return (0);
1180 }
1181 if (!SDDS_dataset->array) {
1182 SDDS_SetError("Unable to set array--internal array pointer is NULL (SDDS_SetArrayVararg)");
1183 return (0);
1184 }
1185
1186 layout = &SDDS_dataset->layout;
1187 array = SDDS_dataset->array + index;
1188 if (!layout->array_definition) {
1189 SDDS_SetError("Unable to set array--internal array definition pointer is NULL (SDDS_SetArrayVararg)");
1190 return (0);
1191 }
1192 array->definition = layout->array_definition + index;
1193 if (!array->dimension && !(array->dimension = (int32_t *)SDDS_Malloc(sizeof(*array->dimension) * array->definition->dimensions))) {
1194 SDDS_SetError("Unable to set array--allocation failure (SDDS_SetArrayVararg)");
1195 return (0);
1196 }
1197
1198 va_start(argptr, data_pointer);
1199
1200 /* variable arguments are dimensions */
1201 retval = 1;
1202 index = 0;
1203 array->elements = 1;
1204 do {
1205 if ((array->dimension[index] = va_arg(argptr, int32_t)) < 0) {
1206 SDDS_SetError("Unable to set array--negative dimension given (SDDS_SetArrayVararg)");
1207 retval = 0;
1208 break;
1209 }
1210 array->elements *= array->dimension[index];
1211 } while (retval == 1 && ++index < array->definition->dimensions);
1212 va_end(argptr);
1213
1214 if (!retval)
1215 return (0);
1216 if (!array->elements)
1217 return (1);
1218 if (!data_pointer) {
1219 SDDS_SetError("Unable to set array--data pointer is NULL (SDDS_SetArrayVararg)");
1220 return (0);
1221 }
1222
1223 size = SDDS_type_size[array->definition->type - 1];
1224 if (!(array->data = SDDS_Realloc(array->data, size * array->elements))) {
1225 SDDS_SetError("Unable to set array--allocation failure (SDDS_SetArrayVararg");
1226 return (0);
1227 }
1228
1229 /* handle 1-d arrays and contiguous data as a special case */
1230 if (array->definition->dimensions == 1 || mode & SDDS_CONTIGUOUS_DATA) {
1231 if (array->definition->type != SDDS_STRING)
1232 memcpy(array->data, data_pointer, size * array->elements);
1233 else if (!SDDS_CopyStringArray(array->data, data_pointer, array->elements)) {
1234 SDDS_SetError("Unable to set array--string copy failure (SDDS_SetArrayVararg");
1235 return (0);
1236 }
1237 return (1);
1238 }
1239
1240 if (!(counter = SDDS_Realloc(counter, sizeof(*counter) * (array->elements - 1)))) {
1241 SDDS_SetError("Unable to set array--allocation failure (SDDS_SetArrayVararg");
1242 return (0);
1243 }
1244 SDDS_ZeroMemory(counter, sizeof(*counter) * (array->elements - 1));
1245 index = 0;
1246 do {
1247 ptr = data_pointer;
1248 for (i = 0; i < array->definition->dimensions - 1; i++)
1249 ptr = ((void **)ptr)[counter[i]];
1250 if (array->definition->type != SDDS_STRING)
1251 memcpy((char *)array->data + size * index, ptr, size * array->dimension[i]);
1252 else if (!SDDS_CopyStringArray(((char **)array->data) + index, ptr, array->dimension[i])) {
1253 SDDS_SetError("Unable to set array--string copy failure (SDDS_SetArrayVararg");
1254 return (0);
1255 }
1256 index += array->dimension[i];
1257 } while (SDDS_AdvanceCounter(counter, array->dimension, array->definition->dimensions - 1) != -1);
1258 if (counter)
1259 free(counter);
1260 return (1);
1261}

◆ SDDS_SetAutoCheckMode()

epicsShareFuncSDDS uint32_t SDDS_SetAutoCheckMode ( uint32_t newMode)

Sets the automatic check mode for SDDS dataset validation.

This function updates the auto-check mode, which controls the automatic validation of SDDS datasets during operations. The previous mode is returned.

Parameters
[in]newModeThe new auto-check mode to be set. It should be a bitwise combination of the following constants:
  • TABULAR_DATA_CHECKS: Enables checks for tabular data consistency.
  • (Other mode flags as defined by SDDS)
Returns
The previous auto-check mode before the update.
See also
SDDS_CheckDataset
SDDS_CheckTabularData

Definition at line 597 of file SDDS_utils.c.

597 {
598 uint32_t oldMode;
599 mdb_thread_lock(&AutoCheckModeLock);
600 oldMode = AutoCheckMode;
601 AutoCheckMode = newMode;
602 mdb_thread_unlock(&AutoCheckModeLock);
603 return oldMode;
604}

◆ SDDS_SetAutoReadRecovery()

epicsShareFuncSDDS int32_t SDDS_SetAutoReadRecovery ( SDDS_DATASET * SDDS_dataset,
uint32_t mode )
extern

Sets the auto-read recovery mode for the SDDS dataset.

Parameters
SDDS_datasetThe SDDS dataset to modify.
modeThe mode to set (SDDS_AUTOREADRECOVER or SDDS_NOAUTOREADRECOVER).
Returns
1 on success, 0 on error.

Definition at line 1787 of file SDDS_input.c.

1787 {
1788 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_SetAutoReadRecovery"))
1789 return 0;
1790 if (mode & SDDS_AUTOREADRECOVER) {
1791 SDDS_dataset->autoRecover = 1;
1792 } else if (mode & SDDS_NOAUTOREADRECOVER) {
1793 SDDS_dataset->autoRecover = 0;
1794 } else {
1795 SDDS_SetError("Invalid Auto Read Recovery mode (SDDS_SetAutoReadRecovery).");
1796 return 0;
1797 }
1798 return 1;
1799}

◆ SDDS_SetColumn()

epicsShareFuncSDDS int32_t SDDS_SetColumn ( SDDS_DATASET * SDDS_dataset,
int32_t mode,
void * data,
int64_t rows,
... )
extern

Sets the values for one data column in the current data table of an SDDS dataset.

This function assigns data to a specified column within the current data table of the given SDDS dataset. The column can be identified either by its index or by its name. The mode parameter determines how the column is identified. The function ensures that the number of rows in the new column matches the existing data table.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the data set.
modeBitwise flags that determine how the column is identified. Valid flags include:
  • SDDS_SET_BY_INDEX: Identify the column by its index.
  • SDDS_SET_BY_NAME: Identify the column by its name.
dataPointer to an array of data to be assigned to the column. The elements of the array must be of the same type as the column type.
rowsThe number of rows in the column. This should match the number of rows in the existing data table.
...Variable arguments specifying either the column index or column name, depending on the mode parameter:
  • If mode includes SDDS_SET_BY_INDEX: Provide an int32_t index.
  • If mode includes SDDS_SET_BY_NAME: Provide a char* name.
Returns
Returns 1 on successful assignment of the column data. On failure, returns 0 and records an appropriate error message.
Note
The function ensures that the number of rows in the new column matches the existing data table. If the data type of the column is SDDS_STRING, it handles memory allocation and copying of strings appropriately.
See also
SDDS_SetRowValues, SDDS_SetError, SDDS_GetColumnIndex, SDDS_CopyStringArray

Definition at line 1542 of file SDDS_dataprep.c.

1542 {
1543 va_list argptr;
1544 int32_t index;
1545 int32_t retval;
1546 SDDS_LAYOUT *layout;
1547 char *name;
1548
1549 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_SetColumn"))
1550 return (0);
1551 if (!(mode & SDDS_SET_BY_INDEX || mode & SDDS_SET_BY_NAME)) {
1552 SDDS_SetError("Unable to set column values--unknown mode (SDDS_SetColumn)");
1553 return (0);
1554 }
1555 if (rows > SDDS_dataset->n_rows_allocated) {
1556 SDDS_SetError("Unable to set column values--number of rows exceeds allocated memory (SDDS_SetColumn)");
1557 return (0);
1558 }
1559 if (!SDDS_CheckTabularData(SDDS_dataset, "SDDS_SetColumn"))
1560 return (0);
1561 if (SDDS_dataset->n_rows != 0 && SDDS_dataset->n_rows != rows) {
1562 SDDS_SetError("Number of rows in new column unequal to number in other columns (SDDS_SetColumn)");
1563 return (0);
1564 }
1565 SDDS_dataset->n_rows = rows;
1566 layout = &SDDS_dataset->layout;
1567
1568 retval = 1;
1569 va_start(argptr, rows);
1570 if (mode & SDDS_SET_BY_INDEX) {
1571 index = va_arg(argptr, int32_t);
1572 if (index < 0 || index >= layout->n_columns) {
1573 SDDS_SetError("Unable to set column values--index out of range (SDDS_SetColumn)");
1574 retval = 0;
1575 }
1576 } else {
1577 name = va_arg(argptr, char *);
1578 if ((index = SDDS_GetColumnIndex(SDDS_dataset, name)) < 0) {
1579 SDDS_SetError0("Unable to set column values--name ");
1580 SDDS_SetError0(name);
1581 SDDS_SetError(" not recognized (SDDS_SetColumn)");
1582 retval = 0;
1583 }
1584 }
1585 va_end(argptr);
1586 if (!retval)
1587 return 0;
1588
1589 if (layout->column_definition[index].type == SDDS_STRING) {
1590 if (SDDS_dataset->data[index]) {
1591 char *ptr;
1592 int64_t i;
1593 for (i = 0; i < rows; i++) {
1594 ptr = *((char **)SDDS_dataset->data[index] + i);
1595 if (ptr)
1596 free(ptr);
1597 *((char **)SDDS_dataset->data[index] + i) = NULL;
1598 }
1599 }
1600 if (!SDDS_CopyStringArray((char **)(SDDS_dataset->data[index]), (char **)data, rows)) {
1601 SDDS_SetError("Unable to set column--error copying string data (SDDS_SetColumn)");
1602 return 0;
1603 }
1604 } else
1605 memcpy(SDDS_dataset->data[index], data, rows * SDDS_type_size[layout->column_definition[index].type - 1]);
1606 return 1;
1607}
void SDDS_SetError0(char *error_text)
Internal function to record an error message in the SDDS error stack.
Definition SDDS_utils.c:437

◆ SDDS_SetColumnFlags()

epicsShareFuncSDDS int32_t SDDS_SetColumnFlags ( SDDS_DATASET * SDDS_dataset,
int32_t column_flag_value )
extern

Sets the acceptance flags for all columns in the current data table of a data set.

This function initializes the acceptance flags for each column. A non-zero flag indicates that the column is "of interest" and should be considered in subsequent operations, while a zero flag marks the column for rejection.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the data set.
column_flag_valueInteger value to assign to all column flags.
  • Non-zero value: Marks columns as accepted ("of interest").
  • Zero value: Marks columns as rejected.
Returns
  • 1 on successful update of column flags.
  • 0 on failure, with an error message recorded (e.g., memory allocation failure).
Note
This function overwrites any existing column flags with the specified column_flag_value. It also updates the column_order array accordingly.
See also
SDDS_GetColumnFlags, SDDS_AssertColumnFlags

Definition at line 218 of file SDDS_extract.c.

218 {
219 int64_t i;
220 /* int32_t j; */
221 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_SetColumnFlags"))
222 return 0;
223 if ((!SDDS_dataset->column_flag || !SDDS_dataset->column_order) && !SDDS_AllocateColumnFlags(SDDS_dataset))
224 return 0;
225 if (!SDDS_SetMemory(SDDS_dataset->column_flag, SDDS_dataset->layout.n_columns, SDDS_LONG, (int32_t)column_flag_value, (int32_t)0)) {
226 SDDS_SetError("Unable to set column flags--memory filling failed (SDDS_SetColumnFlags)");
227 return (0);
228 }
229 SDDS_dataset->n_of_interest = column_flag_value ? SDDS_dataset->layout.n_columns : 0;
230 for (i = 0; i < SDDS_dataset->layout.n_columns; i++)
231 SDDS_dataset->column_order[i] = column_flag_value ? i : -1;
232 return (1);
233}

◆ SDDS_SetColumnFromDoubles()

epicsShareFuncSDDS int32_t SDDS_SetColumnFromDoubles ( SDDS_DATASET * SDDS_dataset,
int32_t mode,
double * data,
int64_t rows,
... )
extern

Sets the values for a single data column using double-precision floating-point numbers.

This function assigns data to a specified column within the current data table of the given SDDS dataset. The column can be identified either by its index or by its name, based on the provided mode. The data provided must be in the form of double-precision floating-point numbers (double). If the target column is of a different numeric type, the function will perform the necessary type casting. For string columns, the function converts the double values to strings with appropriate formatting.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the data set.
modeBitwise flags that determine how the column is identified. Valid flags include:
  • SDDS_SET_BY_INDEX: Identify the column by its index.
  • SDDS_SET_BY_NAME: Identify the column by its name.

Mode Requirements:

  • Exactly one of SDDS_SET_BY_INDEX or SDDS_SET_BY_NAME must be set.

Syntax Based on Mode Combination:

  • SDDS_SET_BY_INDEX: int32_t SDDS_SetColumnFromDoubles(SDDS_DATASET *SDDS_dataset, int32_t mode, double *data, int64_t rows, int32_t index)
  • SDDS_SET_BY_NAME: int32_t SDDS_SetColumnFromDoubles(SDDS_DATASET *SDDS_dataset, int32_t mode, double *data, int64_t rows, char *name)
Parameters
dataPointer to an array of double-precision floating-point data to be assigned to the column. The array should contain at least rows elements.
rowsThe number of rows (elements) in the column to be set. Must not exceed the allocated memory for the dataset.
...Variable arguments specifying either the column index (int32_t) or column name (char *), depending on the mode.
Returns
Returns 1 on successful assignment of the column data. On failure, returns 0 and records an appropriate error message using SDDS_SetError.
Note
  • If the target column is of type SDDS_STRING, the function converts each double value to a string with a precision of up to 15 significant digits.
  • The function ensures that the number of rows in the new column matches the existing data table.
  • It is required to call SDDS_StartPage before setting column values.
See also
SDDS_SetColumnFromLongDoubles, SDDS_SetError, SDDS_GetColumnIndex, SDDS_CopyStringArray, SDDS_CastValue

Definition at line 1648 of file SDDS_dataprep.c.

1648 {
1649 va_list argptr;
1650 int64_t i;
1651 int32_t index, retval, type, size;
1652 SDDS_LAYOUT *layout;
1653 char *name;
1654
1655 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_SetColumnFromDoubles"))
1656 return (0);
1657 if (!(mode & SDDS_SET_BY_INDEX || mode & SDDS_SET_BY_NAME)) {
1658 SDDS_SetError("Unable to set column values--unknown mode (SDDS_SetColumnFromDoubles)");
1659 return (0);
1660 }
1661 if (rows > SDDS_dataset->n_rows_allocated) {
1662 SDDS_SetError("Unable to set column values--number of rows exceeds allocated memory (SDDS_SetColumnFromDoubles)");
1663 return (0);
1664 }
1665 if (!SDDS_CheckTabularData(SDDS_dataset, "SDDS_SetColumnFromDoubles"))
1666 return (0);
1667 if (SDDS_dataset->n_rows != 0 && SDDS_dataset->n_rows != rows) {
1668 SDDS_SetError("Number of rows in new column unequal to number in other columns (SDDS_SetColumnFromDoubles)");
1669 return (0);
1670 }
1671 SDDS_dataset->n_rows = rows;
1672 layout = &SDDS_dataset->layout;
1673
1674 retval = 1;
1675 va_start(argptr, rows);
1676 if (mode & SDDS_SET_BY_INDEX) {
1677 index = va_arg(argptr, int32_t);
1678 if (index < 0 || index >= layout->n_columns) {
1679 SDDS_SetError("Unable to set column values--index out of range (SDDS_SetColumnFromDoubles)");
1680 retval = 0;
1681 }
1682 } else {
1683 name = va_arg(argptr, char *);
1684 if ((index = SDDS_GetColumnIndex(SDDS_dataset, name)) < 0) {
1685 SDDS_SetError("Unable to set column values--name not recognized (SDDS_SetColumnFromDoubles)");
1686 retval = 0;
1687 }
1688 }
1689 va_end(argptr);
1690 if (!retval)
1691 return 0;
1692
1693 type = layout->column_definition[index].type;
1694 if (!SDDS_NUMERIC_TYPE(type)) {
1695 if (type == SDDS_STRING) {
1696 char **stringArray;
1697 if (SDDS_dataset->data[index]) {
1698 char *ptr;
1699 int64_t i;
1700 for (i = 0; i < rows; i++) {
1701 ptr = *((char **)SDDS_dataset->data[index] + i);
1702 if (ptr)
1703 free(ptr);
1704 *((char **)SDDS_dataset->data[index] + i) = NULL;
1705 }
1706 }
1707 stringArray = (char **)malloc(sizeof(char *) * rows);
1708 for (i = 0; i < rows; i++) {
1709 stringArray[i] = (char *)malloc(sizeof(char) * 40);
1710 sprintf(stringArray[i], "%.15lg", data[i]);
1711 }
1712 if (!SDDS_CopyStringArray((char **)(SDDS_dataset->data[index]), (char **)stringArray, rows)) {
1713 SDDS_SetError("Unable to set column--error copying string data (SDDS_SetColumnFromDoubles)");
1714 return 0;
1715 }
1716 for (i = 0; i < rows; i++) {
1717 free(stringArray[i]);
1718 }
1719 free(stringArray);
1720 return 1;
1721 }
1722 SDDS_SetError("Unable to set column--source type is nonnumeric (SDDS_SetColumnFromDoubles)");
1723 return 0;
1724 }
1725
1726 size = SDDS_type_size[layout->column_definition[index].type - 1];
1727
1728 if (type == SDDS_DOUBLE) {
1729 memcpy((char *)SDDS_dataset->data[index], (char *)data, rows * size);
1730 return 1;
1731 }
1732
1733 for (i = 0; i < rows; i++)
1734 if (!SDDS_CastValue(data, i, SDDS_DOUBLE, type, (char *)(SDDS_dataset->data[index]) + i * size)) {
1735 SDDS_SetError("Unable to set column--cast error (SDDS_SetColumnFromDoubles)");
1736 return 0;
1737 }
1738
1739 return 1;
1740}

◆ SDDS_SetColumnFromFloats()

epicsShareFuncSDDS int32_t SDDS_SetColumnFromFloats ( SDDS_DATASET * SDDS_dataset,
int32_t mode,
float * data,
int64_t rows,
... )
extern

Sets the values for a single data column using single-precision floating-point numbers.

This function assigns data to a specified column within the current data table of the given SDDS dataset. The column can be identified either by its index or by its name, based on the provided mode. The data provided must be in the form of single-precision floating-point numbers (float). If the target column is of a different numeric type, the function will perform the necessary type casting. For string columns, the function converts the float values to strings with appropriate formatting.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the data set.
modeBitwise flags that determine how the column is identified. Valid flags include:
  • SDDS_SET_BY_INDEX: Identify the column by its index.
  • SDDS_SET_BY_NAME: Identify the column by its name.

Mode Requirements:

  • Exactly one of SDDS_SET_BY_INDEX or SDDS_SET_BY_NAME must be set.

Syntax Based on Mode Combination:

  • SDDS_SET_BY_INDEX: int32_t SDDS_SetColumnFromFloats(SDDS_DATASET *SDDS_dataset, int32_t mode, float *data, int64_t rows, int32_t index)
  • SDDS_SET_BY_NAME: int32_t SDDS_SetColumnFromFloats(SDDS_DATASET *SDDS_dataset, int32_t mode, float *data, int64_t rows, char *name)
Parameters
dataPointer to an array of single-precision floating-point data to be assigned to the column. The array should contain at least rows elements.
rowsThe number of rows (elements) in the column to be set. Must not exceed the allocated memory for the dataset.
...Variable arguments specifying either the column index (int32_t) or column name (char *), depending on the mode.
Returns
Returns 1 on successful assignment of the column data. On failure, returns 0 and records an appropriate error message using SDDS_SetError.
Note
  • If the target column is of type SDDS_STRING, the function converts each float value to a string with a precision of up to 8 significant digits.
  • The function ensures that the number of rows in the new column matches the existing data table.
  • It is required to call SDDS_StartPage before setting column values.
See also
SDDS_SetColumnFromDoubles, SDDS_SetError, SDDS_GetColumnIndex, SDDS_CopyStringArray, SDDS_CastValue

Definition at line 1918 of file SDDS_dataprep.c.

1918 {
1919 va_list argptr;
1920 int64_t i;
1921 int32_t index, retval, type, size;
1922 SDDS_LAYOUT *layout;
1923 char *name;
1924
1925 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_SetColumnFromFloats"))
1926 return (0);
1927 if (!(mode & SDDS_SET_BY_INDEX || mode & SDDS_SET_BY_NAME)) {
1928 SDDS_SetError("Unable to set column values--unknown mode (SDDS_SetColumnFromFloats)");
1929 return (0);
1930 }
1931 if (rows > SDDS_dataset->n_rows_allocated) {
1932 SDDS_SetError("Unable to set column values--number of rows exceeds allocated memory (SDDS_SetColumnFromFloats)");
1933 return (0);
1934 }
1935 if (!SDDS_CheckTabularData(SDDS_dataset, "SDDS_SetColumnFromFloats"))
1936 return (0);
1937 if (SDDS_dataset->n_rows != 0 && SDDS_dataset->n_rows != rows) {
1938 SDDS_SetError("Number of rows in new column unequal to number in other columns (SDDS_SetColumnFromFloats)");
1939 return (0);
1940 }
1941 SDDS_dataset->n_rows = rows;
1942 layout = &SDDS_dataset->layout;
1943
1944 retval = 1;
1945 va_start(argptr, rows);
1946 if (mode & SDDS_SET_BY_INDEX) {
1947 index = va_arg(argptr, int32_t);
1948 if (index < 0 || index >= layout->n_columns) {
1949 SDDS_SetError("Unable to set column values--index out of range (SDDS_SetColumnFromFloats)");
1950 retval = 0;
1951 }
1952 } else {
1953 name = va_arg(argptr, char *);
1954 if ((index = SDDS_GetColumnIndex(SDDS_dataset, name)) < 0) {
1955 SDDS_SetError("Unable to set column values--name not recognized (SDDS_SetColumnFromFloats)");
1956 retval = 0;
1957 }
1958 }
1959 va_end(argptr);
1960 if (!retval)
1961 return 0;
1962
1963 type = layout->column_definition[index].type;
1964 if (!SDDS_NUMERIC_TYPE(type)) {
1965 if (type == SDDS_STRING) {
1966 char **stringArray;
1967 if (SDDS_dataset->data[index]) {
1968 char *ptr;
1969 int64_t i;
1970 for (i = 0; i < rows; i++) {
1971 ptr = *((char **)SDDS_dataset->data[index] + i);
1972 if (ptr)
1973 free(ptr);
1974 *((char **)SDDS_dataset->data[index] + i) = NULL;
1975 }
1976 }
1977 stringArray = (char **)malloc(sizeof(char *) * rows);
1978 for (i = 0; i < rows; i++) {
1979 stringArray[i] = (char *)malloc(sizeof(char) * 40);
1980 sprintf(stringArray[i], "%.8g", data[i]);
1981 }
1982 if (!SDDS_CopyStringArray((char **)(SDDS_dataset->data[index]), (char **)stringArray, rows)) {
1983 SDDS_SetError("Unable to set column--error copying string data (SDDS_SetColumnFromFloats)");
1984 return 0;
1985 }
1986 for (i = 0; i < rows; i++) {
1987 free(stringArray[i]);
1988 }
1989 free(stringArray);
1990 return 1;
1991 }
1992 SDDS_SetError("Unable to set column--source type is nonnumeric (SDDS_SetColumnFromFloats)");
1993 return 0;
1994 }
1995
1996 size = SDDS_type_size[layout->column_definition[index].type - 1];
1997
1998 if (type == SDDS_FLOAT) {
1999 memcpy((char *)SDDS_dataset->data[index], (char *)data, rows * size);
2000 return 1;
2001 }
2002
2003 for (i = 0; i < rows; i++)
2004 if (!SDDS_CastValue(data, i, SDDS_FLOAT, type, (char *)(SDDS_dataset->data[index]) + i * size)) {
2005 SDDS_SetError("Unable to set column--cast error (SDDS_SetColumnFromFloats)");
2006 return 0;
2007 }
2008
2009 return 1;
2010}

◆ SDDS_SetColumnFromLongs()

epicsShareFuncSDDS int32_t SDDS_SetColumnFromLongs ( SDDS_DATASET * SDDS_dataset,
int32_t mode,
int32_t * data,
int64_t rows,
... )
extern

Sets the values for a single data column using long integer numbers.

This function assigns data to a specified column within the current data table of the given SDDS dataset. The column can be identified either by its index or by its name, based on the provided mode. The data provided must be in the form of long integers (int32_t). If the target column is of a different numeric type, the function will perform the necessary type casting. For string columns, the function converts the integer values to strings with appropriate formatting.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the data set.
modeBitwise flags that determine how the column is identified. Valid flags include:
  • SDDS_SET_BY_INDEX: Identify the column by its index.
  • SDDS_SET_BY_NAME: Identify the column by its name.

Mode Requirements:

  • Exactly one of SDDS_SET_BY_INDEX or SDDS_SET_BY_NAME must be set.

Syntax Based on Mode Combination:

  • SDDS_SET_BY_INDEX: int32_t SDDS_SetColumnFromLongs(SDDS_DATASET *SDDS_dataset, int32_t mode, int32_t *data, int64_t rows, int32_t index)
  • SDDS_SET_BY_NAME: int32_t SDDS_SetColumnFromLongs(SDDS_DATASET *SDDS_dataset, int32_t mode, int32_t *data, int64_t rows, char *name)
Parameters
dataPointer to an array of long integer data to be assigned to the column. The array should contain at least rows elements.
rowsThe number of rows (elements) in the column to be set. Must not exceed the allocated memory for the dataset.
...Variable arguments specifying either the column index (int32_t) or column name (char *), depending on the mode.
Returns
Returns 1 on successful assignment of the column data. On failure, returns 0 and records an appropriate error message using SDDS_SetError.
Note
  • If the target column is of type SDDS_STRING, the function converts each long integer value to a string using the sprintf function with the appropriate format specifier.
  • The function ensures that the number of rows in the new column matches the existing data table.
  • It is required to call SDDS_StartPage before setting column values.
See also
SDDS_SetColumnFromDoubles, SDDS_SetError, SDDS_GetColumnIndex, SDDS_CopyStringArray, SDDS_CastValue

Definition at line 2051 of file SDDS_dataprep.c.

2051 {
2052 va_list argptr;
2053 int64_t i;
2054 int32_t index, retval, type, size;
2055 SDDS_LAYOUT *layout;
2056 char *name;
2057
2058 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_SetColumnFromLongs"))
2059 return (0);
2060 if (!(mode & SDDS_SET_BY_INDEX || mode & SDDS_SET_BY_NAME)) {
2061 SDDS_SetError("Unable to set column values--unknown mode (SDDS_SetColumnFromLongs)");
2062 return (0);
2063 }
2064 if (rows > SDDS_dataset->n_rows_allocated) {
2065 SDDS_SetError("Unable to set column values--number of rows exceeds allocated memory (SDDS_SetColumnFromLongs)");
2066 return (0);
2067 }
2068 if (!SDDS_CheckTabularData(SDDS_dataset, "SDDS_SetColumnFromLongs"))
2069 return (0);
2070 if (SDDS_dataset->n_rows != 0 && SDDS_dataset->n_rows != rows) {
2071 SDDS_SetError("Number of rows in new column unequal to number in other columns (SDDS_SetColumnFromLongs)");
2072 return (0);
2073 }
2074 SDDS_dataset->n_rows = rows;
2075 layout = &SDDS_dataset->layout;
2076
2077 retval = 1;
2078 va_start(argptr, rows);
2079 if (mode & SDDS_SET_BY_INDEX) {
2080 index = va_arg(argptr, int32_t);
2081 if (index < 0 || index >= layout->n_columns) {
2082 SDDS_SetError("Unable to set column values--index out of range (SDDS_SetColumnFromLongs)");
2083 retval = 0;
2084 }
2085 } else {
2086 name = va_arg(argptr, char *);
2087 if ((index = SDDS_GetColumnIndex(SDDS_dataset, name)) < 0) {
2088 SDDS_SetError("Unable to set column values--name not recognized (SDDS_SetColumnFromLongs)");
2089 retval = 0;
2090 }
2091 }
2092 va_end(argptr);
2093 if (!retval)
2094 return 0;
2095
2096 type = layout->column_definition[index].type;
2097 if (!SDDS_NUMERIC_TYPE(type)) {
2098 if (type == SDDS_STRING) {
2099 char **stringArray;
2100 if (SDDS_dataset->data[index]) {
2101 char *ptr;
2102 int64_t i;
2103 for (i = 0; i < rows; i++) {
2104 ptr = *((char **)SDDS_dataset->data[index] + i);
2105 if (ptr)
2106 free(ptr);
2107 *((char **)SDDS_dataset->data[index] + i) = NULL;
2108 }
2109 }
2110 stringArray = (char **)malloc(sizeof(char *) * rows);
2111 for (i = 0; i < rows; i++) {
2112 stringArray[i] = (char *)malloc(sizeof(char) * 40);
2113 sprintf(stringArray[i], "%" PRId32, data[i]);
2114 }
2115 if (!SDDS_CopyStringArray((char **)(SDDS_dataset->data[index]), (char **)stringArray, rows)) {
2116 SDDS_SetError("Unable to set column--error copying string data (SDDS_SetColumnFromLongs)");
2117 return 0;
2118 }
2119 for (i = 0; i < rows; i++) {
2120 free(stringArray[i]);
2121 }
2122 free(stringArray);
2123 return 1;
2124 }
2125 SDDS_SetError("Unable to set column--source type is nonnumeric (SDDS_SetColumnFromLongs)");
2126 return 0;
2127 }
2128
2129 size = SDDS_type_size[layout->column_definition[index].type - 1];
2130
2131 if (type == SDDS_LONG) {
2132 memcpy((char *)SDDS_dataset->data[index], (char *)data, rows * size);
2133 return 1;
2134 }
2135
2136 for (i = 0; i < rows; i++)
2137 if (!SDDS_CastValue(data, i, SDDS_LONG, type, (char *)(SDDS_dataset->data[index]) + i * size)) {
2138 SDDS_SetError("Unable to set column--cast error (SDDS_SetColumnFromLongs)");
2139 return 0;
2140 }
2141
2142 return 1;
2143}

◆ SDDS_SetColumnMemoryMode()

epicsShareFuncSDDS void SDDS_SetColumnMemoryMode ( SDDS_DATASET * SDDS_dataset,
uint32_t mode )
extern

Sets the column memory mode for the SDDS dataset.

Parameters
SDDS_datasetThe SDDS dataset to operate on.
modeThe column memory mode to set.

Definition at line 1371 of file SDDS_input.c.

1371 {
1372 SDDS_dataset->layout.data_mode.column_memory_mode = mode;
1373}

◆ SDDS_SetColumnsOfInterest()

epicsShareFuncSDDS int32_t SDDS_SetColumnsOfInterest ( SDDS_DATASET * SDDS_dataset,
int32_t mode,
... )
extern

Sets the acceptance flags for columns based on specified naming criteria.

This function allows modifying column acceptance flags using various methods, including specifying column names directly or using pattern matching.

Supported modes:

  • SDDS_NAME_ARRAY: Provide an array of column names to mark as "of interest".
  • SDDS_NAMES_STRING: Provide a single string containing comma-separated column names.
  • SDDS_NAME_STRINGS: Provide multiple individual column name strings, terminated by NULL.
  • SDDS_MATCH_STRING: Provide a pattern string and a logic mode to match column names.

A non-zero flag indicates that a column is "of interest", while a zero flag marks it for rejection.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the data set.
modeOperation mode determining how columns are selected. Possible values:
  • SDDS_NAME_ARRAY: c SDDS_SetColumnsOfInterest(SDDS_DATASET *SDDS_dataset, SDDS_NAME_ARRAY, int32_t n_entries, char **nameArray);
  • SDDS_NAMES_STRING: c SDDS_SetColumnsOfInterest(SDDS_DATASET *SDDS_dataset, SDDS_NAMES_STRING, char *names);
  • SDDS_NAME_STRINGS: c SDDS_SetColumnsOfInterest(SDDS_DATASET *SDDS_dataset, SDDS_NAME_STRINGS, char *name1, char *name2, ..., NULL);
  • SDDS_MATCH_STRING: c SDDS_SetColumnsOfInterest(SDDS_DATASET *SDDS_dataset, SDDS_MATCH_STRING, char *pattern, int32_t logic_mode);
...Variable arguments based on the selected mode:
  • SDDS_NAME_ARRAY:
    • int32_t n_entries: Number of column names in the array.
    • char **nameArray: Array of column name strings.
  • SDDS_NAMES_STRING:
    • char *names: Comma-separated string of column names.
  • SDDS_NAME_STRINGS:
    • char *name1, char *name2, ..., NULL: Individual column name strings terminated by NULL.
  • SDDS_MATCH_STRING:
    • char *pattern: Pattern string to match column names (supports wildcards).
    • int32_t logic_mode: Logic mode for matching (e.g., AND, OR).
Returns
  • 1 on successful update of column flags.
  • 0 on failure, with an error message recorded (e.g., invalid mode, memory issues, unrecognized column names).
Note
  • When using SDDS_MATCH_STRING, the pattern may include wildcards to match multiple column names.
  • Ensure that column names provided exist within the dataset to avoid errors.
See also
SDDS_SetColumnFlags, SDDS_AssertColumnFlags, SDDS_GetColumnFlags

Definition at line 432 of file SDDS_extract.c.

439{
440 va_list argptr;
441 int32_t i, j, index, n_names;
442 int32_t retval;
443 /* int32_t type; */
444 char **name, *string, *match_string, *ptr;
445 int32_t local_memory; /* (0,1,2) --> (none, pointer array, pointer array + strings) locally allocated */
446 char buffer[SDDS_MAXLINE];
447 int32_t logic;
448
449 name = NULL;
450 n_names = local_memory = logic = 0;
451
452 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_SetColumnsOfInterest"))
453 return (0);
454 if ((!SDDS_dataset->column_flag || !SDDS_dataset->column_order) && !SDDS_AllocateColumnFlags(SDDS_dataset))
455 return 0;
456 va_start(argptr, mode);
457 retval = -1;
458 match_string = NULL;
459 switch (mode) {
460 case SDDS_NAME_ARRAY:
461 local_memory = 0;
462 n_names = va_arg(argptr, int32_t);
463 name = va_arg(argptr, char **);
464 break;
465 case SDDS_NAMES_STRING:
466 local_memory = 2;
467 n_names = 0;
468 name = NULL;
469 ptr = va_arg(argptr, char *);
470 SDDS_CopyString(&string, ptr);
471 while ((ptr = strchr(string, ',')))
472 *ptr = ' ';
473 while (SDDS_GetToken(string, buffer, SDDS_MAXLINE) > 0) {
474 if (!(name = SDDS_Realloc(name, sizeof(*name) * (n_names + 1))) || !SDDS_CopyString(name + n_names, buffer)) {
475 SDDS_SetError("Unable to process column selection--memory allocation failure (SDDS_SetColumnsOfInterest)");
476 retval = 0;
477 break;
478 }
479 n_names++;
480 }
481 free(string);
482 break;
483 case SDDS_NAME_STRINGS:
484 local_memory = 1;
485 n_names = 0;
486 name = NULL;
487 while ((string = va_arg(argptr, char *))) {
488 if (!(name = SDDS_Realloc(name, sizeof(*name) * (n_names + 1)))) {
489 SDDS_SetError("Unable to process column selection--memory allocation failure (SDDS_SetColumnsOfInterest)");
490 retval = 0;
491 break;
492 }
493 name[n_names++] = string;
494 }
495 break;
496 case SDDS_MATCH_STRING:
497 local_memory = 0;
498 n_names = 1;
499 if (!(string = va_arg(argptr, char *))) {
500 SDDS_SetError("Unable to process column selection--invalid matching string (SDDS_SetColumnsOfInterest)");
501 retval = 0;
502 break;
503 }
504 match_string = expand_ranges(string);
505 logic = va_arg(argptr, int32_t);
506 break;
507 default:
508 SDDS_SetError("Unable to process column selection--unknown mode (SDDS_SetColumnsOfInterest)");
509 retval = 0;
510 break;
511 }
512
513 va_end(argptr);
514 if (retval != -1)
515 return (retval);
516
517 if (n_names == 0) {
518 SDDS_SetError("Unable to process column selection--no names in call (SDDS_SetColumnsOfInterest)");
519 return (0);
520 }
521 if (!SDDS_dataset->column_order) {
522 SDDS_SetError("Unable to process column selection--'column_order' array in SDDS_DATASET is NULL (SDDS_SetColumnsOfInterest)");
523 return (0);
524 }
525
526 if (mode != SDDS_MATCH_STRING) {
527 for (i = 0; i < n_names; i++) {
528 if ((index = SDDS_GetColumnIndex(SDDS_dataset, name[i])) < 0) {
529 sprintf(buffer, "Unable to process column selection--unrecognized column name %s seen (SDDS_SetColumnsOfInterest)", name[i]);
530 SDDS_SetError(buffer);
531 return (0);
532 }
533 for (j = 0; j < SDDS_dataset->n_of_interest; j++)
534 if (index == SDDS_dataset->column_order[j])
535 break;
536 if (j == SDDS_dataset->n_of_interest) {
537 SDDS_dataset->column_flag[index] = 1;
538 SDDS_dataset->column_order[j] = index;
539 SDDS_dataset->n_of_interest++;
540 }
541 }
542 } else {
543 for (i = 0; i < SDDS_dataset->layout.n_columns; i++) {
544 if (SDDS_Logic(SDDS_dataset->column_flag[i], wild_match(SDDS_dataset->layout.column_definition[i].name, match_string), logic)) {
545#if defined(DEBUG)
546 fprintf(stderr, "logic match of %s to %s\n", SDDS_dataset->layout.column_definition[i].name, match_string);
547#endif
548 for (j = 0; j < SDDS_dataset->n_of_interest; j++)
549 if (i == SDDS_dataset->column_order[j])
550 break;
551 if (j == SDDS_dataset->n_of_interest) {
552 SDDS_dataset->column_flag[i] = 1;
553 SDDS_dataset->column_order[j] = i;
554 SDDS_dataset->n_of_interest++;
555 }
556 } else {
557#if defined(DEBUG)
558 fprintf(stderr, "no logic match of %s to %s\n", SDDS_dataset->layout.column_definition[i].name, match_string);
559#endif
560 SDDS_dataset->column_flag[i] = 0;
561 for (j = 0; j < SDDS_dataset->n_of_interest; j++)
562 if (i == SDDS_dataset->column_order[j])
563 break;
564 if (j != SDDS_dataset->n_of_interest) {
565 for (j++; j < SDDS_dataset->n_of_interest; j++)
566 SDDS_dataset->column_order[j - 1] = SDDS_dataset->column_order[j];
567 }
568 }
569 }
570 free(match_string);
571 }
572
573#if defined(DEBUG)
574 for (i = 0; i < SDDS_dataset->n_of_interest; i++)
575 fprintf(stderr, "column %" PRId32 " will be %s\n", i, SDDS_dataset->layout.column_definition[SDDS_dataset->column_order[i]].name);
576#endif
577
578 if (local_memory == 2) {
579 for (i = 0; i < n_names; i++)
580 free(name[i]);
581 }
582 if (local_memory >= 1)
583 free(name);
584
585 return (1);
586}

◆ SDDS_SetColumnUnitsConversion()

epicsShareFuncSDDS int32_t SDDS_SetColumnUnitsConversion ( SDDS_DATASET * SDDS_dataset,
char * column_name,
char * new_units,
char * old_units,
double factor )
extern

Sets unit conversions for a specified column in an SDDS dataset.

This function updates the units of the specified column within the SDDS dataset and applies a conversion factor to all its elements if the dataset has already been read (i.e., pages_read > 0). The function ensures that the new units are consistent with the old units if provided.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
column_nameA null-terminated string specifying the name of the column to update.
new_unitsA null-terminated string specifying the new units to assign to the column. This parameter must not be NULL.
old_unitsA null-terminated string specifying the expected current units of the column. If NULL, the function does not verify the existing units.
factorA double representing the conversion factor to apply to each element of the column. Each element will be multiplied by this factor.
Returns
Returns 1 on successful unit conversion and update. On failure, returns 0 and sets an appropriate error message.
Return values
1Indicates that the unit conversion was successfully applied.
0Indicates that an error occurred (e.g., invalid dataset, unrecognized column name, type undefined, memory allocation failure).
Note
  • The new_units parameter must not be NULL. Passing NULL will result in an error.
  • If the dataset has not been read yet (pages_read == 0), the conversion factor is stored but not applied immediately.
  • The function handles various data types, ensuring that the conversion factor is appropriately applied based on the column's type.
See also
SDDS_SetArrayUnitsConversion, SDDS_SetParameterUnitsConversion, SDDS_GetColumn

Definition at line 4789 of file SDDS_extract.c.

4789 {
4790 int32_t index, type;
4791 int64_t i;
4792 void *rawData;
4793 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_SetColumnUnitsConversion"))
4794 return(0);
4795 if (new_units == NULL) {
4796 SDDS_SetError("new_units is NULL (SDDS_SetColumnUnitsConversion)");
4797 return(0);
4798 }
4799 if ((index = SDDS_GetColumnIndex(SDDS_dataset, column_name)) < 0) {
4800 SDDS_SetError("Unable to get column--name is not recognized (SDDS_SetColumnUnitsConversion)");
4801 return(0);
4802 }
4803 if (!(type = SDDS_GetColumnType(SDDS_dataset, index))) {
4804 SDDS_SetError("Unable to get column--data type undefined (SDDS_SetColumnUnitsConversion)");
4805 return(0);
4806 }
4807 if (SDDS_dataset->layout.column_definition[index].units != NULL) {
4808 if (strcmp(new_units, SDDS_dataset->layout.column_definition[index].units) != 0) {
4809 if ((old_units != NULL) && (strcmp(old_units, SDDS_dataset->layout.column_definition[index].units) != 0)) {
4810 SDDS_SetError("Unexpected units value found (SDDS_SetColumnUnitsConversion)");
4811 return(0);
4812 }
4813 free(SDDS_dataset->layout.column_definition[index].units);
4814 cp_str(&(SDDS_dataset->original_layout.column_definition[index].units), new_units);
4815 cp_str(&(SDDS_dataset->layout.column_definition[index].units), new_units);
4816 }
4817 } else {
4818 cp_str(&(SDDS_dataset->original_layout.column_definition[index].units), new_units);
4819 cp_str(&(SDDS_dataset->layout.column_definition[index].units), new_units);
4820 }
4821
4822 if (SDDS_dataset->pages_read == 0) {
4823 return(1);
4824 }
4825 rawData = SDDS_dataset->data[index];
4826 switch (type) {
4827 case SDDS_LONGDOUBLE:
4828 for (i = 0; i < SDDS_dataset->n_rows; i++) {
4829 ((long double *)rawData)[i] *= factor;
4830 }
4831 break;
4832 case SDDS_DOUBLE:
4833 for (i = 0; i < SDDS_dataset->n_rows; i++) {
4834 ((double *)rawData)[i] *= factor;
4835 }
4836 break;
4837 case SDDS_FLOAT:
4838 for (i = 0; i < SDDS_dataset->n_rows; i++) {
4839 ((float *)rawData)[i] *= factor;
4840 }
4841 break;
4842 case SDDS_LONG:
4843 for (i = 0; i < SDDS_dataset->n_rows; i++) {
4844 ((int32_t *)rawData)[i] *= factor;
4845 }
4846 break;
4847 case SDDS_ULONG:
4848 for (i = 0; i < SDDS_dataset->n_rows; i++) {
4849 ((uint32_t *)rawData)[i] *= factor;
4850 }
4851 break;
4852 case SDDS_LONG64:
4853 for (i = 0; i < SDDS_dataset->n_rows; i++) {
4854 ((int64_t *)rawData)[i] *= factor;
4855 }
4856 break;
4857 case SDDS_ULONG64:
4858 for (i = 0; i < SDDS_dataset->n_rows; i++) {
4859 ((uint64_t *)rawData)[i] *= factor;
4860 }
4861 break;
4862 case SDDS_SHORT:
4863 for (i = 0; i < SDDS_dataset->n_rows; i++) {
4864 ((short *)rawData)[i] *= factor;
4865 }
4866 break;
4867 case SDDS_USHORT:
4868 for (i = 0; i < SDDS_dataset->n_rows; i++) {
4869 ((unsigned short *)rawData)[i] *= factor;
4870 }
4871 break;
4872 }
4873 return(1);
4874}

◆ SDDS_SetDataMode()

epicsShareFuncSDDS int32_t SDDS_SetDataMode ( SDDS_DATASET * SDDS_dataset,
int32_t newmode )
extern

Sets the data mode (ASCII or Binary) for the SDDS dataset.

This function configures the data mode of the SDDS dataset to either ASCII or Binary. When setting to Binary mode with byte swapping (using -SDDS_BINARY), it adjusts the byte order based on the machine's endianness to ensure compatibility.

Parameters
[in]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset whose data mode is to be set.
[in]newmodeThe desired data mode. Valid values are:
  • SDDS_ASCII for ASCII mode.
  • SDDS_BINARY for Binary mode.
  • -SDDS_BINARY for Binary mode with byte swapping (for compatibility with systems like the sddsendian program).
Returns
  • 1 on successful mode change.
  • 0 if the mode is invalid, if the dataset is NULL, or if the dataset has already been written to and the mode cannot be changed.
Note
  • Changing the data mode is only permitted if no data has been written to the dataset (i.e., page_number is 0 and n_rows_written is 0).
  • When using -SDDS_BINARY, the function automatically determines the appropriate byte order based on the machine's endianness.
Warning
  • Attempting to change the data mode after writing data to the dataset will result in an error.
  • Ensure that the newmode parameter is correctly specified to prevent unintended behavior.
See also
SDDS_SetError, SDDS_IsBigEndianMachine, SDDS_BINARY, SDDS_ASCII

Definition at line 5023 of file SDDS_utils.c.

5023 {
5024 if (!SDDS_dataset) {
5025 SDDS_SetError("NULL page pointer (SDDS_SetDataMode)");
5026 return 0;
5027 }
5028 if (newmode == -SDDS_BINARY) {
5029 /* will write with bytes swapped.
5030 * provided for compatibility with sddsendian program, which writes the
5031 * data itself
5032 */
5033 SDDS_dataset->layout.byteOrderDeclared = SDDS_IsBigEndianMachine() ? SDDS_LITTLEENDIAN : SDDS_BIGENDIAN;
5034 newmode = SDDS_BINARY;
5035 }
5036 if (newmode != SDDS_ASCII && newmode != SDDS_BINARY) {
5037 SDDS_SetError("Invalid data mode (SDDS_SetDataMode)");
5038 return 0;
5039 }
5040 if (newmode == SDDS_dataset->layout.data_mode.mode)
5041 return 1;
5042 if (SDDS_dataset->page_number != 0 && (SDDS_dataset->page_number > 1 || SDDS_dataset->n_rows_written != 0)) {
5043 SDDS_SetError("Can't change the mode of a file that's been written to (SDDS_SetDataMode)");
5044 return 0;
5045 }
5046 SDDS_dataset->layout.data_mode.mode = SDDS_dataset->original_layout.data_mode.mode = newmode;
5047 return 1;
5048}

◆ SDDS_SetDefaultIOBufferSize()

epicsShareFuncSDDS int32_t SDDS_SetDefaultIOBufferSize ( int32_t newValue)
extern

Sets the default I/O buffer size used for file operations.

This function updates the global defaultIOBufferSize variable, which determines the size of the I/O buffer used for file read/write operations. The initial default is SDDS_FILEBUFFER_SIZE, which is 262144 bytes.

Parameters
newValueThe new default I/O buffer size in bytes. If newValue is negative, the function returns the current buffer size without changing it. If newValue is between 0 and 128 (inclusive), it is treated as 0, effectively disabling buffering.
Returns
The previous default I/O buffer size if newValue is greater than or equal to 0; otherwise, returns the current default buffer size without changing it.

Definition at line 82 of file SDDS_binary.c.

82 {
83 int32_t previous;
84 if (newValue < 0)
85 return SDDS_GetLockedDefaultIOBufferSize();
86 if (newValue < 128) /* arbitrary limit */
87 newValue = 0;
88 mdb_thread_lock(&defaultIOBufferSizeLock);
89 previous = defaultIOBufferSize;
90 defaultIOBufferSize = newValue;
91 mdb_thread_unlock(&defaultIOBufferSizeLock);
92 return previous;
93}

◆ SDDS_SetError()

epicsShareFuncSDDS void SDDS_SetError ( char * error_text)
extern

Records an error message in the SDDS error stack.

This function appends an error message to the internal error stack. These errors can later be retrieved and displayed using SDDS_PrintErrors.

Parameters
[in]error_textThe error message to be recorded. If NULL, a warning is printed to stderr.
See also
SDDS_PrintErrors
SDDS_ClearErrors

Definition at line 421 of file SDDS_utils.c.

421 {
422 SDDS_SetError0(error_text);
423 SDDS_SetError0("\n");
424}

◆ SDDS_SetError0()

epicsShareFuncSDDS void SDDS_SetError0 ( char * error_text)
extern

Internal function to record an error message in the SDDS error stack.

This function appends an error message to the internal error stack without adding additional formatting or line breaks. It is typically called by SDDS_SetError.

Parameters
[in]error_textThe error message to be recorded. If NULL, a warning is printed to stderr.
Note
This function is intended for internal use within the SDDS library and should not be called directly by user code.
See also
SDDS_SetError

Definition at line 437 of file SDDS_utils.c.

437 {
438 if (n_errors >= n_errors_max) {
439 if (!(error_description = SDDS_Realloc(error_description, (n_errors_max += 10) * sizeof(*error_description)))) {
440 fputs("Error trying to allocate additional error description string (SDDS_SetError)\n", stderr);
441 fprintf(stderr, "Most recent error text:\n%s\n", error_text);
442 abort();
443 }
444 }
445 if (!error_text)
446 fprintf(stderr, "warning: error text is NULL (SDDS_SetError)\n");
447 else {
448 if (!SDDS_CopyString(&error_description[n_errors], error_text)) {
449 fputs("Error trying to copy additional error description text (SDDS_SetError)\n", stderr);
450 fprintf(stderr, "Most recent error text: %s\n", error_text);
451 abort();
452 }
453 n_errors++;
454 }
455}

◆ SDDS_SetLZMACompressionLevel()

epicsShareFuncSDDS void SDDS_SetLZMACompressionLevel ( int32_t level)
extern

Definition at line 83 of file SDDS_lzma.c.

83 {
84 if (level >= 0 && level <= 9) {
85 mdb_thread_lock(&lzmaCompressionLevelLock);
86 lzmaCompressionLevel = level;
87 mdb_thread_unlock(&lzmaCompressionLevelLock);
88 }
89}

◆ SDDS_SetMemory()

epicsShareFuncSDDS int32_t SDDS_SetMemory ( void * mem,
int64_t n_elements,
int32_t data_type,
... )
extern

Initializes a memory block with a sequence of values based on a specified data type.

This function sets a block of memory to a sequence of values, starting from a specified initial value and incrementing by a defined delta. The sequence is determined by the data_type parameter, which specifies the type of each element in the memory block. The function supports various SDDS data types and handles the initialization accordingly.

Parameters
[in,out]memPointer to the memory block to be initialized.
[in]n_elementsThe number of elements to initialize in the memory block.
[in]data_typeThe SDDS data type of each element. Must be one of the following constants:
  • SDDS_SHORT
  • SDDS_USHORT
  • SDDS_LONG
  • SDDS_ULONG
  • SDDS_LONG64
  • SDDS_ULONG64
  • SDDS_FLOAT
  • SDDS_DOUBLE
  • SDDS_LONGDOUBLE
  • SDDS_CHARACTER
[in]...Variable arguments specifying the starting value and increment value. The types of these arguments depend on the data_type:
  • For integer types (SDDS_SHORT, SDDS_USHORT, SDDS_LONG, SDDS_ULONG, SDDS_LONG64, SDDS_ULONG64):
    • First argument: initial value (int, unsigned int, int32_t, uint32_t, int64_t, uint64_t)
    • Second argument: increment value (int, unsigned int, int32_t, uint32_t, int64_t, uint64_t)
  • For floating-point types (SDDS_FLOAT, SDDS_DOUBLE, SDDS_LONGDOUBLE):
    • First argument: initial value (double for float and double, long double for SDDS_LONGDOUBLE)
    • Second argument: increment value (double for float and double, long double for SDDS_LONGDOUBLE)
  • For SDDS_CHARACTER:
    • First argument: initial value (char)
    • Second argument: increment value (short)
Returns
Returns 1 on successful memory initialization. Returns 0 if an unknown or invalid data_type is provided.
Note
The function uses variable arguments to accept the starting and increment values. The caller must ensure that the correct types are provided based on the data_type parameter.
See also
SDDS_Malloc
SDDS_Free

Definition at line 2105 of file SDDS_utils.c.

2107{
2108 va_list argptr;
2109 int32_t retval;
2110 int64_t i;
2111 short short_val, short_dval, *short_ptr;
2112 unsigned short ushort_val, ushort_dval, *ushort_ptr;
2113 int32_t long_val, long_dval, *long_ptr;
2114 uint32_t ulong_val, ulong_dval, *ulong_ptr;
2115 int64_t long64_val, long64_dval, *long64_ptr;
2116 uint64_t ulong64_val, ulong64_dval, *ulong64_ptr;
2117 float float_val, float_dval, *float_ptr;
2118 double double_val, double_dval, *double_ptr;
2119 long double longdouble_val, longdouble_dval, *longdouble_ptr;
2120 char char_val, *char_ptr;
2121
2122 retval = 1;
2123 va_start(argptr, data_type);
2124 switch (data_type) {
2125 case SDDS_SHORT:
2126 short_val = (short)va_arg(argptr, int);
2127 short_dval = (short)va_arg(argptr, int);
2128 short_ptr = (short *)mem;
2129 for (i = 0; i < n_elements; i++, short_val += short_dval)
2130 *short_ptr++ = short_val;
2131 break;
2132 case SDDS_USHORT:
2133 ushort_val = (unsigned short)va_arg(argptr, int);
2134 ushort_dval = (unsigned short)va_arg(argptr, int);
2135 ushort_ptr = (unsigned short *)mem;
2136 for (i = 0; i < n_elements; i++, ushort_val += ushort_dval)
2137 *ushort_ptr++ = ushort_val;
2138 break;
2139 case SDDS_LONG:
2140 long_val = (int32_t)va_arg(argptr, int32_t);
2141 long_dval = (int32_t)va_arg(argptr, int32_t);
2142 long_ptr = (int32_t *)mem;
2143 for (i = 0; i < n_elements; i++, long_val += long_dval)
2144 *long_ptr++ = long_val;
2145 break;
2146 case SDDS_ULONG:
2147 ulong_val = (uint32_t)va_arg(argptr, uint32_t);
2148 ulong_dval = (uint32_t)va_arg(argptr, uint32_t);
2149 ulong_ptr = (uint32_t *)mem;
2150 for (i = 0; i < n_elements; i++, ulong_val += ulong_dval)
2151 *ulong_ptr++ = ulong_val;
2152 break;
2153 case SDDS_LONG64:
2154 long64_val = (int64_t)va_arg(argptr, int64_t);
2155 long64_dval = (int64_t)va_arg(argptr, int64_t);
2156 long64_ptr = (int64_t *)mem;
2157 for (i = 0; i < n_elements; i++, long64_val += long64_dval)
2158 *long64_ptr++ = long64_val;
2159 break;
2160 case SDDS_ULONG64:
2161 ulong64_val = (uint64_t)va_arg(argptr, uint32_t);
2162 ulong64_dval = (uint64_t)va_arg(argptr, uint32_t);
2163 ulong64_ptr = (uint64_t *)mem;
2164 for (i = 0; i < n_elements; i++, ulong64_val += ulong64_dval)
2165 *ulong64_ptr++ = ulong64_val;
2166 break;
2167 case SDDS_FLOAT:
2168 float_val = (float)va_arg(argptr, double);
2169 float_dval = (float)va_arg(argptr, double);
2170 float_ptr = (float *)mem;
2171 for (i = 0; i < n_elements; i++, float_val += float_dval)
2172 *float_ptr++ = float_val;
2173 break;
2174 case SDDS_DOUBLE:
2175 double_val = (double)va_arg(argptr, double);
2176 double_dval = (double)va_arg(argptr, double);
2177 double_ptr = (double *)mem;
2178 for (i = 0; i < n_elements; i++, double_val += double_dval)
2179 *double_ptr++ = double_val;
2180 break;
2181 case SDDS_LONGDOUBLE:
2182 longdouble_val = (long double)va_arg(argptr, long double);
2183 longdouble_dval = (long double)va_arg(argptr, long double);
2184 longdouble_ptr = (long double *)mem;
2185 for (i = 0; i < n_elements; i++, longdouble_val += longdouble_dval)
2186 *longdouble_ptr++ = longdouble_val;
2187 break;
2188 case SDDS_CHARACTER:
2189 char_val = (char)va_arg(argptr, int);
2190 short_dval = (short)va_arg(argptr, int);
2191 char_ptr = (char *)mem;
2192 for (i = 0; i < n_elements; i++, char_val += short_dval)
2193 *char_ptr++ = char_val;
2194 break;
2195 default:
2196 SDDS_SetError("Unable to set memory--unknown or invalid data type (SDDS_SetMemory)");
2197 retval = 0;
2198 break;
2199 }
2200 va_end(argptr);
2201 return (retval);
2202}

◆ SDDS_SetNameValidityFlags()

epicsShareFuncSDDS int32_t SDDS_SetNameValidityFlags ( uint32_t flags)
extern

Sets the validity flags for parameter and column names in the SDDS dataset.

This function allows the user to configure the rules for validating names of parameters and columns within the SDDS dataset. The validity flags determine the set of allowed characters and naming conventions.

Parameters
[in]flagsA bitmask representing the desired name validity flags. Possible flags include:
  • SDDS_ALLOW_ANY_NAME: Allows any name without restrictions.
  • SDDS_ALLOW_V15_NAME: Enables compatibility with SDDS version 1.5 naming conventions.
  • Additional flags as defined in the SDDS library.
Returns
  • The previous name validity flags before the update.
Precondition
  • The function can be called at any time before defining parameters or columns to influence name validation.
Postcondition
  • The name validity flags are updated to reflect the specified rules.
Note
  • Changing name validity flags affects how subsequent parameter and column names are validated.
  • It is recommended to set the desired validity flags before defining any dataset elements to avoid validation errors.
Warning
  • Improperly setting validity flags may lead to unintended acceptance or rejection of valid or invalid names.
  • Ensure that the flags are set according to the desired naming conventions for your dataset.

Definition at line 2060 of file SDDS_output.c.

2060 {
2061 uint32_t oldFlags;
2062 mdb_thread_lock(&nameValidityFlagsLock);
2063 oldFlags = nameValidityFlags;
2064 nameValidityFlags = flags;
2065 mdb_thread_unlock(&nameValidityFlagsLock);
2066 return oldFlags;
2067}

◆ SDDS_SetNoRowCounts()

epicsShareFuncSDDS int32_t SDDS_SetNoRowCounts ( SDDS_DATASET * SDDS_dataset,
int32_t value )
extern

Sets the flag to enable or disable row counts in the SDDS dataset.

This function configures the SDDS dataset to either include or exclude row counts in the output. Row counts provide metadata about the number of rows written, which can be useful for data integrity and validation. Disabling row counts can improve performance when such metadata is unnecessary.

Parameters
[in,out]SDDS_datasetPointer to the SDDS_DATASET structure to be configured.
[in]valueThe flag value to set:
  • 0: Enable row counts (default behavior).
  • Non-zero: Disable row counts.
Returns
  • 1 on successful configuration.
  • 0 if an error occurred (e.g., attempting to change the flag after the layout has been written).
Precondition
  • The SDDS_dataset must be initialized and not have written the layout yet.
Postcondition
  • The dataset's configuration reflects the specified row count setting.
Note
  • Changing the row count setting affects how data rows are managed and stored in the output file.
Warning
  • This function cannot be called after the dataset layout has been written to the file or if the dataset is in read mode.
  • Disabling row counts may complicate data validation and integrity checks.

Definition at line 854 of file SDDS_output.c.

854 {
855 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_SetNoRowCounts"))
856 return 0;
857 if (SDDS_dataset->layout.layout_written) {
858 SDDS_SetError("Can't change no_row_counts after writing the layout, or for a file you are reading.");
859 return 0;
860 }
861 SDDS_dataset->layout.data_mode.no_row_counts = value ? 1 : 0;
862 return 1;
863}

◆ SDDS_SetParameter()

epicsShareFuncSDDS int32_t SDDS_SetParameter ( SDDS_DATASET * SDDS_dataset,
int32_t mode,
... )
extern

Sets the value of a single parameter in the current data table of an SDDS dataset.

This function assigns a value to a specified parameter in the current data table of the given SDDS dataset. It must be preceded by a call to SDDS_StartPage to initialize the table. The parameter to be set can be identified either by its index or by its name. The value can be passed either by value or by reference, depending on the specified mode.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the data set.
modeA bitwise combination of the following constants:
  • SDDS_SET_BY_INDEX: Identify the parameter by its index.
  • SDDS_SET_BY_NAME: Identify the parameter by its name.
  • SDDS_PASS_BY_VALUE: Pass the parameter value by value.
  • SDDS_PASS_BY_REFERENCE: Pass the parameter value by reference.

Mode Requirements:

  • Exactly one of SDDS_SET_BY_INDEX or SDDS_SET_BY_NAME must be set.
  • Exactly one of SDDS_PASS_BY_VALUE or SDDS_PASS_BY_REFERENCE must be set.

Syntax Based on Mode Combination:

  • SDDS_SET_BY_INDEX + SDDS_PASS_BY_VALUE: int32_t SDDS_SetParameter(SDDS_DATASET *SDDS_dataset, int32_t mode, int32_t index, value)
  • SDDS_SET_BY_INDEX + SDDS_PASS_BY_REFERENCE: int32_t SDDS_SetParameter(SDDS_DATASET *SDDS_dataset, int32_t mode, int32_t index, void *data)
  • SDDS_SET_BY_NAME + SDDS_PASS_BY_VALUE: int32_t SDDS_SetParameter(SDDS_DATASET *SDDS_dataset, int32_t mode, char *name, value)
  • SDDS_SET_BY_NAME + SDDS_PASS_BY_REFERENCE: int32_t SDDS_SetParameter(SDDS_DATASET *SDDS_dataset, int32_t mode, char *name, void *data)

Note: For parameters of type SDDS_STRING, passing by value means passing a char *, whereas passing by reference means passing a char **.

Returns
Returns 1 on successful assignment of the parameter value. On failure, returns 0 and records an appropriate error message.
See also
SDDS_StartPage, SDDS_SetError, SDDS_GetParameterIndex, SDDS_CopyString

Definition at line 539 of file SDDS_dataprep.c.

539 {
540 va_list argptr;
541 int32_t index;
542 SDDS_LAYOUT *layout;
543 char *name;
544 char s[SDDS_MAXLINE];
545
546 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_SetParameters"))
547 return (0);
548 if (!(mode & SDDS_SET_BY_INDEX || mode & SDDS_SET_BY_NAME) || !(mode & SDDS_PASS_BY_VALUE || mode & SDDS_PASS_BY_REFERENCE)) {
549 SDDS_SetError("Unable to set parameter values--unknown mode (SDDS_SetParameters)");
550 return (0);
551 }
552
553 va_start(argptr, mode);
554 layout = &SDDS_dataset->layout;
555
556 /* variable arguments are pairs of (index, value), where index is a int32_t integer */
557 if (mode & SDDS_SET_BY_INDEX) {
558 if ((index = va_arg(argptr, int32_t)) == -1) {
559 SDDS_SetError("Unable to set parameter values--index is null (SDDS_SetParameter)");
560 va_end(argptr);
561 return (0);
562 }
563 if (index < 0 || index >= layout->n_parameters) {
564 SDDS_SetError("Unable to set parameter values--index out of range (SDDS_SetParameter)");
565 va_end(argptr);
566 return (0);
567 }
568 } else {
569 if ((name = va_arg(argptr, char *)) == NULL) {
570 SDDS_SetError("Unable to set parameter values--name is null (SDDS_SetParameter)");
571 va_end(argptr);
572 return (0);
573 }
574 if ((index = SDDS_GetParameterIndex(SDDS_dataset, name)) < 0) {
575 sprintf(s, "Unable to set parameter values--name %s not recognized (SDDS_SetParameter)", name);
576 SDDS_SetError(s);
577 va_end(argptr);
578 return (0);
579 }
580 }
581 switch (layout->parameter_definition[index].type) {
582 case SDDS_SHORT:
583 if (mode & SDDS_PASS_BY_VALUE)
584 *((short *)SDDS_dataset->parameter[index]) = (short)va_arg(argptr, int);
585 else
586 *((short *)SDDS_dataset->parameter[index]) = *(va_arg(argptr, short *));
587 break;
588 case SDDS_USHORT:
589 if (mode & SDDS_PASS_BY_VALUE)
590 *((unsigned short *)SDDS_dataset->parameter[index]) = (unsigned short)va_arg(argptr, unsigned int);
591 else
592 *((unsigned short *)SDDS_dataset->parameter[index]) = *(va_arg(argptr, unsigned short *));
593 break;
594 case SDDS_LONG:
595 if (mode & SDDS_PASS_BY_VALUE)
596 *((int32_t *)SDDS_dataset->parameter[index]) = (int32_t)va_arg(argptr, int32_t);
597 else
598 *((int32_t *)SDDS_dataset->parameter[index]) = *(va_arg(argptr, int32_t *));
599 break;
600 case SDDS_ULONG:
601 if (mode & SDDS_PASS_BY_VALUE)
602 *((uint32_t *)SDDS_dataset->parameter[index]) = (uint32_t)va_arg(argptr, uint32_t);
603 else
604 *((uint32_t *)SDDS_dataset->parameter[index]) = *(va_arg(argptr, uint32_t *));
605 break;
606 case SDDS_LONG64:
607 if (mode & SDDS_PASS_BY_VALUE)
608 *((int64_t *)SDDS_dataset->parameter[index]) = (int64_t)va_arg(argptr, int64_t);
609 else
610 *((int64_t *)SDDS_dataset->parameter[index]) = *(va_arg(argptr, int64_t *));
611 break;
612 case SDDS_ULONG64:
613 if (mode & SDDS_PASS_BY_VALUE)
614 *((uint64_t *)SDDS_dataset->parameter[index]) = (uint64_t)va_arg(argptr, uint64_t);
615 else
616 *((uint64_t *)SDDS_dataset->parameter[index]) = *(va_arg(argptr, uint64_t *));
617 break;
618 case SDDS_FLOAT:
619 if (mode & SDDS_PASS_BY_VALUE)
620 *((float *)SDDS_dataset->parameter[index]) = (float)va_arg(argptr, double);
621 else
622 *((float *)SDDS_dataset->parameter[index]) = *(va_arg(argptr, float *));
623 break;
624 case SDDS_DOUBLE:
625 if (mode & SDDS_PASS_BY_VALUE)
626 *((double *)SDDS_dataset->parameter[index]) = va_arg(argptr, double);
627 else
628 *((double *)SDDS_dataset->parameter[index]) = *(va_arg(argptr, double *));
629 break;
630 case SDDS_LONGDOUBLE:
631 if (mode & SDDS_PASS_BY_VALUE)
632 *((long double *)SDDS_dataset->parameter[index]) = va_arg(argptr, long double);
633 else
634 *((long double *)SDDS_dataset->parameter[index]) = *(va_arg(argptr, long double *));
635 break;
636 case SDDS_STRING:
637 if (*(char **)SDDS_dataset->parameter[index])
638 free(*(char **)SDDS_dataset->parameter[index]);
639 if (mode & SDDS_PASS_BY_VALUE) {
640 if (!SDDS_CopyString((char **)SDDS_dataset->parameter[index], va_arg(argptr, char *))) {
641 SDDS_SetError("Unable to set string parameter value--allocation failure (SDDS_SetParameters)");
642 va_end(argptr);
643 return (0);
644 }
645 } else {
646 if (!SDDS_CopyString((char **)SDDS_dataset->parameter[index], *(va_arg(argptr, char **)))) {
647 SDDS_SetError("Unable to set string parameter value--allocation failure (SDDS_SetParameters)");
648 va_end(argptr);
649 return (0);
650 }
651 }
652 break;
653 case SDDS_CHARACTER:
654 if (mode & SDDS_PASS_BY_VALUE)
655 *((char *)SDDS_dataset->parameter[index]) = (char)va_arg(argptr, int);
656 else
657 *((char *)SDDS_dataset->parameter[index]) = *(va_arg(argptr, char *));
658 break;
659 default:
660 SDDS_SetError("Unknown data type encountered (SDDS_SetParameters)");
661 va_end(argptr);
662 return (0);
663 }
664 va_end(argptr);
665 return (1);
666}

◆ SDDS_SetParameters()

epicsShareFuncSDDS int32_t SDDS_SetParameters ( SDDS_DATASET * SDDS_dataset,
int32_t mode,
... )
extern

Sets the values of one or more parameters for the current data table in an SDDS dataset.

This function assigns values to parameters in the current data table of the specified SDDS dataset. It must be preceded by a call to SDDS_StartPage to initialize the table. The function can be called multiple times to set parameters for different tables, but SDDS_WriteTable should be used to write each table to disk.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the data set.
modeA bitwise combination of the following constants:
  • SDDS_SET_BY_INDEX: Specify parameters by their index.
  • SDDS_SET_BY_NAME: Specify parameters by their name.
  • SDDS_PASS_BY_VALUE: Pass parameter values by value.
  • SDDS_PASS_BY_REFERENCE: Pass parameter values by reference.

Exactly one of SDDS_SET_BY_INDEX or SDDS_SET_BY_NAME must be set to indicate how parameters are identified. Additionally, exactly one of SDDS_PASS_BY_VALUE or SDDS_PASS_BY_REFERENCE must be set to indicate how parameter values are provided.

The syntax for the four possible mode combinations is as follows:

  • SDDS_SET_BY_INDEX + SDDS_PASS_BY_VALUE: int32_t SDDS_SetParameters(SDDS_DATASET *SDDS_dataset, int32_t mode, int32_t index1, value1, int32_t index2, value2, ..., -1)
  • SDDS_SET_BY_INDEX + SDDS_PASS_BY_REFERENCE: int32_t SDDS_SetParameters(SDDS_DATASET *SDDS_dataset, int32_t mode, int32_t index1, void *data1, int32_t index2, void *data2, ..., -1)
  • SDDS_SET_BY_NAME + SDDS_PASS_BY_VALUE: int32_t SDDS_SetParameters(SDDS_DATASET *SDDS_dataset, int32_t mode, char *name1, value1, char *name2, value2, ..., NULL)
  • SDDS_SET_BY_NAME + SDDS_PASS_BY_REFERENCE: int32_t SDDS_SetParameters(SDDS_DATASET *SDDS_dataset, int32_t mode, char *name1, void *data1, char *name2, void *data2, ..., NULL)

Note: For parameters of type SDDS_STRING, passing by value means passing a char *, whereas passing by reference means passing a char **.

Returns
Returns 1 on success. On failure, returns 0 and records an error message.
See also
SDDS_StartPage, SDDS_WriteTable, SDDS_SetError, SDDS_GetParameterIndex, va_start, va_arg, va_end

Definition at line 375 of file SDDS_dataprep.c.

375 {
376 va_list argptr;
377 int32_t index, retval;
378 SDDS_LAYOUT *layout;
379 char *name;
380 char s[SDDS_MAXLINE];
381
382 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_SetParameters"))
383 return (0);
384 if (!(mode & SDDS_SET_BY_INDEX || mode & SDDS_SET_BY_NAME) || !(mode & SDDS_PASS_BY_VALUE || mode & SDDS_PASS_BY_REFERENCE)) {
385 SDDS_SetError("Unable to set parameter values--unknown mode (SDDS_SetParameters)");
386 return (0);
387 }
388
389 va_start(argptr, mode);
390 layout = &SDDS_dataset->layout;
391
392 /* variable arguments are pairs of (index, value), where index is a int32_t integer */
393 retval = -1;
394 do {
395 if (mode & SDDS_SET_BY_INDEX) {
396 if ((index = va_arg(argptr, int32_t)) == -1) {
397 retval = 1;
398 break;
399 }
400 if (index < 0 || index >= layout->n_parameters) {
401 SDDS_SetError("Unable to set parameter values--index out of range (SDDS_SetParameters)");
402 retval = 0;
403 break;
404 }
405 } else {
406 if ((name = va_arg(argptr, char *)) == NULL) {
407 retval = 1;
408 break;
409 }
410 if ((index = SDDS_GetParameterIndex(SDDS_dataset, name)) < 0) {
411 sprintf(s, "Unable to set parameter values--name %s not recognized (SDDS_SetParameters)", name);
412 SDDS_SetError(s);
413 retval = 0;
414 break;
415 }
416 }
417 switch (layout->parameter_definition[index].type) {
418 case SDDS_SHORT:
419 if (mode & SDDS_PASS_BY_VALUE)
420 *((short *)SDDS_dataset->parameter[index]) = (short)va_arg(argptr, int);
421 else
422 *((short *)SDDS_dataset->parameter[index]) = *(va_arg(argptr, short *));
423 break;
424 case SDDS_USHORT:
425 if (mode & SDDS_PASS_BY_VALUE)
426 *((unsigned short *)SDDS_dataset->parameter[index]) = (unsigned short)va_arg(argptr, unsigned int);
427 else
428 *((unsigned short *)SDDS_dataset->parameter[index]) = *(va_arg(argptr, unsigned short *));
429 break;
430 case SDDS_LONG:
431 if (mode & SDDS_PASS_BY_VALUE)
432 *((int32_t *)SDDS_dataset->parameter[index]) = (int32_t)va_arg(argptr, int32_t);
433 else
434 *((int32_t *)SDDS_dataset->parameter[index]) = *(va_arg(argptr, int32_t *));
435 break;
436 case SDDS_ULONG:
437 if (mode & SDDS_PASS_BY_VALUE)
438 *((uint32_t *)SDDS_dataset->parameter[index]) = (uint32_t)va_arg(argptr, uint32_t);
439 else
440 *((uint32_t *)SDDS_dataset->parameter[index]) = *(va_arg(argptr, uint32_t *));
441 break;
442 case SDDS_LONG64:
443 if (mode & SDDS_PASS_BY_VALUE)
444 *((int64_t *)SDDS_dataset->parameter[index]) = (int64_t)va_arg(argptr, int64_t);
445 else
446 *((int64_t *)SDDS_dataset->parameter[index]) = *(va_arg(argptr, int64_t *));
447 break;
448 case SDDS_ULONG64:
449 if (mode & SDDS_PASS_BY_VALUE)
450 *((uint64_t *)SDDS_dataset->parameter[index]) = (uint64_t)va_arg(argptr, uint64_t);
451 else
452 *((uint64_t *)SDDS_dataset->parameter[index]) = *(va_arg(argptr, uint64_t *));
453 break;
454 case SDDS_FLOAT:
455 if (mode & SDDS_PASS_BY_VALUE)
456 *((float *)SDDS_dataset->parameter[index]) = (float)va_arg(argptr, double);
457 else
458 *((float *)SDDS_dataset->parameter[index]) = *(va_arg(argptr, float *));
459 break;
460 case SDDS_DOUBLE:
461 if (mode & SDDS_PASS_BY_VALUE)
462 *((double *)SDDS_dataset->parameter[index]) = va_arg(argptr, double);
463 else
464 *((double *)SDDS_dataset->parameter[index]) = *(va_arg(argptr, double *));
465 break;
466 case SDDS_LONGDOUBLE:
467 if (mode & SDDS_PASS_BY_VALUE)
468 *((long double *)SDDS_dataset->parameter[index]) = va_arg(argptr, long double);
469 else
470 *((long double *)SDDS_dataset->parameter[index]) = *(va_arg(argptr, long double *));
471 break;
472 case SDDS_STRING:
473 if (*(char **)SDDS_dataset->parameter[index])
474 free(*(char **)SDDS_dataset->parameter[index]);
475 if (mode & SDDS_PASS_BY_VALUE) {
476 if (!SDDS_CopyString((char **)SDDS_dataset->parameter[index], va_arg(argptr, char *))) {
477 SDDS_SetError("Unable to set string parameter value--allocation failure (SDDS_SetParameters)");
478 retval = 0;
479 }
480 } else {
481 if (!SDDS_CopyString((char **)SDDS_dataset->parameter[index], *(va_arg(argptr, char **)))) {
482 SDDS_SetError("Unable to set string parameter value--allocation failure (SDDS_SetParameters)");
483 retval = 0;
484 }
485 }
486 break;
487 case SDDS_CHARACTER:
488 if (mode & SDDS_PASS_BY_VALUE)
489 *((char *)SDDS_dataset->parameter[index]) = (char)va_arg(argptr, int);
490 else
491 *((char *)SDDS_dataset->parameter[index]) = *(va_arg(argptr, char *));
492 break;
493 default:
494 SDDS_SetError("Unknown data type encountered (SDDS_SetParameters)");
495 retval = 0;
496 }
497 } while (retval == -1);
498 va_end(argptr);
499 return (retval);
500}

◆ SDDS_SetParametersFromDoubles()

epicsShareFuncSDDS int32_t SDDS_SetParametersFromDoubles ( SDDS_DATASET * SDDS_dataset,
int32_t mode,
... )
extern

Sets the values of one or more parameters in the current data table of an SDDS dataset using double-precision floating-point numbers.

This function assigns double-precision floating-point values to specified parameters in the current data table of the given SDDS dataset. It must be preceded by a call to SDDS_StartPage to initialize the table. Parameters can be identified either by their index or by their name. The values can be passed either by value or by reference, depending on the specified mode.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the data set.
modeA bitwise combination of the following constants:
  • SDDS_SET_BY_INDEX: Identify parameters by their indices.
  • SDDS_SET_BY_NAME: Identify parameters by their names.
  • SDDS_PASS_BY_VALUE: Pass parameter values by value.
  • SDDS_PASS_BY_REFERENCE: Pass parameter values by reference.

Mode Requirements:

  • Exactly one of SDDS_SET_BY_INDEX or SDDS_SET_BY_NAME must be set.
  • Exactly one of SDDS_PASS_BY_VALUE or SDDS_PASS_BY_REFERENCE must be set.

Syntax Based on Mode Combination:

  • SDDS_SET_BY_INDEX + SDDS_PASS_BY_VALUE: int32_t SDDS_SetParametersFromDoubles(SDDS_DATASET *SDDS_dataset, int32_t mode, int32_t index, double value)
  • SDDS_SET_BY_INDEX + SDDS_PASS_BY_REFERENCE: int32_t SDDS_SetParametersFromDoubles(SDDS_DATASET *SDDS_dataset, int32_t mode, int32_t index, double *data)
  • SDDS_SET_BY_NAME + SDDS_PASS_BY_VALUE: int32_t SDDS_SetParametersFromDoubles(SDDS_DATASET *SDDS_dataset, int32_t mode, char *name, double value)
  • SDDS_SET_BY_NAME + SDDS_PASS_BY_REFERENCE: int32_t SDDS_SetParametersFromDoubles(SDDS_DATASET *SDDS_dataset, int32_t mode, char *name, double *data)

Note: For parameters of type SDDS_STRING, setting values using this function is not supported and will result in an error.

Returns
Returns 1 on successful assignment of all specified parameter values. On failure, returns 0 and records an appropriate error message.
See also
SDDS_StartPage, SDDS_SetError, SDDS_GetParameterIndex

Definition at line 703 of file SDDS_dataprep.c.

703 {
704 va_list argptr;
705 int32_t index, retval;
706 SDDS_LAYOUT *layout;
707 char *name;
708 char s[SDDS_MAXLINE];
709
710 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_SetParametersFromDoubles"))
711 return (0);
712 if (!(mode & SDDS_SET_BY_INDEX || mode & SDDS_SET_BY_NAME) || !(mode & SDDS_PASS_BY_VALUE || mode & SDDS_PASS_BY_REFERENCE)) {
713 SDDS_SetError("Unable to set parameter values--unknown mode (SDDS_SetParametersFromDoubles)");
714 return (0);
715 }
716
717 va_start(argptr, mode);
718 layout = &SDDS_dataset->layout;
719
720 /* variable arguments are pairs of (index, value), where index is a int32_t integer */
721 retval = -1;
722 do {
723 if (mode & SDDS_SET_BY_INDEX) {
724 if ((index = va_arg(argptr, int32_t)) == -1) {
725 retval = 1;
726 break;
727 }
728 if (index < 0 || index >= layout->n_parameters) {
729 sprintf(s, "Unable to set parameter values--index %" PRId32 " out of range [%d, %" PRId32 "] (SDDS_SetParametersFromDoubles)", index, 0, layout->n_parameters);
730 SDDS_SetError(s);
731 retval = 0;
732 break;
733 }
734 } else {
735 if ((name = va_arg(argptr, char *)) == NULL) {
736 retval = 1;
737 break;
738 }
739 if ((index = SDDS_GetParameterIndex(SDDS_dataset, name)) < 0) {
740 sprintf(s, "Unable to set parameter values--name %s not recognized (SDDS_SetParametersFromDoubles)", name);
741 SDDS_SetError(s);
742 retval = 0;
743 break;
744 }
745 }
746 switch (layout->parameter_definition[index].type) {
747 case SDDS_SHORT:
748 if (mode & SDDS_PASS_BY_VALUE)
749 *((short *)SDDS_dataset->parameter[index]) = va_arg(argptr, double);
750 else
751 *((short *)SDDS_dataset->parameter[index]) = *(va_arg(argptr, double *));
752 break;
753 case SDDS_USHORT:
754 if (mode & SDDS_PASS_BY_VALUE)
755 *((unsigned short *)SDDS_dataset->parameter[index]) = va_arg(argptr, double);
756 else
757 *((unsigned short *)SDDS_dataset->parameter[index]) = *(va_arg(argptr, double *));
758 break;
759 case SDDS_LONG:
760 if (mode & SDDS_PASS_BY_VALUE)
761 *((int32_t *)SDDS_dataset->parameter[index]) = va_arg(argptr, double);
762 else
763 *((int32_t *)SDDS_dataset->parameter[index]) = *(va_arg(argptr, double *));
764 break;
765 case SDDS_ULONG:
766 if (mode & SDDS_PASS_BY_VALUE)
767 *((uint32_t *)SDDS_dataset->parameter[index]) = va_arg(argptr, double);
768 else
769 *((uint32_t *)SDDS_dataset->parameter[index]) = *(va_arg(argptr, double *));
770 break;
771 case SDDS_LONG64:
772 if (mode & SDDS_PASS_BY_VALUE)
773 *((int64_t *)SDDS_dataset->parameter[index]) = va_arg(argptr, double);
774 else
775 *((int64_t *)SDDS_dataset->parameter[index]) = *(va_arg(argptr, double *));
776 break;
777 case SDDS_ULONG64:
778 if (mode & SDDS_PASS_BY_VALUE)
779 *((uint64_t *)SDDS_dataset->parameter[index]) = va_arg(argptr, double);
780 else
781 *((uint64_t *)SDDS_dataset->parameter[index]) = *(va_arg(argptr, double *));
782 break;
783 case SDDS_FLOAT:
784 if (mode & SDDS_PASS_BY_VALUE)
785 *((float *)SDDS_dataset->parameter[index]) = (float)va_arg(argptr, double);
786 else
787 *((float *)SDDS_dataset->parameter[index]) = *(va_arg(argptr, double *));
788 break;
789 case SDDS_DOUBLE:
790 if (mode & SDDS_PASS_BY_VALUE)
791 *((double *)SDDS_dataset->parameter[index]) = va_arg(argptr, double);
792 else
793 *((double *)SDDS_dataset->parameter[index]) = *(va_arg(argptr, double *));
794 break;
795 case SDDS_STRING:
796 case SDDS_CHARACTER:
797 SDDS_SetError("Nonnumeric data type encountered (SDDS_SetParametersFromDoubles)");
798 retval = 0;
799 break;
800 default:
801 SDDS_SetError("Unknown data type encountered (SDDS_SetParametersFromDoubles)");
802 retval = 0;
803 }
804 } while (retval == -1);
805 va_end(argptr);
806 return (retval);
807}

◆ SDDS_SetParameterUnitsConversion()

epicsShareFuncSDDS int32_t SDDS_SetParameterUnitsConversion ( SDDS_DATASET * SDDS_dataset,
char * parameter_name,
char * new_units,
char * old_units,
double factor )
extern

Sets unit conversions for a specified parameter in an SDDS dataset.

This function updates the units of the specified parameter within the SDDS dataset and applies a conversion factor to its value if the dataset has already been read (i.e., pages_read > 0). The function ensures that the new units are consistent with the old units if provided.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
parameter_nameA null-terminated string specifying the name of the parameter to update.
new_unitsA null-terminated string specifying the new units to assign to the parameter. This parameter must not be NULL.
old_unitsA null-terminated string specifying the expected current units of the parameter. If NULL, the function does not verify the existing units.
factorA double representing the conversion factor to apply to the parameter's value. The parameter's value will be multiplied by this factor.
Returns
Returns 1 on successful unit conversion and update. On failure, returns 0 and sets an appropriate error message.
Return values
1Indicates that the unit conversion was successfully applied.
0Indicates that an error occurred (e.g., invalid dataset, unrecognized parameter name, type undefined, memory allocation failure).
Note
  • The new_units parameter must not be NULL. Passing NULL will result in an error.
  • If the dataset has not been read yet (pages_read == 0), the conversion factor is stored but not applied immediately.
  • The function handles various data types, ensuring that the conversion factor is appropriately applied based on the parameter's type.
See also
SDDS_SetArrayUnitsConversion, SDDS_SetColumnUnitsConversion, SDDS_GetParameter

Definition at line 4904 of file SDDS_extract.c.

4904 {
4905 int32_t index, type;
4906 void *rawData;
4907 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_SetParameterUnitsConversion"))
4908 return(0);
4909 if (new_units == NULL) {
4910 SDDS_SetError("new_units is NULL (SDDS_SetParameterUnitsConversion)");
4911 return(0);
4912 }
4913 if ((index = SDDS_GetParameterIndex(SDDS_dataset, parameter_name)) < 0) {
4914 SDDS_SetError("Unable to get parameter--name is not recognized (SDDS_SetParameterUnitsConversion)");
4915 return(0);
4916 }
4917 if (!(type = SDDS_GetParameterType(SDDS_dataset, index))) {
4918 SDDS_SetError("Unable to get parameter--data type undefined (SDDS_SetParameterUnitsConversion)");
4919 return(0);
4920 }
4921 if (SDDS_dataset->layout.parameter_definition[index].units != NULL) {
4922 if (strcmp(new_units, SDDS_dataset->layout.parameter_definition[index].units) != 0) {
4923 if ((old_units != NULL) && (strcmp(old_units, SDDS_dataset->layout.parameter_definition[index].units) != 0)) {
4924 SDDS_SetError("Unexpected units value found (SDDS_SetParameterUnitsConversion)");
4925 return(0);
4926 }
4927 /* free(SDDS_dataset->layout.parameter_definition[index].units); */
4928 cp_str(&(SDDS_dataset->layout.parameter_definition[index].units), new_units);
4929 }
4930 } else {
4931 cp_str(&(SDDS_dataset->layout.parameter_definition[index].units), new_units);
4932 }
4933
4934 if (SDDS_dataset->pages_read == 0) {
4935 return(1);
4936 }
4937 rawData = SDDS_dataset->parameter[index];
4938 switch (type) {
4939 case SDDS_LONGDOUBLE:
4940 *((long double *)rawData) *= factor;
4941 break;
4942 case SDDS_DOUBLE:
4943 *((double *)rawData) *= factor;
4944 break;
4945 case SDDS_FLOAT:
4946 *((float *)rawData) *= factor;
4947 break;
4948 case SDDS_LONG:
4949 *((int32_t *)rawData) *= factor;
4950 break;
4951 case SDDS_ULONG:
4952 *((uint32_t *)rawData) *= factor;
4953 break;
4954 case SDDS_LONG64:
4955 *((int64_t *)rawData) *= factor;
4956 break;
4957 case SDDS_ULONG64:
4958 *((uint64_t *)rawData) *= factor;
4959 break;
4960 case SDDS_SHORT:
4961 *((short *)rawData) *= factor;
4962 break;
4963 case SDDS_USHORT:
4964 *((unsigned short *)rawData) *= factor;
4965 break;
4966 }
4967 return(1);
4968}

◆ SDDS_SetReadRecoveryMode()

epicsShareFuncSDDS void SDDS_SetReadRecoveryMode ( SDDS_DATASET * SDDS_dataset,
int32_t mode )
extern

Sets the read recovery mode for an SDDS dataset.

This function configures whether read recovery is possible for the specified SDDS dataset. Enabling recovery allows the dataset to attempt to recover partial data in case of read errors.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
modeInteger flag indicating the recovery mode:
  • 0 to disable read recovery.
  • 1 to enable read recovery.

The function updates the readRecoveryPossible flag within the dataset structure based on the provided mode parameter. This flag is later checked by other functions to determine whether to attempt data recovery after encountering read errors.

Note
  • Enabling read recovery does not guarantee that all data can be recovered after an error.
  • It is recommended to enable recovery only if partial data recovery is acceptable in your application.

Definition at line 2103 of file SDDS_binary.c.

2103 {
2104 SDDS_dataset->readRecoveryPossible = mode;
2105}

◆ SDDS_SetRowCountMode()

epicsShareFuncSDDS int32_t SDDS_SetRowCountMode ( SDDS_DATASET * SDDS_dataset,
uint32_t mode )
extern

Sets the row count mode for the SDDS dataset.

This function configures how row counts are managed within the SDDS dataset. The row count mode determines whether row counts are variable, fixed, or entirely omitted during data writing. Proper configuration of row count modes can enhance data integrity and performance based on specific use cases.

Parameters
[in,out]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
[in]modeThe row count mode to be set. Must be one of the following:
  • SDDS_VARIABLEROWCOUNT: Enables variable row counts, allowing the number of rows to vary.
  • SDDS_FIXEDROWCOUNT: Sets a fixed row count mode, where the number of rows is constant.
  • SDDS_NOROWCOUNT: Disables row counts, omitting them from the dataset.
Returns
  • 1 on successful configuration of the row count mode.
  • 0 on failure, with an error message set internally.
Precondition
  • The dataset must be initialized and configured for output.
  • The layout must not have been written to the file yet.
Postcondition
  • The dataset's row count mode is updated according to the specified mode.
Note
  • Changing the row count mode affects how row metadata is handled during data writing.
  • The SDDS_FIXEDROWCOUNT mode may require specifying additional parameters such as row increment.
Warning
  • Attempting to change the row count mode after the layout has been written to the file or while reading from a file will result in an error.
  • Selecting an invalid row count mode will result in an error.

Definition at line 2346 of file SDDS_output.c.

2346 {
2347 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_SetRowCountMode"))
2348 return 0;
2349 if (SDDS_dataset->layout.layout_written) {
2350 SDDS_SetError("Can't change row count mode after writing the layout, or for a file you are reading.");
2351 return 0;
2352 }
2353 if (mode & SDDS_VARIABLEROWCOUNT) {
2354 SDDS_dataset->layout.data_mode.fixed_row_count = 0;
2355 SDDS_dataset->layout.data_mode.no_row_counts = 0;
2356 } else if (mode & SDDS_FIXEDROWCOUNT) {
2357 SDDS_dataset->layout.data_mode.fixed_row_count = 1;
2358 SDDS_dataset->layout.data_mode.fixed_row_increment = 500;
2359 SDDS_dataset->layout.data_mode.no_row_counts = 0;
2360 SDDS_dataset->layout.data_mode.fsync_data = 0;
2361 } else if (mode & SDDS_NOROWCOUNT) {
2362 SDDS_dataset->layout.data_mode.fixed_row_count = 0;
2363 SDDS_dataset->layout.data_mode.no_row_counts = 1;
2364 } else {
2365 SDDS_SetError("Invalid row count mode (SDDS_SetRowCountMode).");
2366 return 0;
2367 }
2368 if (!SDDS_SaveLayout(SDDS_dataset))
2369 return 0;
2370 return 1;
2371}

◆ SDDS_SetRowFlags()

epicsShareFuncSDDS int32_t SDDS_SetRowFlags ( SDDS_DATASET * SDDS_dataset,
int32_t row_flag_value )
extern

Sets the acceptance flags for all rows in the current data table of a data set.

This function initializes the acceptance flags for each row in the data table. A non-zero flag indicates that the row is "of interest" and should be considered in subsequent operations, while a zero flag marks the row for rejection.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the data set.
row_flag_valueInteger value to assign to all row flags.
  • Non-zero value: Marks rows as accepted ("of interest").
  • Zero value: Marks rows as rejected.
Returns
  • 1 on successful update of row flags.
  • 0 on failure, with an error message recorded.
Note
This function overwrites any existing row flags with the specified row_flag_value.
See also
SDDS_GetRowFlag, SDDS_GetRowFlags

Definition at line 46 of file SDDS_extract.c.

46 {
47 /* int32_t i; */
48 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_SetRowFlags"))
49 return (0);
50 if (!SDDS_SetMemory(SDDS_dataset->row_flag, SDDS_dataset->n_rows_allocated, SDDS_LONG, (int32_t)row_flag_value, (int32_t)0)) {
51 SDDS_SetError("Unable to set row flags--memory filling failed (SDDS_SetRowFlags)");
52 return (0);
53 }
54 return (1);
55}

◆ SDDS_SetRowLimit()

epicsShareFuncSDDS int64_t SDDS_SetRowLimit ( int64_t limit)
extern

Sets the row limit for the SDDS dataset.

Parameters
limitThe maximum number of rows to read. If limit <= 0, the row limit is set to INT64_MAX.
Returns
The previous row limit value.

Definition at line 1243 of file SDDS_input.c.

1243 {
1244 int64_t previous;
1245 if (limit <= 0)
1246 limit = INT64_MAX;
1247 mdb_thread_lock(&SDDS_RowLimitLock);
1248 previous = SDDS_RowLimit;
1249 SDDS_RowLimit = limit;
1250 mdb_thread_unlock(&SDDS_RowLimitLock);
1251 return previous;
1252}
static MDB_THREAD_LOCK SDDS_RowLimitLock
Global variable to set a limit on the number of rows read.

◆ SDDS_SetRowsOfInterest()

epicsShareFuncSDDS int64_t SDDS_SetRowsOfInterest ( SDDS_DATASET * SDDS_dataset,
char * selection_column,
int32_t mode,
... )
extern

Sets the rows of interest in an SDDS dataset based on various selection criteria.

This function marks rows in the provided SDDS dataset as "of interest" based on the specified selection criteria. It supports multiple selection modes, allowing users to specify rows by an array of names, a single string containing multiple names, a variadic list of names, or by matching a specific string with logical operations.

Calling Modes:

  • SDDS_NAME_ARRAY: Specify an array of names.
    SDDS_SetRowsOfInterest(&SDDS_dataset, selection_column, SDDS_NAME_ARRAY, int32_t n_entries, char **name);
    int64_t SDDS_SetRowsOfInterest(SDDS_DATASET *SDDS_dataset, char *selection_column, int32_t mode,...)
    Sets the rows of interest in an SDDS dataset based on various selection criteria.
  • SDDS_NAMES_STRING: Provide a single string containing multiple names separated by delimiters.
    SDDS_SetRowsOfInterest(&SDDS_dataset, selection_column, SDDS_NAMES_STRING, char *names);
  • SDDS_NAME_STRINGS: Pass multiple name strings, terminated by NULL.
    SDDS_SetRowsOfInterest(&SDDS_dataset, selection_column, SDDS_NAME_STRINGS, char *name1, char *name2, ..., NULL);
  • SDDS_MATCH_STRING: Match rows based on a single string and logical operations.
    SDDS_SetRowsOfInterest(&SDDS_dataset, selection_column, SDDS_MATCH_STRING, char *name, int32_t logic_mode);

Additionally, each of these modes has a case-insensitive variant prefixed with SDDS_CI_ (e.g., SDDS_CI_NAME_ARRAY).

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
selection_columnA null-terminated string specifying the name of the column used for row selection. This column must be of string type.
modeAn integer representing the selection mode. Supported modes include:
  • SDDS_NAME_ARRAY
  • SDDS_NAMES_STRING
  • SDDS_NAME_STRINGS
  • SDDS_MATCH_STRING
  • SDDS_CI_NAME_ARRAY
  • SDDS_CI_NAMES_STRING
  • SDDS_CI_NAME_STRINGS
  • SDDS_CI_MATCH_STRING
...Variable arguments corresponding to the selected mode:
  • SDDS_NAME_ARRAY and SDDS_CI_NAME_ARRAY:
    • int32_t n_entries: Number of names.
    • char **name: Array of name strings.
  • SDDS_NAMES_STRING and SDDS_CI_NAMES_STRING:
    • char *names: Single string containing multiple names separated by delimiters.
  • SDDS_NAME_STRINGS and SDDS_CI_NAME_STRINGS:
    • char *name1, char *name2, ..., NULL: Multiple name strings terminated by NULL.
  • SDDS_MATCH_STRING and SDDS_CI_MATCH_STRING:
    • char *name: String to match.
    • int32_t logic_mode: Logical operation mode.
Returns
On success, returns the number of rows marked as "of interest". On failure, returns -1 and sets an appropriate error message.
Return values
-1Indicates that an error occurred (e.g., invalid dataset, unrecognized selection column, memory allocation failure, unknown mode).
Non-negativeInteger representing the count of rows marked as "of interest".
Note
  • The caller must ensure that the selection_column exists and is of string type in the dataset.
  • For modes that allocate memory internally (e.g., SDDS_NAMES_STRING), the function handles memory management internally.
See also
SDDS_MatchRowsOfInterest, SDDS_FilterRowsOfInterest, SDDS_DeleteUnsetRows

Definition at line 3325 of file SDDS_extract.c.

3332{
3333 va_list argptr;
3334 int32_t retval, type, index, n_names;
3335 int64_t i, j;
3336 char **name, *string, *match_string, *ptr;
3337 int32_t local_memory; /* (0,1,2) --> (none, pointer array, pointer array + strings) locally allocated */
3338 char buffer[SDDS_MAXLINE];
3339 int32_t logic, caseSensitive;
3340 int64_t count;
3341
3342 name = NULL;
3343 n_names = local_memory = logic = 0;
3344
3345 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_SetRowsOfInterest"))
3346 return (-1);
3347 va_start(argptr, mode);
3348 retval = 1;
3349 caseSensitive = 1;
3350 match_string = NULL;
3351 switch (mode) {
3352 case SDDS_CI_NAME_ARRAY:
3353 caseSensitive = 0;
3354 case SDDS_NAME_ARRAY:
3355 local_memory = 0;
3356 n_names = va_arg(argptr, int32_t);
3357 name = va_arg(argptr, char **);
3358 break;
3359 case SDDS_CI_NAMES_STRING:
3360 caseSensitive = 0;
3361 case SDDS_NAMES_STRING:
3362 local_memory = 2;
3363 n_names = 0;
3364 name = NULL;
3365 ptr = va_arg(argptr, char *);
3366 SDDS_CopyString(&string, ptr);
3367 while (SDDS_GetToken(string, buffer, SDDS_MAXLINE) > 0) {
3368 if (!(name = SDDS_Realloc(name, sizeof(*name) * (n_names + 1))) || !SDDS_CopyString(name + n_names, buffer)) {
3369 SDDS_SetError("Unable to process row selection--memory allocation failure (SDDS_SetRowsOfInterest)");
3370 retval = -1;
3371 break;
3372 }
3373 n_names++;
3374 }
3375 free(string);
3376 break;
3377 case SDDS_CI_NAME_STRINGS:
3378 caseSensitive = 0;
3379 case SDDS_NAME_STRINGS:
3380 local_memory = 1;
3381 n_names = 0;
3382 name = NULL;
3383 while ((string = va_arg(argptr, char *))) {
3384 if (!(name = SDDS_Realloc(name, sizeof(*name) * (n_names + 1)))) {
3385 SDDS_SetError("Unable to process row selection--memory allocation failure (SDDS_SetRowsOfInterest)");
3386 retval = -1;
3387 break;
3388 }
3389 name[n_names++] = string;
3390 }
3391 break;
3392 case SDDS_CI_MATCH_STRING:
3393 caseSensitive = 0;
3394 case SDDS_MATCH_STRING:
3395 local_memory = 0;
3396 n_names = 1;
3397 if ((string = va_arg(argptr, char *)))
3398 match_string = expand_ranges(string);
3399 logic = va_arg(argptr, int32_t);
3400 if (logic & SDDS_NOCASE_COMPARE)
3401 caseSensitive = 0;
3402 break;
3403 default:
3404 SDDS_SetError("Unable to process row selection--unknown mode (SDDS_SetRowsOfInterest)");
3405 retval = -1;
3406 break;
3407 }
3408
3409 va_end(argptr);
3410 if (retval != 1)
3411 return (-1);
3412
3413 if (mode != SDDS_MATCH_STRING && mode != SDDS_CI_MATCH_STRING) {
3414 int (*stringCompare)(const char *s1, const char *s2);
3415 if (caseSensitive)
3416 stringCompare = strcmp;
3417 else
3418 stringCompare = strcmp_ci;
3419 if ((index = SDDS_GetColumnIndex(SDDS_dataset, selection_column)) < 0) {
3420 SDDS_SetError("Unable to process row selection--unrecognized selection column name (SDDS_SetRowsOfInterest)");
3421 return (-1);
3422 }
3423 if ((type = SDDS_GetColumnType(SDDS_dataset, index)) != SDDS_STRING) {
3424 SDDS_SetError("Unable to select rows--selection column is not string type (SDDS_SetRowsOfInterest)");
3425 return (-1);
3426 }
3427 if (n_names == 0) {
3428 SDDS_SetError("Unable to process row selection--no names in call (SDDS_SetRowsOfInterest)");
3429 return (-1);
3430 }
3431 for (j = 0; j < n_names; j++) {
3432 for (i = 0; i < SDDS_dataset->n_rows; i++) {
3433 if ((*stringCompare)(*((char **)SDDS_dataset->data[index] + i), name[j]) == 0)
3434 SDDS_dataset->row_flag[i] = 1;
3435 }
3436 }
3437 } else {
3438 if (selection_column) {
3439 int (*wildMatch)(char *string, char *template);
3440 if (caseSensitive)
3441 wildMatch = wild_match;
3442 else
3443 wildMatch = wild_match_ci;
3444 if (!match_string) {
3445 SDDS_SetError("Unable to select rows--no matching string given (SDDS_SetRowsOfInterest)");
3446 return (-1);
3447 }
3448 if ((index = SDDS_GetColumnIndex(SDDS_dataset, selection_column)) < 0) {
3449 free(match_string);
3450 SDDS_SetError("Unable to process row selection--unrecognized selection column name (SDDS_SetRowsOfInterest)");
3451 return (-1);
3452 }
3453 if ((type = SDDS_GetColumnType(SDDS_dataset, index)) != SDDS_STRING) {
3454 free(match_string);
3455 SDDS_SetError("Unable to select rows--selection column is not string type (SDDS_SetRowsOfInterest)");
3456 return (-1);
3457 }
3458 for (i = 0; i < SDDS_dataset->n_rows; i++)
3459 SDDS_dataset->row_flag[i] = SDDS_Logic(SDDS_dataset->row_flag[i], (*wildMatch)(*((char **)SDDS_dataset->data[index] + i), match_string), logic);
3460 } else {
3461 for (i = 0; i < SDDS_dataset->n_rows; i++)
3462 SDDS_dataset->row_flag[i] = SDDS_Logic(SDDS_dataset->row_flag[i], 0, logic & ~(SDDS_AND | SDDS_OR));
3463 }
3464 }
3465
3466 if (local_memory == 2) {
3467 for (i = 0; i < n_names; i++)
3468 free(name[i]);
3469 }
3470 if (match_string)
3471 free(match_string);
3472 if (local_memory >= 1)
3473 free(name);
3474
3475 for (i = count = 0; i < SDDS_dataset->n_rows; i++)
3476 if (SDDS_dataset->row_flag[i])
3477 count++;
3478 return (count);
3479}

◆ SDDS_SetRowValues()

epicsShareFuncSDDS int32_t SDDS_SetRowValues ( SDDS_DATASET * SDDS_dataset,
int32_t mode,
int64_t row,
... )
extern

Sets the values of one or more columns in a specified row of the current data table of an SDDS dataset.

This function assigns values to specified columns in a particular row of the current data table within the given SDDS dataset. It must be preceded by a call to SDDS_StartPage to initialize the table. Columns can be identified either by their index or by their name. The values can be passed either by value or by reference, depending on the specified mode.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the data set.
modeA bitwise combination of the following constants:
  • SDDS_SET_BY_INDEX: Identify columns by their indices.
  • SDDS_SET_BY_NAME: Identify columns by their names.
  • SDDS_PASS_BY_VALUE: Pass column values by value.
  • SDDS_PASS_BY_REFERENCE: Pass column values by reference.

Mode Requirements:

  • Exactly one of SDDS_SET_BY_INDEX or SDDS_SET_BY_NAME must be set.
  • Exactly one of SDDS_PASS_BY_VALUE or SDDS_PASS_BY_REFERENCE must be set.

Syntax Based on Mode Combination:

  • SDDS_SET_BY_INDEX + SDDS_PASS_BY_VALUE: int32_t SDDS_SetRowValues(SDDS_DATASET *SDDS_dataset, int32_t mode, int64_t row, int32_t index, value, ..., -1)
  • SDDS_SET_BY_INDEX + SDDS_PASS_BY_REFERENCE: int32_t SDDS_SetRowValues(SDDS_DATASET *SDDS_dataset, int32_t mode, int64_t row, int32_t index, void *data, ..., -1)
  • SDDS_SET_BY_NAME + SDDS_PASS_BY_VALUE: int32_t SDDS_SetRowValues(SDDS_DATASET *SDDS_dataset, int32_t mode, int64_t row, char *name, value, ..., NULL)
  • SDDS_SET_BY_NAME + SDDS_PASS_BY_REFERENCE: int32_t SDDS_SetRowValues(SDDS_DATASET *SDDS_dataset, int32_t mode, int64_t row, char *name, void *data, ..., NULL)

Note: For columns of type SDDS_STRING, passing by value means passing a char *, whereas passing by reference means passing a char **.

Parameters
rowThe row number in the data table where the column values will be set. Row numbering starts from 1.
Returns
Returns 1 on successful assignment of all specified column values. On failure, returns 0 and records an appropriate error message.
See also
SDDS_StartPage, SDDS_SetError, SDDS_GetColumnIndex, SDDS_CopyString

Definition at line 994 of file SDDS_dataprep.c.

994 {
995 va_list argptr;
996 int32_t index;
997 int32_t retval;
998 SDDS_LAYOUT *layout;
999 char *name;
1000 char buffer[200];
1001
1002 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_SetRowValues"))
1003 return (0);
1004 if (!(mode & SDDS_SET_BY_INDEX || mode & SDDS_SET_BY_NAME) || !(mode & SDDS_PASS_BY_VALUE || mode & SDDS_PASS_BY_REFERENCE)) {
1005 SDDS_SetError("Unable to set column values--unknown mode (SDDS_SetRowValues)");
1006 return (0);
1007 }
1008 if (!SDDS_CheckTabularData(SDDS_dataset, "SDDS_SetRowValues"))
1009 return (0);
1010 row -= SDDS_dataset->first_row_in_mem;
1011 if (row >= SDDS_dataset->n_rows_allocated) {
1012 sprintf(buffer, "Unable to set column values--row number (%" PRId64 ") exceeds exceeds allocated memory (%" PRId64 ") (SDDS_SetRowValues)", row, SDDS_dataset->n_rows_allocated);
1013 SDDS_SetError(buffer);
1014 return (0);
1015 }
1016 if (row > SDDS_dataset->n_rows - 1)
1017 SDDS_dataset->n_rows = row + 1;
1018
1019 va_start(argptr, row);
1020 layout = &SDDS_dataset->layout;
1021
1022 /* variable arguments are pairs of (index, value), where index is a int32_t integer */
1023 retval = -1;
1024#ifdef DEBUG
1025 fprintf(stderr, "setting row %" PRId64 " (mem slot %" PRId64 ")\n", row + SDDS_dataset->first_row_in_mem, row);
1026#endif
1027 do {
1028 if (mode & SDDS_SET_BY_INDEX) {
1029 if ((index = va_arg(argptr, int32_t)) == -1) {
1030 retval = 1;
1031 break;
1032 }
1033 if (index < 0 || index >= layout->n_columns) {
1034 SDDS_SetError("Unable to set column values--index out of range (SDDS_SetRowValues)");
1035 retval = 0;
1036 break;
1037 }
1038#ifdef DEBUG
1039 fprintf(stderr, "Setting values for column #%" PRId32 "\n", index);
1040#endif
1041 } else {
1042 if ((name = va_arg(argptr, char *)) == NULL) {
1043 retval = 1;
1044 break;
1045 }
1046#ifdef DEBUG
1047 fprintf(stderr, "Setting values for column %s\n", name);
1048#endif
1049 if ((index = SDDS_GetColumnIndex(SDDS_dataset, name)) < 0) {
1050 SDDS_SetError("Unable to set column values--name not recognized (SDDS_SetRowValues)");
1051 retval = 0;
1052 break;
1053 }
1054 }
1055 switch (layout->column_definition[index].type) {
1056 case SDDS_SHORT:
1057 if (mode & SDDS_PASS_BY_VALUE)
1058 *(((short *)SDDS_dataset->data[index]) + row) = (short)va_arg(argptr, int);
1059 else
1060 *(((short *)SDDS_dataset->data[index]) + row) = *(va_arg(argptr, short *));
1061 break;
1062 case SDDS_USHORT:
1063 if (mode & SDDS_PASS_BY_VALUE)
1064 *(((unsigned short *)SDDS_dataset->data[index]) + row) = (unsigned short)va_arg(argptr, unsigned int);
1065 else
1066 *(((unsigned short *)SDDS_dataset->data[index]) + row) = *(va_arg(argptr, unsigned short *));
1067 break;
1068 case SDDS_LONG:
1069 if (mode & SDDS_PASS_BY_VALUE)
1070 *(((int32_t *)SDDS_dataset->data[index]) + row) = va_arg(argptr, int32_t);
1071 else
1072 *(((int32_t *)SDDS_dataset->data[index]) + row) = *(va_arg(argptr, int32_t *));
1073 break;
1074 case SDDS_ULONG:
1075 if (mode & SDDS_PASS_BY_VALUE)
1076 *(((uint32_t *)SDDS_dataset->data[index]) + row) = va_arg(argptr, uint32_t);
1077 else
1078 *(((uint32_t *)SDDS_dataset->data[index]) + row) = *(va_arg(argptr, uint32_t *));
1079 break;
1080 case SDDS_LONG64:
1081 if (mode & SDDS_PASS_BY_VALUE)
1082 *(((int64_t *)SDDS_dataset->data[index]) + row) = va_arg(argptr, int64_t);
1083 else
1084 *(((int64_t *)SDDS_dataset->data[index]) + row) = *(va_arg(argptr, int64_t *));
1085 break;
1086 case SDDS_ULONG64:
1087 if (mode & SDDS_PASS_BY_VALUE)
1088 *(((uint64_t *)SDDS_dataset->data[index]) + row) = va_arg(argptr, uint64_t);
1089 else
1090 *(((uint64_t *)SDDS_dataset->data[index]) + row) = *(va_arg(argptr, uint64_t *));
1091 break;
1092 case SDDS_FLOAT:
1093 if (mode & SDDS_PASS_BY_VALUE)
1094 *(((float *)SDDS_dataset->data[index]) + row) = (float)va_arg(argptr, double);
1095 else
1096 *(((float *)SDDS_dataset->data[index]) + row) = *(va_arg(argptr, float *));
1097 break;
1098 case SDDS_DOUBLE:
1099 if (mode & SDDS_PASS_BY_VALUE)
1100 *(((double *)SDDS_dataset->data[index]) + row) = va_arg(argptr, double);
1101 else
1102 *(((double *)SDDS_dataset->data[index]) + row) = *(va_arg(argptr, double *));
1103 break;
1104 case SDDS_LONGDOUBLE:
1105 if (mode & SDDS_PASS_BY_VALUE)
1106 *(((long double *)SDDS_dataset->data[index]) + row) = va_arg(argptr, long double);
1107 else
1108 *(((long double *)SDDS_dataset->data[index]) + row) = *(va_arg(argptr, long double *));
1109 break;
1110 case SDDS_STRING:
1111 if (((char **)SDDS_dataset->data[index])[row]) {
1112 free(((char **)SDDS_dataset->data[index])[row]);
1113 ((char **)SDDS_dataset->data[index])[row] = NULL;
1114 }
1115 if (mode & SDDS_PASS_BY_VALUE) {
1116 if (!SDDS_CopyString((char **)SDDS_dataset->data[index] + row, va_arg(argptr, char *))) {
1117 SDDS_SetError("Unable to set string column value--allocation failure (SDDS_SetRowValues)");
1118 retval = 0;
1119 }
1120 } else {
1121 if (!SDDS_CopyString((char **)SDDS_dataset->data[index] + row, *(va_arg(argptr, char **)))) {
1122 SDDS_SetError("Unable to set string column value--allocation failure (SDDS_SetRowValues)");
1123 retval = 0;
1124 }
1125 }
1126 break;
1127 case SDDS_CHARACTER:
1128 if (mode & SDDS_PASS_BY_VALUE)
1129 *(((char *)SDDS_dataset->data[index]) + row) = (char)va_arg(argptr, int);
1130 else
1131 *(((char *)SDDS_dataset->data[index]) + row) = *(va_arg(argptr, char *));
1132 break;
1133 default:
1134 SDDS_SetError("Unknown data type encountered (SDDS_SetRowValues");
1135 retval = 0;
1136 break;
1137 }
1138 } while (retval == -1);
1139 va_end(argptr);
1140 return (retval);
1141}

◆ SDDS_SetTerminateMode()

epicsShareFuncSDDS void SDDS_SetTerminateMode ( uint32_t mode)
extern

Sets the terminate mode for the SDDS dataset.

Parameters
modeThe terminate mode to set.

Definition at line 1359 of file SDDS_input.c.

1359 {
1360 mdb_thread_lock(&terminateModeLock);
1361 terminateMode = mode;
1362 mdb_thread_unlock(&terminateModeLock);
1363}
static MDB_THREAD_LOCK terminateModeLock
Global variable to set the terminate mode for the SDDS dataset.

◆ SDDS_ShortenTable()

epicsShareFuncSDDS int32_t SDDS_ShortenTable ( SDDS_DATASET * SDDS_dataset,
int64_t rows )
extern

Shortens the data table in the SDDS dataset to a specified number of rows.

This function reduces the number of allocated rows in the specified SDDS dataset to the given rows count. It reallocates memory for each column's data array and the row flags, freeing existing data as necessary. All data is reset, and the number of rows is set to zero.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure whose table will be shortened.
rowsThe new number of rows to allocate in the table. If rows is less than or equal to zero, it defaults to 1.
Returns
Returns 1 on successful reallocation and initialization. On failure, returns 0 and records an error message.
See also
SDDS_Realloc, SDDS_SetMemory, SDDS_Free, SDDS_SetError

Definition at line 244 of file SDDS_dataprep.c.

244 {
245 SDDS_LAYOUT *layout;
246 int64_t i, size;
247
248 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_ShortenTable"))
249 return (0);
250 layout = &SDDS_dataset->layout;
251 if (!SDDS_dataset->data && !(SDDS_dataset->data = (void **)calloc(layout->n_columns, sizeof(*SDDS_dataset->data)))) {
252 SDDS_SetError("Unable to start page--memory allocation failure (SDDS_ShortenTable)");
253 return (0);
254 }
255 if (rows <= 0)
256 rows = 1;
257 for (i = 0; i < layout->n_columns; i++) {
258 size = SDDS_type_size[layout->column_definition[i].type - 1];
259 if (SDDS_dataset->data[i])
260 free(SDDS_dataset->data[i]);
261 if (!(SDDS_dataset->data[i] = (void *)calloc(rows, size))) {
262 SDDS_SetError("Unable to shorten page--memory allocation failure (SDDS_ShortenTable)");
263 return (0);
264 }
265 }
266 if (SDDS_dataset->row_flag)
267 free(SDDS_dataset->row_flag);
268 if (!(SDDS_dataset->row_flag = (int32_t *)malloc(rows * sizeof(int32_t)))) {
269 SDDS_SetError("Unable to shorten page--memory allocation failure (SDDS_ShortenTable)");
270 return (0);
271 }
272 SDDS_dataset->n_rows_allocated = rows;
273 /* Shorten table is not exactly true. It is really deleting all the rows and then allocating new space.
274 if (SDDS_dataset->n_rows > rows) {
275 SDDS_dataset->n_rows = rows;
276 }
277 */
278 SDDS_dataset->n_rows = 0;
279
280 if (!SDDS_SetMemory(SDDS_dataset->row_flag, SDDS_dataset->n_rows_allocated, SDDS_LONG, (int32_t)1, (int32_t)0) ||
281 !SDDS_SetMemory(SDDS_dataset->column_flag, SDDS_dataset->layout.n_columns, SDDS_LONG, (int32_t)1, (int32_t)0) ||
282 !SDDS_SetMemory(SDDS_dataset->column_order, SDDS_dataset->layout.n_columns, SDDS_LONG, (int32_t)0, (int32_t)1)) {
283 SDDS_SetError("Unable to shorten page--memory initialization failure (SDDS_ShortenTable)");
284 return (0);
285 }
286 return (1);
287}

◆ SDDS_SprintTypedValue()

epicsShareFuncSDDS int32_t SDDS_SprintTypedValue ( void * data,
int64_t index,
int32_t type,
const char * format,
char * buffer,
uint32_t mode )
extern

Formats a data value of a specified type into a string buffer using an optional printf format string.

This function formats a single data value from a data array into a provided buffer. It is a wrapper for SDDS_SprintTypedValueFactor with a default scaling factor of 1.0.

Parameters
[in]dataPointer to the base address of the data array containing the value to be formatted.
[in]indexThe index of the item within the data array to be formatted.
[in]typeThe data type of the value, specified by one of the SDDS constants:
  • SDDS_LONGDOUBLE
  • SDDS_DOUBLE
  • SDDS_FLOAT
  • SDDS_LONG
  • SDDS_ULONG
  • SDDS_LONG64
  • SDDS_ULONG64
  • SDDS_SHORT
  • SDDS_USHORT
  • SDDS_CHARACTER
  • SDDS_STRING
[in]format(Optional) NULL-terminated string specifying a printf format. If NULL, a default format is used based on the data type.
[out]bufferPointer to a character array where the formatted string will be stored.
[in]modeFlags controlling the formatting behavior. Valid values are:
  • 0: Default behavior.
  • SDDS_PRINT_NOQUOTES: When formatting strings, do not enclose them in quotes.
Returns
Returns 1 on success. On failure, returns 0 and records an error message.
Note
This function uses a default scaling factor of 1.0.
See also
SDDS_SprintTypedValueFactor
SDDS_SetError

Definition at line 161 of file SDDS_utils.c.

161 {
162 return SDDS_SprintTypedValueFactor(data, index, type, format, buffer, mode, 1.0);
163}
int32_t SDDS_SprintTypedValueFactor(void *data, int64_t index, int32_t type, const char *format, char *buffer, uint32_t mode, double factor)
Reallocates memory to a new size and zero-initializes the additional space.
Definition SDDS_utils.c:196

◆ SDDS_SprintTypedValueFactor()

epicsShareFuncSDDS int32_t SDDS_SprintTypedValueFactor ( void * data,
int64_t index,
int32_t type,
const char * format,
char * buffer,
uint32_t mode,
double factor )
extern

Reallocates memory to a new size and zero-initializes the additional space.

This function extends the standard realloc functionality by zero-initializing any newly allocated memory beyond the original size. It ensures that memory is consistently reallocated and initialized across different build configurations.

Parameters
[in]dataPointer to the base address of the data array containing the value to be formatted.
[in]indexThe index of the item within the data array to be formatted.
[in]typeThe data type of the value, specified by one of the SDDS constants:
  • SDDS_LONGDOUBLE
  • SDDS_DOUBLE
  • SDDS_FLOAT
  • SDDS_LONG
  • SDDS_ULONG
  • SDDS_SHORT
  • SDDS_USHORT
  • SDDS_CHARACTER
  • SDDS_STRING
[in]format(Optional) NULL-terminated string specifying a printf format. If NULL, a default format is used based on the data type.
[out]bufferPointer to a character array where the formatted string will be stored.
[in]modeFlags controlling the formatting behavior. Valid values are:
  • 0: Default behavior.
  • SDDS_PRINT_NOQUOTES: When formatting strings, do not enclose them in quotes.
[in]factorScaling factor to be applied to the value before formatting. The value is multiplied by this factor.
Returns
Returns 1 on success. On failure, returns 0 and records an error message.
Note
This function handles string types by optionally enclosing them in quotes, unless SDDS_PRINT_NOQUOTES is specified in mode.
See also
SDDS_SprintTypedValue
SDDS_SetError

Definition at line 196 of file SDDS_utils.c.

196 {
197 char buffer2[SDDS_PRINT_BUFLEN], *s;
198 short printed;
199
200 if (!data) {
201 SDDS_SetError("Unable to print value--data pointer is NULL (SDDS_SprintTypedValueFactor)");
202 return (0);
203 }
204 if (!buffer) {
205 SDDS_SetError("Unable to print value--buffer pointer is NULL (SDDS_SprintTypedValueFactor)");
206 return (0);
207 }
208 switch (type) {
209 case SDDS_SHORT:
210 sprintf(buffer, format ? format : "%hd", (short)(*((short *)data + index) * (factor)));
211 break;
212 case SDDS_USHORT:
213 sprintf(buffer, format ? format : "%hu", (unsigned short)(*((unsigned short *)data + index) * (factor)));
214 break;
215 case SDDS_LONG:
216 sprintf(buffer, format ? format : "%" PRId32, (int32_t)(*((int32_t *)data + index) * (factor)));
217 break;
218 case SDDS_ULONG:
219 sprintf(buffer, format ? format : "%" PRIu32, (uint32_t)(*((uint32_t *)data + index) * (factor)));
220 break;
221 case SDDS_LONG64:
222 sprintf(buffer, format ? format : "%" PRId64, (int64_t)(*((int64_t *)data + index) * (factor)));
223 break;
224 case SDDS_ULONG64:
225 sprintf(buffer, format ? format : "%" PRIu64, (uint64_t)(*((uint64_t *)data + index) * (factor)));
226 break;
227 case SDDS_FLOAT:
228 sprintf(buffer, format ? format : "%15.8e", (float)(*((float *)data + index) * (factor)));
229 break;
230 case SDDS_DOUBLE:
231 sprintf(buffer, format ? format : "%21.15e", (double)(*((double *)data + index) * (factor)));
232 break;
233 case SDDS_LONGDOUBLE:
234 if (LDBL_DIG == 18) {
235 sprintf(buffer, format ? format : "%21.18Le", (long double)(*((long double *)data + index) * (factor)));
236 } else {
237 sprintf(buffer, format ? format : "%21.15Le", (long double)(*((long double *)data + index) * (factor)));
238 }
239 break;
240 case SDDS_STRING:
241 s = *((char **)data + index);
242 if ((int32_t)strlen(s) > SDDS_PRINT_BUFLEN - 3) {
243 SDDS_SetError("Buffer size overflow (SDDS_SprintTypedValue)");
244 return (0);
245 }
246 if (!(mode & SDDS_PRINT_NOQUOTES)) {
247 printed = 0;
248 if (!s || SDDS_StringIsBlank(s))
249 sprintf(buffer, "\"\"");
250 else if (strchr(s, '"')) {
251 strcpy(buffer2, s);
252 SDDS_EscapeQuotes(buffer2, '"');
253 if (SDDS_HasWhitespace(buffer2))
254 sprintf(buffer, "\"%s\"", buffer2);
255 else
256 strcpy(buffer, buffer2);
257 } else if (SDDS_HasWhitespace(s))
258 sprintf(buffer, "\"%s\"", s);
259 else {
260 sprintf(buffer, format ? format : "%s", s);
261 printed = 1;
262 }
263 if (!printed) {
264 sprintf(buffer2, format ? format : "%s", buffer);
265 strcpy(buffer, buffer2);
266 }
267 } else {
268 sprintf(buffer, format ? format : "%s", s);
269 }
270 break;
271 case SDDS_CHARACTER:
272 sprintf(buffer, format ? format : "%c", *((char *)data + index));
273 break;
274 default:
275 SDDS_SetError("Unable to print value--unknown data type (SDDS_SprintTypedValue)");
276 return (0);
277 }
278 return (1);
279}
void SDDS_EscapeQuotes(char *s, char quote_char)
Escapes quote characters within a string by inserting backslashes.
int32_t SDDS_HasWhitespace(char *string)
Checks if a string contains any whitespace characters.

◆ SDDS_StartPage()

epicsShareFuncSDDS int32_t SDDS_StartPage ( SDDS_DATASET * SDDS_dataset,
int64_t expected_n_rows )
extern

Initializes an SDDS_DATASET structure in preparation for inserting data into a new table.

This function prepares the specified SDDS dataset for data insertion by initializing necessary data structures and allocating memory based on the expected number of rows. It must be preceded by a call to SDDS_InitializeOutput. SDDS_StartPage can be called multiple times to begin writing additional tables within the dataset. After initializing a page, SDDS_WriteTable should be used to write the table to disk.

Parameters
SDDS_datasetPointer to the SDDS_DATASET structure representing the data set.
expected_n_rowsThe expected number of rows in the data table. This value is used to preallocate memory for storing data values. If expected_n_rows is less than or equal to zero, it defaults to 1.
Returns
Returns 1 on successful initialization. On failure, returns 0 and records an error message.
See also
SDDS_InitializeOutput, SDDS_WriteTable, SDDS_SetError

Definition at line 70 of file SDDS_dataprep.c.

70 {
71 SDDS_LAYOUT *layout;
72 int64_t i;
73 int32_t size;
74
75 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_StartPage"))
76 return (0);
77 if ((SDDS_dataset->writing_page) && (SDDS_dataset->layout.data_mode.fixed_row_count)) {
78 if (!SDDS_UpdateRowCount(SDDS_dataset))
79 return (0);
80 }
81 if (!SDDS_RestoreLayout(SDDS_dataset)) {
82 SDDS_SetError("Unable to start page--couldn't restore layout (SDDS_StartPage)");
83 return (0);
84 }
85 if (expected_n_rows <= 0)
86 expected_n_rows = 1;
87 SDDS_dataset->n_rows_written = 0;
88 SDDS_dataset->last_row_written = -1;
89 SDDS_dataset->writing_page = 0;
90 SDDS_dataset->first_row_in_mem = 0;
91 layout = &SDDS_dataset->layout;
92 if (SDDS_dataset->page_started == 0) {
93 if (layout->n_parameters) {
94 if (!(SDDS_dataset->parameter = (void **)calloc(sizeof(*SDDS_dataset->parameter), layout->n_parameters))) {
95 SDDS_SetError("Unable to start page--memory allocation failure (SDDS_StartPage)");
96 return (0);
97 }
98 for (i = 0; i < layout->n_parameters; i++) {
99 if (!(SDDS_dataset->parameter[i] = (void *)calloc(SDDS_type_size[layout->parameter_definition[i].type - 1], 1))) {
100 SDDS_SetError("Unable to start page--memory allocation failure (SDDS_StartPage)");
101 return (0);
102 }
103 }
104 }
105 if (layout->n_arrays) {
106 if (!(SDDS_dataset->array = (SDDS_ARRAY *)calloc(sizeof(*SDDS_dataset->array), layout->n_arrays))) {
107 SDDS_SetError("Unable to start page--memory allocation failure (SDDS_StartPage)");
108 return (0);
109 }
110 }
111 if (layout->n_columns) {
112 if (!(SDDS_dataset->data = (void **)calloc(sizeof(*SDDS_dataset->data), layout->n_columns))) {
113 SDDS_SetError("Unable to start page--memory allocation failure (SDDS_StartPage)");
114 return (0);
115 }
116 SDDS_dataset->row_flag = NULL;
117 if (expected_n_rows) {
118 if (!(SDDS_dataset->row_flag = (int32_t *)SDDS_Malloc(sizeof(int32_t) * expected_n_rows))) {
119 SDDS_SetError("Unable to start page--memory allocation failure (SDDS_StartPage)");
120 return (0);
121 }
122 for (i = 0; i < layout->n_columns; i++) {
123 if (!(SDDS_dataset->data[i] = (void *)calloc(expected_n_rows, SDDS_type_size[layout->column_definition[i].type - 1]))) {
124 SDDS_SetError("Unable to start page--memory allocation failure (SDDS_StartPage)");
125 return (0);
126 }
127 }
128 }
129 SDDS_dataset->n_rows_allocated = expected_n_rows;
130 if (!(SDDS_dataset->column_flag = (int32_t *)SDDS_Realloc(SDDS_dataset->column_flag, sizeof(int32_t) * layout->n_columns)) ||
131 !(SDDS_dataset->column_order = (int32_t *)SDDS_Realloc(SDDS_dataset->column_order, sizeof(int32_t) * layout->n_columns))) {
132 SDDS_SetError("Unable to start page--memory allocation failure (SDDS_StartPage)");
133 return (0);
134 }
135 }
136 } else if (SDDS_dataset->n_rows_allocated >= expected_n_rows && layout->n_columns) {
137 for (i = 0; i < layout->n_columns; i++) {
138 if (SDDS_dataset->data[i] && layout->column_definition[i].type == SDDS_STRING)
139 SDDS_FreeStringArray(SDDS_dataset->data[i], SDDS_dataset->n_rows_allocated);
140 }
141 } else if (SDDS_dataset->n_rows_allocated < expected_n_rows && layout->n_columns) {
142 if (!SDDS_dataset->data) {
143 if (!(SDDS_dataset->column_flag = (int32_t *)SDDS_Realloc(SDDS_dataset->column_flag, sizeof(int32_t) * layout->n_columns)) ||
144 !(SDDS_dataset->column_order = (int32_t *)SDDS_Realloc(SDDS_dataset->column_order, sizeof(int32_t) * layout->n_columns)) ||
145 !(SDDS_dataset->data = (void **)calloc(layout->n_columns, sizeof(*SDDS_dataset->data)))) {
146 SDDS_SetError("Unable to start page--memory allocation failure (SDDS_StartPage)");
147 return (0);
148 }
149 }
150 for (i = 0; i < layout->n_columns; i++) {
151 size = SDDS_type_size[layout->column_definition[i].type - 1];
152 if (SDDS_dataset->data[i] && layout->column_definition[i].type == SDDS_STRING)
153 SDDS_FreeStringArray(SDDS_dataset->data[i], SDDS_dataset->n_rows_allocated);
154 if (!(SDDS_dataset->data[i] = (void *)SDDS_Realloc(SDDS_dataset->data[i], expected_n_rows * size))) {
155 SDDS_SetError("Unable to start page--memory allocation failure (SDDS_StartPage)");
156 return (0);
157 }
158 SDDS_ZeroMemory((char *)SDDS_dataset->data[i] + size * SDDS_dataset->n_rows_allocated, size * (expected_n_rows - SDDS_dataset->n_rows_allocated));
159 }
160 if (!(SDDS_dataset->row_flag = (int32_t *)SDDS_Realloc(SDDS_dataset->row_flag, sizeof(int32_t) * expected_n_rows))) {
161 SDDS_SetError("Unable to start page--memory allocation failure (SDDS_StartPage)");
162 return (0);
163 }
164 SDDS_dataset->n_rows_allocated = expected_n_rows;
165 }
166 if (SDDS_dataset->n_rows_allocated && layout->n_columns && !SDDS_SetMemory(SDDS_dataset->row_flag, SDDS_dataset->n_rows_allocated, SDDS_LONG, (int32_t)1, (int32_t)0)) {
167 SDDS_SetError("Unable to start page--memory initialization failure (SDDS_StartPage)");
168 return (0);
169 }
170 if (layout->n_columns && (!SDDS_SetMemory(SDDS_dataset->column_flag, layout->n_columns, SDDS_LONG, (int32_t)1, (int32_t)0) ||
171 !SDDS_SetMemory(SDDS_dataset->column_order, layout->n_columns, SDDS_LONG, (int32_t)0, (int32_t)1))) {
172 SDDS_SetError("Unable to start page--memory initialization failure (SDDS_StartPage)");
173 return (0);
174 }
175 SDDS_dataset->n_of_interest = layout->n_columns;
176 SDDS_dataset->page_number++;
177 SDDS_dataset->page_started = 1;
178 SDDS_dataset->n_rows = 0;
179 return (1);
180}
int32_t SDDS_RestoreLayout(SDDS_DATASET *SDDS_dataset)
Definition SDDS_copy.c:697
int32_t SDDS_UpdateRowCount(SDDS_DATASET *SDDS_dataset)

◆ SDDS_StringIsBlank()

epicsShareFuncSDDS int32_t SDDS_StringIsBlank ( char * s)
extern

Checks if a string is blank (contains only whitespace characters).

This function determines whether the provided NULL-terminated string s consists solely of whitespace characters. If the string is NULL or contains only whitespace, the function returns 1. If the string contains any non-whitespace characters, it returns 0.

Parameters
[in]sPointer to the NULL-terminated string to be checked.
Returns
  • Returns 1 if the string is NULL or contains only whitespace characters.
  • Returns 0 if the string contains any non-whitespace characters.
See also
isspace

Definition at line 2470 of file SDDS_utils.c.

2470 {
2471 if (!s)
2472 return 1;
2473 while (*s)
2474 if (!isspace(*s++))
2475 return (0);
2476 return (1);
2477}

◆ SDDS_SwapDouble()

void SDDS_SwapDouble ( double * data)

Swaps the endianness of a double.

This function swaps the byte order of a 64-bit double-precision floating-point number pointed to by the provided data pointer. It effectively converts the data between little-endian and big-endian formats.

Parameters
[in,out]dataPointer to the double whose byte order is to be swapped.
Note
The function modifies the data in place. Ensure that the pointer is valid and points to a properly aligned double.

Definition at line 4083 of file SDDS_binary.c.

4083 {
4084 double copy;
4085 short i, j;
4086 copy = *data;
4087 for (i = 0, j = 7; i < 8; i++, j--)
4088 *(((char *)data) + i) = *(((char *)&copy) + j);
4089}

◆ SDDS_SwapEndsArrayData()

epicsShareFuncSDDS int32_t SDDS_SwapEndsArrayData ( SDDS_DATASET * SDDSin)
extern

Swaps the endianness of the array data in an SDDS dataset.

This function iterates through all arrays defined in the specified SDDS dataset and swaps the byte order of each element to match the system's native endianness. It supports various data types including short, unsigned short, long, unsigned long, long long, unsigned long long, float, double, and long double. The function ensures that binary data is correctly interpreted on systems with different byte orders.

Parameters
[in,out]SDDSinPointer to the SDDS_DATASET structure representing the dataset whose array data endianness is to be swapped.
Returns
int32_t Always returns 1.
Return values
1The endianness of all applicable array data elements was successfully swapped.
Note
This function modifies the dataset's array data in place. It should be called only when the dataset's byte order is known to differ from the system's native byte order.

Definition at line 3872 of file SDDS_binary.c.

3872 {
3873 int32_t i, j;
3874 SDDS_LAYOUT *layout;
3875 short *sData;
3876 unsigned short *suData;
3877 int32_t *lData;
3878 uint32_t *luData;
3879 int64_t *lData64;
3880 uint64_t *luData64;
3881 float *fData;
3882 double *dData;
3883 long double *ldData;
3884
3885 layout = &SDDSin->layout;
3886
3887 for (i = 0; i < layout->n_arrays; i++) {
3888 switch (layout->array_definition[i].type) {
3889 case SDDS_SHORT:
3890 sData = SDDSin->array[i].data;
3891 for (j = 0; j < SDDSin->array[i].elements; j++)
3892 SDDS_SwapShort(sData + j);
3893 break;
3894 case SDDS_USHORT:
3895 suData = SDDSin->array[i].data;
3896 for (j = 0; j < SDDSin->array[i].elements; j++)
3897 SDDS_SwapUShort(suData + j);
3898 break;
3899 case SDDS_LONG:
3900 lData = SDDSin->array[i].data;
3901 for (j = 0; j < SDDSin->array[i].elements; j++)
3902 SDDS_SwapLong(lData + j);
3903 break;
3904 case SDDS_ULONG:
3905 luData = SDDSin->array[i].data;
3906 for (j = 0; j < SDDSin->array[i].elements; j++)
3907 SDDS_SwapULong(luData + j);
3908 break;
3909 case SDDS_LONG64:
3910 lData64 = SDDSin->array[i].data;
3911 for (j = 0; j < SDDSin->array[i].elements; j++)
3912 SDDS_SwapLong64(lData64 + j);
3913 break;
3914 case SDDS_ULONG64:
3915 luData64 = SDDSin->array[i].data;
3916 for (j = 0; j < SDDSin->array[i].elements; j++)
3917 SDDS_SwapULong64(luData64 + j);
3918 break;
3919 case SDDS_LONGDOUBLE:
3920 ldData = SDDSin->array[i].data;
3921 for (j = 0; j < SDDSin->array[i].elements; j++)
3922 SDDS_SwapLongDouble(ldData + j);
3923 break;
3924 case SDDS_DOUBLE:
3925 dData = SDDSin->array[i].data;
3926 for (j = 0; j < SDDSin->array[i].elements; j++)
3927 SDDS_SwapDouble(dData + j);
3928 break;
3929 case SDDS_FLOAT:
3930 fData = SDDSin->array[i].data;
3931 for (j = 0; j < SDDSin->array[i].elements; j++)
3932 SDDS_SwapFloat(fData + j);
3933 break;
3934 default:
3935 break;
3936 }
3937 }
3938 return (1);
3939}
void SDDS_SwapLongDouble(long double *data)
Swaps the endianness of a long double.
void SDDS_SwapULong64(uint64_t *data)
Swaps the endianness of a 64-bit unsigned integer.
void SDDS_SwapULong(uint32_t *data)
Swaps the endianness of a 32-bit unsigned integer.
void SDDS_SwapUShort(unsigned short *data)
Swaps the endianness of an unsigned short integer.
void SDDS_SwapDouble(double *data)
Swaps the endianness of a double.
void SDDS_SwapShort(short *data)
Swaps the endianness of a short integer.
void SDDS_SwapFloat(float *data)
Swaps the endianness of a float.

◆ SDDS_SwapEndsColumnData()

epicsShareFuncSDDS int32_t SDDS_SwapEndsColumnData ( SDDS_DATASET * SDDSin)
extern

Swaps the endianness of the column data in an SDDS dataset.

This function iterates through all columns in the specified SDDS dataset and swaps the byte order of each data element to match the system's native endianness. It supports various data types, including short, unsigned short, long, unsigned long, long long, unsigned long long, float, double, and long double. The function ensures that binary data is correctly interpreted on systems with different byte orders.

Parameters
[in,out]SDDSinPointer to the SDDS_DATASET structure representing the dataset whose column data endianness is to be swapped.
Returns
int32_t Always returns 1.
Return values
1The endianness of all applicable column data elements was successfully swapped.
Note
This function modifies the dataset's column data in place. It should be called only when the dataset's byte order is known to differ from the system's native byte order. String data types are not affected by this function.

Definition at line 3707 of file SDDS_binary.c.

3707 {
3708 int32_t i, row;
3709 SDDS_LAYOUT *layout;
3710 short *sData;
3711 unsigned short *suData;
3712 int32_t *lData;
3713 uint32_t *luData;
3714 int64_t *lData64;
3715 uint64_t *luData64;
3716 float *fData;
3717 double *dData;
3718 long double *ldData;
3719
3720 layout = &SDDSin->layout;
3721 for (i = 0; i < layout->n_columns; i++) {
3722 switch (layout->column_definition[i].type) {
3723 case SDDS_SHORT:
3724 sData = SDDSin->data[i];
3725 for (row = 0; row < SDDSin->n_rows; row++)
3726 SDDS_SwapShort(sData + row);
3727 break;
3728 case SDDS_USHORT:
3729 suData = SDDSin->data[i];
3730 for (row = 0; row < SDDSin->n_rows; row++)
3731 SDDS_SwapUShort(suData + row);
3732 break;
3733 case SDDS_LONG:
3734 lData = SDDSin->data[i];
3735 for (row = 0; row < SDDSin->n_rows; row++)
3736 SDDS_SwapLong(lData + row);
3737 break;
3738 case SDDS_ULONG:
3739 luData = SDDSin->data[i];
3740 for (row = 0; row < SDDSin->n_rows; row++)
3741 SDDS_SwapULong(luData + row);
3742 break;
3743 case SDDS_LONG64:
3744 lData64 = SDDSin->data[i];
3745 for (row = 0; row < SDDSin->n_rows; row++)
3746 SDDS_SwapLong64(lData64 + row);
3747 break;
3748 case SDDS_ULONG64:
3749 luData64 = SDDSin->data[i];
3750 for (row = 0; row < SDDSin->n_rows; row++)
3751 SDDS_SwapULong64(luData64 + row);
3752 break;
3753 case SDDS_LONGDOUBLE:
3754 ldData = SDDSin->data[i];
3755 for (row = 0; row < SDDSin->n_rows; row++)
3756 SDDS_SwapLongDouble(ldData + row);
3757 break;
3758 case SDDS_DOUBLE:
3759 dData = SDDSin->data[i];
3760 for (row = 0; row < SDDSin->n_rows; row++)
3761 SDDS_SwapDouble(dData + row);
3762 break;
3763 case SDDS_FLOAT:
3764 fData = SDDSin->data[i];
3765 for (row = 0; row < SDDSin->n_rows; row++)
3766 SDDS_SwapFloat(fData + row);
3767 break;
3768 default:
3769 break;
3770 }
3771 }
3772 return (1);
3773}

◆ SDDS_SwapEndsParameterData()

epicsShareFuncSDDS int32_t SDDS_SwapEndsParameterData ( SDDS_DATASET * SDDSin)
extern

Swaps the endianness of the parameter data in an SDDS dataset.

This function iterates through all parameters in the specified SDDS dataset and swaps the byte order of each data element to match the system's native endianness. It handles various data types, including short, unsigned short, long, unsigned long, long long, unsigned long long, float, double, and long double. Parameters with fixed values are skipped as their byte order is already consistent.

Parameters
[in,out]SDDSinPointer to the SDDS_DATASET structure representing the dataset whose parameter data endianness is to be swapped.
Returns
int32_t Always returns 1.
Return values
1The endianness of all applicable parameter data elements was successfully swapped.
Note
This function modifies the dataset's parameter data in place. It should be called only when the dataset's byte order is known to differ from the system's native byte order. String data types and parameters with fixed values are not affected by this function.

Definition at line 3793 of file SDDS_binary.c.

3793 {
3794 int32_t i;
3795 SDDS_LAYOUT *layout;
3796 short *sData;
3797 unsigned short *suData;
3798 int32_t *lData;
3799 uint32_t *luData;
3800 int64_t *lData64;
3801 uint64_t *luData64;
3802 float *fData;
3803 double *dData;
3804 long double *ldData;
3805
3806 layout = &SDDSin->layout;
3807 for (i = 0; i < layout->n_parameters; i++) {
3808 if (layout->parameter_definition[i].fixed_value) {
3809 continue;
3810 }
3811 switch (layout->parameter_definition[i].type) {
3812 case SDDS_SHORT:
3813 sData = SDDSin->parameter[i];
3814 SDDS_SwapShort(sData);
3815 break;
3816 case SDDS_USHORT:
3817 suData = SDDSin->parameter[i];
3818 SDDS_SwapUShort(suData);
3819 break;
3820 case SDDS_LONG:
3821 lData = SDDSin->parameter[i];
3822 SDDS_SwapLong(lData);
3823 break;
3824 case SDDS_ULONG:
3825 luData = SDDSin->parameter[i];
3826 SDDS_SwapULong(luData);
3827 break;
3828 case SDDS_LONG64:
3829 lData64 = SDDSin->parameter[i];
3830 SDDS_SwapLong64(lData64);
3831 break;
3832 case SDDS_ULONG64:
3833 luData64 = SDDSin->parameter[i];
3834 SDDS_SwapULong64(luData64);
3835 break;
3836 case SDDS_LONGDOUBLE:
3837 ldData = SDDSin->parameter[i];
3838 SDDS_SwapLongDouble(ldData);
3839 break;
3840 case SDDS_DOUBLE:
3841 dData = SDDSin->parameter[i];
3842 SDDS_SwapDouble(dData);
3843 break;
3844 case SDDS_FLOAT:
3845 fData = SDDSin->parameter[i];
3846 SDDS_SwapFloat(fData);
3847 break;
3848 default:
3849 break;
3850 }
3851 }
3852 return (1);
3853}

◆ SDDS_SwapFloat()

void SDDS_SwapFloat ( float * data)

Swaps the endianness of a float.

This function swaps the byte order of a 32-bit floating-point number pointed to by the provided data pointer. It effectively converts the data between little-endian and big-endian formats.

Parameters
[in,out]dataPointer to the float whose byte order is to be swapped.
Note
The function modifies the data in place. Ensure that the pointer is valid and points to a properly aligned float.

Definition at line 4064 of file SDDS_binary.c.

4064 {
4065 float copy;
4066 short i, j;
4067 copy = *data;
4068 for (i = 0, j = 3; i < 4; i++, j--)
4069 *(((char *)data) + i) = *(((char *)&copy) + j);
4070}

◆ SDDS_SwapLong()

epicsShareFuncSDDS void SDDS_SwapLong ( int32_t * data)
extern

Swaps the endianness of a 32-bit integer.

This function swaps the byte order of a 32-bit integer pointed to by the provided data pointer. It effectively converts the data between little-endian and big-endian formats.

Parameters
[in,out]dataPointer to the 32-bit integer whose byte order is to be swapped.
Note
The function modifies the data in place. Ensure that the pointer is valid and points to a properly aligned 32-bit integer.

Definition at line 3988 of file SDDS_binary.c.

3988 {
3989 int32_t copy;
3990 short i, j;
3991 copy = *data;
3992 for (i = 0, j = 3; i < 4; i++, j--)
3993 *(((char *)data) + i) = *(((char *)&copy) + j);
3994}

◆ SDDS_SwapLong64()

epicsShareFuncSDDS void SDDS_SwapLong64 ( int64_t * data)
extern

Swaps the endianness of a 64-bit integer.

This function swaps the byte order of a 64-bit integer pointed to by the provided data pointer. It effectively converts the data between little-endian and big-endian formats.

Parameters
[in,out]dataPointer to the 64-bit integer whose byte order is to be swapped.
Note
The function modifies the data in place. Ensure that the pointer is valid and points to a properly aligned 64-bit integer.

Definition at line 4026 of file SDDS_binary.c.

4026 {
4027 int64_t copy;
4028 short i, j;
4029 copy = *data;
4030 for (i = 0, j = 7; i < 8; i++, j--)
4031 *(((char *)data) + i) = *(((char *)&copy) + j);
4032}

◆ SDDS_SwapLongDouble()

void SDDS_SwapLongDouble ( long double * data)

Swaps the endianness of a long double.

This function swaps the byte order of a long double floating-point number pointed to by the provided data pointer. It effectively converts the data between little-endian and big-endian formats. The function accounts for different sizes of long double based on the system's architecture.

Parameters
[in,out]dataPointer to the long double whose byte order is to be swapped.
Note
The function modifies the data in place. Ensure that the pointer is valid and points to a properly aligned long double. The size of long double may vary between different systems.

Definition at line 4103 of file SDDS_binary.c.

4103 {
4104 long double copy;
4105 short i, j;
4106 copy = *data;
4107 if (LDBL_DIG == 18) {
4108 for (i = 0, j = 11; i < 12; i++, j--)
4109 *(((char *)data) + i) = *(((char *)&copy) + j);
4110 } else {
4111 for (i = 0, j = 7; i < 8; i++, j--)
4112 *(((char *)data) + i) = *(((char *)&copy) + j);
4113 }
4114}

◆ SDDS_SwapShort()

void SDDS_SwapShort ( short * data)

Swaps the endianness of a short integer.

This function swaps the byte order of a 16-bit short integer pointed to by the provided data pointer. It effectively converts the data between little-endian and big-endian formats.

Parameters
[in,out]dataPointer to the short integer whose byte order is to be swapped.
Note
The function modifies the data in place. Ensure that the pointer is valid and points to a properly aligned 16-bit short integer.

Definition at line 3952 of file SDDS_binary.c.

3952 {
3953 unsigned char c1;
3954 c1 = *((char *)data);
3955 *((char *)data) = *(((char *)data) + 1);
3956 *(((char *)data) + 1) = c1;
3957}

◆ SDDS_SwapULong()

epicsShareFuncSDDS void SDDS_SwapULong ( uint32_t * data)
extern

Swaps the endianness of a 32-bit unsigned integer.

This function swaps the byte order of a 32-bit unsigned integer pointed to by the provided data pointer. It effectively converts the data between little-endian and big-endian formats.

Parameters
[in,out]dataPointer to the 32-bit unsigned integer whose byte order is to be swapped.
Note
The function modifies the data in place. Ensure that the pointer is valid and points to a properly aligned 32-bit unsigned integer.

Definition at line 4007 of file SDDS_binary.c.

4007 {
4008 uint32_t copy;
4009 short i, j;
4010 copy = *data;
4011 for (i = 0, j = 3; i < 4; i++, j--)
4012 *(((char *)data) + i) = *(((char *)&copy) + j);
4013}

◆ SDDS_SwapULong64()

epicsShareFuncSDDS void SDDS_SwapULong64 ( uint64_t * data)
extern

Swaps the endianness of a 64-bit unsigned integer.

This function swaps the byte order of a 64-bit unsigned integer pointed to by the provided data pointer. It effectively converts the data between little-endian and big-endian formats.

Parameters
[in,out]dataPointer to the 64-bit unsigned integer whose byte order is to be swapped.
Note
The function modifies the data in place. Ensure that the pointer is valid and points to a properly aligned 64-bit unsigned integer.

Definition at line 4045 of file SDDS_binary.c.

4045 {
4046 uint64_t copy;
4047 short i, j;
4048 copy = *data;
4049 for (i = 0, j = 7; i < 8; i++, j--)
4050 *(((char *)data) + i) = *(((char *)&copy) + j);
4051}

◆ SDDS_SwapUShort()

void SDDS_SwapUShort ( unsigned short * data)

Swaps the endianness of an unsigned short integer.

This function swaps the byte order of a 16-bit unsigned short integer pointed to by the provided data pointer. It effectively converts the data between little-endian and big-endian formats.

Parameters
[in,out]dataPointer to the unsigned short integer whose byte order is to be swapped.
Note
The function modifies the data in place. Ensure that the pointer is valid and points to a properly aligned 16-bit unsigned short integer.

Definition at line 3970 of file SDDS_binary.c.

3970 {
3971 unsigned char c1;
3972 c1 = *((char *)data);
3973 *((char *)data) = *(((char *)data) + 1);
3974 *(((char *)data) + 1) = c1;
3975}

◆ SDDS_SyncDataSet()

epicsShareFuncSDDS int32_t SDDS_SyncDataSet ( SDDS_DATASET * SDDS_dataset)
extern

Synchronizes the SDDS dataset with the disk by flushing buffered data.

This function attempts to ensure that any buffered data associated with the SDDS dataset is written to the disk using the fsync system call. However, on certain platforms such as VxWorks, Windows, Linux, and macOS, this functionality is not implemented and the function simply returns success. This behavior should be considered when relying on data synchronization across different operating systems.

Parameters
[in]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
Returns
  • 0 on success, indicating that data synchronization is either not needed or was successful.
  • A negative value (e.g., -1) on failure to synchronize the data, with an error message set internally.
Note
  • On unsupported platforms, the function does not perform any synchronization and returns success.
  • The synchronization behavior depends on the operating system and its support for the fsync system call.
Warning
  • On platforms where synchronization is not implemented, relying on this function for data integrity is not possible.
  • Ensure that critical data is handled appropriately, considering the limitations of the target operating system.

Definition at line 1340 of file SDDS_output.c.

1340 {
1341#if defined(vxWorks) || defined(_WIN32) || defined(linux) || defined(__APPLE__)
1342 return (0);
1343#else
1344 if (!(SDDS_dataset->layout.fp)) {
1345 SDDS_SetError("Unable to sync file--file pointer is NULL (SDDS_SyncDataSet)");
1346 return (-1);
1347 }
1348 if (SDDS_dataset->layout.data_mode.fsync_data == 0)
1349 return (0);
1350 if (fsync(fileno(SDDS_dataset->layout.fp)) == 0)
1351 return (0);
1352 /*
1353 SDDS_SetError("Unable to sync file (SDDS_SyncDataSet)");
1354 return(-1);
1355 */
1356 /* This error should not be fatal */
1357 return (0);
1358#endif
1359}

◆ SDDS_Terminate()

epicsShareFuncSDDS int32_t SDDS_Terminate ( SDDS_DATASET * SDDS_dataset)
extern

Closes an SDDS file and frees the related memory.

Parameters
SDDS_datasetA pointer to an SDDS dataset.
Returns
1 on success, 0 on error.

Definition at line 1471 of file SDDS_input.c.

1471 {
1472 SDDS_LAYOUT *layout;
1473 char **ptr;
1474 int64_t i, j;
1475 FILE *fp;
1476 char termBuffer[16384];
1477 int32_t terminateMode;
1478#if SDDS_MPI_IO
1479 if (SDDS_dataset->parallel_io)
1480 return SDDS_MPI_Terminate(SDDS_dataset);
1481#endif
1482 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_Terminate"))
1483 return (0);
1484 layout = &SDDS_dataset->original_layout;
1485 terminateMode = SDDS_GetTerminateMode();
1486
1487 fp = SDDS_dataset->layout.fp;
1488#if defined(zLib)
1489 if (SDDS_dataset->layout.gzipFile) {
1490 if (SDDS_dataset->layout.gzfp && layout->filename) {
1491 if ((SDDS_dataset->writing_page) && (SDDS_dataset->layout.data_mode.fixed_row_count)) {
1492 if (!SDDS_UpdateRowCount(SDDS_dataset))
1493 return (0);
1494 }
1495 gzclose(SDDS_dataset->layout.gzfp);
1496 }
1497 } else {
1498#endif
1499 if (SDDS_dataset->layout.lzmaFile) {
1500 if (SDDS_dataset->layout.lzmafp && layout->filename) {
1501 if ((SDDS_dataset->writing_page) && (SDDS_dataset->layout.data_mode.fixed_row_count)) {
1502 if (!SDDS_UpdateRowCount(SDDS_dataset))
1503 return (0);
1504 }
1505 lzma_close(SDDS_dataset->layout.lzmafp);
1506 }
1507 } else {
1508 if (fp && layout->filename) {
1509 if ((SDDS_dataset->writing_page) && (SDDS_dataset->layout.data_mode.fixed_row_count)) {
1510 if (!SDDS_UpdateRowCount(SDDS_dataset))
1511 return (0);
1512 }
1513 if (layout->popenUsed) {
1514 while (fread(termBuffer, sizeof(*termBuffer), 16384, fp)) {
1515 }
1516#if defined(vxWorks)
1517 fprintf(stderr, "pclose is not supported in vxWorks\n");
1518 exit(1);
1519#else
1520 pclose(fp);
1521#endif
1522 } else {
1523 fclose(fp);
1524 }
1525 }
1526 }
1527#if defined(zLib)
1528 }
1529#endif
1530
1531#if DEBUG
1532 fprintf(stderr, "Freeing data for file %s\n", SDDS_dataset->layout.filename ? SDDS_dataset->layout.filename : "NULL");
1533#endif
1534
1535 if (SDDS_dataset->pagecount_offset)
1536 free(SDDS_dataset->pagecount_offset);
1537 if (SDDS_dataset->row_flag)
1538 free(SDDS_dataset->row_flag);
1539 if (SDDS_dataset->column_order)
1540 free(SDDS_dataset->column_order);
1541 if (SDDS_dataset->column_flag)
1542 free(SDDS_dataset->column_flag);
1543 if (SDDS_dataset->fBuffer.buffer)
1544 free(SDDS_dataset->fBuffer.buffer);
1545#if DEBUG
1546 fprintf(stderr, "freeing parameter data...\n");
1547#endif
1548 if (SDDS_dataset->parameter) {
1549 for (i = 0; i < layout->n_parameters; i++) {
1550 if (layout->parameter_definition[i].type == SDDS_STRING && *(char **)(SDDS_dataset->parameter[i]))
1551 free(*(char **)(SDDS_dataset->parameter[i]));
1552 if (SDDS_dataset->parameter[i])
1553 free(SDDS_dataset->parameter[i]);
1554 }
1555 free(SDDS_dataset->parameter);
1556 }
1557#if DEBUG
1558 fprintf(stderr, "freeing array data...\n");
1559#endif
1560 if (SDDS_dataset->array) {
1561 for (i = 0; i < layout->n_arrays; i++) {
1562 if (layout->array_definition[i].type == SDDS_STRING && !(terminateMode & TERMINATE_DONT_FREE_ARRAY_STRINGS)) {
1563 for (j = 0; j < SDDS_dataset->array[i].elements; j++)
1564 if (((char **)SDDS_dataset->array[i].data)[j])
1565 free(((char **)SDDS_dataset->array[i].data)[j]);
1566 }
1567 /*
1568 if (SDDS_dataset->array[i].definition->type==SDDS_STRING &&
1569 !(SDDS_GetTerminateMode()&TERMINATE_DONT_FREE_ARRAY_STRINGS)) {
1570 for (j=0; j<SDDS_dataset->array[i].elements; j++)
1571 if (((char**)SDDS_dataset->array[i].data)[j])
1572 free(((char**)SDDS_dataset->array[i].data)[j]);
1573 }
1574 */
1575 if (SDDS_dataset->array[i].data)
1576 free(SDDS_dataset->array[i].data);
1577 /* should free the subpointers too, but it would be a lot of trouble for little benefit: */
1578 if (SDDS_dataset->array[i].pointer && SDDS_dataset->array[i].definition->dimensions != 1)
1579 free(SDDS_dataset->array[i].pointer);
1580 if (SDDS_dataset->array[i].dimension)
1581 free(SDDS_dataset->array[i].dimension);
1582 /* don't touch this--it's done below */
1583 if (SDDS_dataset->array[i].definition && SDDS_dataset->array[i].definition->name) {
1584 if (SDDS_dataset->array[i].definition->name != layout->array_definition[i].name)
1585 SDDS_FreeArrayDefinition(SDDS_dataset->array[i].definition);
1586 }
1587 SDDS_dataset->array[i].definition = NULL;
1588 }
1589 free(SDDS_dataset->array);
1590 }
1591#if DEBUG
1592 fprintf(stderr, "freeing tabular data...\n");
1593#endif
1594 if (SDDS_dataset->data) {
1595 for (i = 0; i < layout->n_columns; i++)
1596 if (SDDS_dataset->data[i]) {
1597 if ((SDDS_dataset->column_track_memory == NULL) || (SDDS_dataset->column_track_memory[i])) {
1598 if (layout->column_definition[i].type == SDDS_STRING && !(terminateMode & TERMINATE_DONT_FREE_TABLE_STRINGS)) {
1599 ptr = (char **)SDDS_dataset->data[i];
1600 for (j = 0; j < SDDS_dataset->n_rows_allocated; j++, ptr++)
1601 if (*ptr)
1602 free(*ptr);
1603 }
1604 free(SDDS_dataset->data[i]);
1605 }
1606 }
1607 free(SDDS_dataset->data);
1608 }
1609 if (SDDS_dataset->column_track_memory)
1610 free(SDDS_dataset->column_track_memory);
1611#if DEBUG
1612 fprintf(stderr, "freeing layout data...\n");
1613#endif
1614 if (layout->description)
1615 free(layout->description);
1616 if (layout->contents == (&SDDS_dataset->layout)->contents)
1617 (&SDDS_dataset->layout)->contents = NULL;
1618 if (layout->contents)
1619 free(layout->contents);
1620 if (layout->filename)
1621 free(layout->filename);
1622 if (layout->column_definition) {
1623 for (i = 0; i < layout->n_columns; i++) {
1624 if (layout->column_index[i])
1625 free(layout->column_index[i]);
1626 if (layout->column_definition[i].name)
1627 free(layout->column_definition[i].name);
1628 if (layout->column_definition[i].symbol)
1629 free(layout->column_definition[i].symbol);
1630 if (layout->column_definition[i].units)
1631 free(layout->column_definition[i].units);
1632 if (layout->column_definition[i].description)
1633 free(layout->column_definition[i].description);
1634 if (layout->column_definition[i].format_string)
1635 free(layout->column_definition[i].format_string);
1636 }
1637 free(layout->column_definition);
1638 free(layout->column_index);
1639 }
1640 if (layout->parameter_definition) {
1641 for (i = 0; i < layout->n_parameters; i++) {
1642 if (layout->parameter_index[i])
1643 free(layout->parameter_index[i]);
1644 if (layout->parameter_definition[i].name)
1645 free(layout->parameter_definition[i].name);
1646 if (layout->parameter_definition[i].symbol)
1647 free(layout->parameter_definition[i].symbol);
1648 if (layout->parameter_definition[i].units)
1649 free(layout->parameter_definition[i].units);
1650 if (layout->parameter_definition[i].description)
1651 free(layout->parameter_definition[i].description);
1652 if (layout->parameter_definition[i].format_string)
1653 free(layout->parameter_definition[i].format_string);
1654 if (layout->parameter_definition[i].fixed_value)
1655 free(layout->parameter_definition[i].fixed_value);
1656 }
1657 free(layout->parameter_definition);
1658 free(layout->parameter_index);
1659 }
1660 if (layout->array_definition) {
1661 for (i = 0; i < layout->n_arrays; i++) {
1662 if (layout->array_index[i])
1663 free(layout->array_index[i]);
1664 if (layout->array_definition[i].name)
1665 free(layout->array_definition[i].name);
1666 if (layout->array_definition[i].symbol)
1667 free(layout->array_definition[i].symbol);
1668 if (layout->array_definition[i].units)
1669 free(layout->array_definition[i].units);
1670 if (layout->array_definition[i].description)
1671 free(layout->array_definition[i].description);
1672 if (layout->array_definition[i].format_string)
1673 free(layout->array_definition[i].format_string);
1674 if (layout->array_definition[i].group_name)
1675 free(layout->array_definition[i].group_name);
1676 }
1677 free(layout->array_definition);
1678 free(layout->array_index);
1679 }
1680 if (layout->associate_definition) {
1681 for (i = 0; i < layout->n_associates; i++) {
1682 if (layout->associate_definition[i].name)
1683 free(layout->associate_definition[i].name);
1684 if (layout->associate_definition[i].filename)
1685 free(layout->associate_definition[i].filename);
1686 if (layout->associate_definition[i].path)
1687 free(layout->associate_definition[i].path);
1688 if (layout->associate_definition[i].description)
1689 free(layout->associate_definition[i].description);
1690 if (layout->associate_definition[i].contents)
1691 free(layout->associate_definition[i].contents);
1692 }
1693 free(layout->associate_definition);
1694 }
1695 SDDS_ZeroMemory(&SDDS_dataset->original_layout, sizeof(SDDS_LAYOUT));
1696 layout = &SDDS_dataset->layout;
1697 if (layout->contents)
1698 free(layout->contents);
1699 if (layout->column_definition)
1700 free(layout->column_definition);
1701 if (layout->array_definition)
1702 free(layout->array_definition);
1703 if (layout->associate_definition)
1704 free(layout->associate_definition);
1705 if (layout->parameter_definition)
1706 free(layout->parameter_definition);
1707 if (layout->column_index)
1708 free(layout->column_index);
1709 if (layout->parameter_index)
1710 free(layout->parameter_index);
1711 if (layout->array_index)
1712 free(layout->array_index);
1713 SDDS_ZeroMemory(&SDDS_dataset->layout, sizeof(SDDS_LAYOUT));
1714 SDDS_ZeroMemory(SDDS_dataset, sizeof(SDDS_DATASET));
1715#if DEBUG
1716 fprintf(stderr, "done\n");
1717#endif
1718 return (1);
1719}
int32_t SDDS_MPI_Terminate(SDDS_DATASET *SDDS_dataset)
Terminates the SDDS dataset by freeing all allocated resources and closing MPI files.

◆ SDDS_TransferAllArrayDefinitions()

epicsShareFuncSDDS int32_t SDDS_TransferAllArrayDefinitions ( SDDS_DATASET * SDDS_target,
SDDS_DATASET * SDDS_source,
uint32_t mode )
extern

Transfers all array definitions from a source dataset to a target dataset.

This function defines all arrays in the target SDDS dataset to match the array definitions in the source SDDS dataset. Currently, only mode 0 is supported, which results in an error if any array already exists in the target dataset.

Parameters
SDDS_targetPointer to the SDDS_DATASET structure representing the target dataset.
SDDS_sourcePointer to the SDDS_DATASET structure representing the source dataset.
modeFlags that determine how to handle existing arrays. Valid value:
  • 0: Error if an array already exists in the target dataset.
Returns
1 on success; 0 on failure. On failure, an error message is recorded.
Note
Non-zero mode flags are not supported for array definitions.

Definition at line 506 of file SDDS_transfer.c.

506 {
507 SDDS_LAYOUT *source;
508 int32_t i;
509
510 if (!SDDS_CheckDataset(SDDS_target, "SDDS_TransferAllArrayDefinitions"))
511 return (0);
512 if (!SDDS_CheckDataset(SDDS_source, "SDDS_TransferAllArrayDefinitions"))
513 return (0);
514 if (mode) {
515 /* haven't done this one yet */
516 SDDS_SetError("Nonzero mode not supported for arrays (SDDS_TransferAllArrayDefinitions)");
517 return 0;
518 }
519 source = &SDDS_source->layout;
520 SDDS_DeferSavingLayout(SDDS_target, 1);
521 for (i = 0; i < source->n_arrays; i++)
522 if (SDDS_DefineArray(SDDS_target, source->array_definition[i].name, source->array_definition[i].symbol,
523 source->array_definition[i].units, source->array_definition[i].description,
524 source->array_definition[i].format_string, source->array_definition[i].type, source->array_definition[i].field_length, source->array_definition[i].dimensions, source->array_definition[i].group_name) < 0) {
525 SDDS_SetError("Unable to define array (SDDS_TransferAllArrayDefinitions)");
526 SDDS_DeferSavingLayout(SDDS_target, 0);
527 return 0;
528 }
529 SDDS_DeferSavingLayout(SDDS_target, 0);
530 return 1;
531}

◆ SDDS_TransferAllColumnDefinitions()

epicsShareFuncSDDS int32_t SDDS_TransferAllColumnDefinitions ( SDDS_DATASET * SDDS_target,
SDDS_DATASET * SDDS_source,
uint32_t mode )
extern

Transfers all column definitions from a source dataset to a target dataset.

This function defines all columns in the target SDDS dataset to match the column definitions in the source SDDS dataset. It handles existing columns based on the specified mode.

Parameters
SDDS_targetPointer to the SDDS_DATASET structure representing the target dataset.
SDDS_sourcePointer to the SDDS_DATASET structure representing the source dataset.
modeFlags that determine how to handle existing columns. Valid flags include:
  • 0: Error if a column already exists in the target dataset.
  • SDDS_TRANSFER_KEEPOLD: Retain existing columns in the target dataset and skip transferring conflicting columns.
  • SDDS_TRANSFER_OVERWRITE: Overwrite existing columns in the target dataset with definitions from the source dataset.
Returns
1 on success; 0 on failure. On failure, an error message is recorded.

Definition at line 424 of file SDDS_transfer.c.

424 {
425 SDDS_LAYOUT *target, *source;
426 int32_t i, index;
427 char messBuffer[1024];
428
429 if (!SDDS_CheckDataset(SDDS_target, "SDDS_TransferAllColumnDefinitions"))
430 return (0);
431 if (!SDDS_CheckDataset(SDDS_source, "SDDS_TransferAllColumnDefinitions"))
432 return (0);
433 if (mode & SDDS_TRANSFER_KEEPOLD && mode & SDDS_TRANSFER_OVERWRITE) {
434 SDDS_SetError("Inconsistent mode flags (SDDS_TransferAllColumnDefinitions)");
435 return 0;
436 }
437 target = &SDDS_target->layout;
438 source = &SDDS_source->layout;
439 SDDS_DeferSavingLayout(SDDS_target, 1);
440 for (i = 0; i < source->n_columns; i++)
441 if ((index = SDDS_GetColumnIndex(SDDS_target, source->column_definition[i].name)) >= 0) {
442 /* already exists */
443 if (mode & SDDS_TRANSFER_KEEPOLD)
444 continue;
445 if (!(mode & SDDS_TRANSFER_OVERWRITE)) {
446 sprintf(messBuffer, "Unable to define column %s---already exists (SDDS_TransferAllColumnDefinitions)", source->column_definition[i].name);
447 SDDS_SetError(messBuffer);
448 SDDS_DeferSavingLayout(SDDS_target, 0);
449 return 0;
450 }
451 if (source->column_definition[i].type != target->column_definition[index].type && SDDS_target->n_rows_allocated) {
452 sprintf(messBuffer, "Unable to define column %s---type mismatch and table already allocated (SDDS_TransferAllColumnDefinitions)", source->column_definition[i].name);
453 SDDS_SetError(messBuffer);
454 SDDS_DeferSavingLayout(SDDS_target, 0);
455 return 0;
456 }
457 if (!SDDS_ChangeColumnInformation(SDDS_target, "symbol",
458 &source->column_definition[i].symbol,
459 SDDS_BY_INDEX, index) ||
460 !SDDS_ChangeColumnInformation(SDDS_target, "units",
461 &source->column_definition[i].units,
462 SDDS_BY_INDEX, index) ||
463 !SDDS_ChangeColumnInformation(SDDS_target, "description",
464 &source->column_definition[i].description,
465 SDDS_BY_INDEX, index) ||
466 !SDDS_ChangeColumnInformation(SDDS_target, "format_string",
467 &source->column_definition[i].format_string,
468 SDDS_BY_INDEX, index) ||
469 !SDDS_ChangeColumnInformation(SDDS_target, "type", &source->column_definition[i].type, SDDS_BY_INDEX, index) || !SDDS_ChangeColumnInformation(SDDS_target, "field_length", &source->column_definition[i].field_length, SDDS_BY_INDEX, index)) {
470 SDDS_SetError("Unable to define column---problem with overwrite (SDDS_TransferAllColumnDefinitions)");
471 SDDS_DeferSavingLayout(SDDS_target, 0);
472 return 0;
473 }
474 target->column_definition[index].definition_mode = source->column_definition[index].definition_mode;
475 if (target->column_definition[index].type == SDDS_STRING)
476 target->column_definition[index].memory_number = SDDS_CreateRpnMemory(source->column_definition[i].name, 1);
477 else
478 target->column_definition[index].memory_number = SDDS_CreateRpnMemory(source->column_definition[i].name, 0);
479 } else {
480 if (SDDS_DefineColumn(SDDS_target, source->column_definition[i].name, source->column_definition[i].symbol,
481 source->column_definition[i].units, source->column_definition[i].description, source->column_definition[i].format_string, source->column_definition[i].type, source->column_definition[i].field_length) < 0) {
482 SDDS_SetError("Unable to define column (SDDS_TransferAllColumnDefinitions)");
483 SDDS_DeferSavingLayout(SDDS_target, 0);
484 return 0;
485 }
486 }
487 SDDS_DeferSavingLayout(SDDS_target, 0);
488 return 1;
489}

◆ SDDS_TransferAllParameterDefinitions()

epicsShareFuncSDDS int32_t SDDS_TransferAllParameterDefinitions ( SDDS_DATASET * SDDS_target,
SDDS_DATASET * SDDS_source,
uint32_t mode )
extern

Transfers all parameter definitions from a source dataset to a target dataset.

This function defines all parameters in the target SDDS dataset to match the parameter definitions in the source SDDS dataset. It handles existing parameters based on the specified mode.

Parameters
SDDS_targetPointer to the SDDS_DATASET structure representing the target dataset.
SDDS_sourcePointer to the SDDS_DATASET structure representing the source dataset.
modeFlags that determine how to handle existing parameters. Valid flags include:
  • 0: Error if a parameter already exists in the target dataset.
  • SDDS_TRANSFER_KEEPOLD: Retain existing parameters in the target dataset and skip transferring conflicting parameters.
  • SDDS_TRANSFER_OVERWRITE: Overwrite existing parameters in the target dataset with definitions from the source dataset.
Returns
1 on success; 0 on failure. On failure, an error message is recorded.

Definition at line 343 of file SDDS_transfer.c.

343 {
344 SDDS_LAYOUT *target, *source;
345 int32_t i, index;
346 char messBuffer[1024];
347
348 if (!SDDS_CheckDataset(SDDS_target, "SDDS_TransferAllParameterDefinitions"))
349 return (0);
350 if (!SDDS_CheckDataset(SDDS_source, "SDDS_TransferAllParameterDefinitions"))
351 return (0);
352 if (mode & SDDS_TRANSFER_KEEPOLD && mode & SDDS_TRANSFER_OVERWRITE) {
353 SDDS_SetError("Inconsistent mode flags (SDDS_TransferAllParameterDefinitions)");
354 return 0;
355 }
356 target = &SDDS_target->layout;
357 source = &SDDS_source->layout;
358 SDDS_DeferSavingLayout(SDDS_target, 1);
359 for (i = 0; i < source->n_parameters; i++) {
360 if ((index = SDDS_GetParameterIndex(SDDS_target, source->parameter_definition[i].name)) >= 0) {
361 /* already exists */
362 if (mode & SDDS_TRANSFER_KEEPOLD)
363 continue;
364 if (!(mode & SDDS_TRANSFER_OVERWRITE)) {
365 sprintf(messBuffer, "Unable to define parameter %s---already exists (SDDS_TransferAllParameterDefinitions)", source->parameter_definition[i].name);
366 SDDS_SetError(messBuffer);
367 SDDS_DeferSavingLayout(SDDS_target, 0);
368 return 0;
369 }
370 if (!SDDS_ChangeParameterInformation(SDDS_target, "symbol",
371 &source->parameter_definition[i].symbol,
372 SDDS_BY_INDEX, index) ||
373 !SDDS_ChangeParameterInformation(SDDS_target, "units",
374 &source->parameter_definition[i].units,
375 SDDS_BY_INDEX, index) ||
376 !SDDS_ChangeParameterInformation(SDDS_target, "description",
377 &source->parameter_definition[i].description,
378 SDDS_BY_INDEX, index) ||
379 !SDDS_ChangeParameterInformation(SDDS_target, "format_string",
380 &source->parameter_definition[i].format_string,
381 SDDS_BY_INDEX, index) ||
382 !SDDS_ChangeParameterInformation(SDDS_target, "type",
383 &source->parameter_definition[i].type, SDDS_BY_INDEX, index) ||
384 (source->parameter_definition[i].fixed_value != NULL && !SDDS_ChangeParameterInformation(SDDS_target, "fixed_value", &source->parameter_definition[i].fixed_value, SDDS_BY_INDEX, index))) {
385 SDDS_SetError("Unable to define parameter---problem with overwrite (SDDS_TransferAllParameterDefinitions)");
386 SDDS_DeferSavingLayout(SDDS_target, 0);
387 return 0;
388 }
389 if (source->parameter_definition[i].fixed_value == NULL)
390 target->parameter_definition[index].fixed_value = NULL;
391 target->parameter_definition[index].definition_mode = source->parameter_definition[index].definition_mode;
392 if (target->parameter_definition[index].type == SDDS_STRING)
393 target->parameter_definition[index].memory_number = SDDS_CreateRpnMemory(source->parameter_definition[i].name, 1);
394 else
395 target->parameter_definition[index].memory_number = SDDS_CreateRpnMemory(source->parameter_definition[i].name, 0);
396 } else {
397 if (SDDS_DefineParameter(SDDS_target, source->parameter_definition[i].name,
398 source->parameter_definition[i].symbol, source->parameter_definition[i].units, source->parameter_definition[i].description, source->parameter_definition[i].format_string, source->parameter_definition[i].type, source->parameter_definition[i].fixed_value) < 0) {
399 SDDS_SetError("Unable to define parameter (SDDS_TransferAllParameterDefinitions)");
400 SDDS_DeferSavingLayout(SDDS_target, 0);
401 return 0;
402 }
403 }
404 }
405 SDDS_DeferSavingLayout(SDDS_target, 0);
406 return 1;
407}

◆ SDDS_TransferArrayDefinition()

epicsShareFuncSDDS int32_t SDDS_TransferArrayDefinition ( SDDS_DATASET * target,
SDDS_DATASET * source,
char * name,
char * newName )
extern

Transfers an array definition from a source dataset to a target dataset.

This function defines an array in the target SDDS dataset to match the definition of an array in the source SDDS dataset.

Parameters
targetPointer to the SDDS_DATASET structure representing the target dataset.
sourcePointer to the SDDS_DATASET structure representing the source dataset.
nameThe name of the array in the source dataset to be transferred.
newNameThe name of the array in the target dataset. If NULL, the original name is used.
Returns
1 on success; 0 on failure. On failure, an error message is recorded.

Definition at line 111 of file SDDS_transfer.c.

111 {
112 ARRAY_DEFINITION *ardef;
113
114 if (!name || SDDS_StringIsBlank(name)) {
115 SDDS_SetError("Unable to transfer array definition--NULL or blank name passed (SDDS_TransferArrayDefinition)");
116 return 0;
117 }
118 if (!newName)
119 newName = name;
120 if (!(ardef = SDDS_GetArrayDefinition(source, name))) {
121 SDDS_SetError("Unable to transfer array definition--unknown array named (SDDS_TransferArrayDefinition)");
122 return 0;
123 }
124 if (SDDS_GetArrayIndex(target, newName) >= 0) {
125 SDDS_SetError("Unable to transfer array definition--array already present (SDDS_TransferArrayDefinition)");
126 return 0;
127 }
128 if (SDDS_DefineArray(target, newName, ardef->symbol, ardef->units, ardef->description, ardef->format_string, ardef->type, ardef->field_length, ardef->dimensions, ardef->group_name) < 0) {
130 SDDS_SetError("Unable to transfer array definition--call to define array failed (SDDS_TransferArrayDefinition)");
131 return 0;
132 }
134 return 1;
135}

◆ SDDS_TransferAssociateDefinition()

epicsShareFuncSDDS int32_t SDDS_TransferAssociateDefinition ( SDDS_DATASET * target,
SDDS_DATASET * source,
char * name,
char * newName )
extern

Transfers an associate definition from a source dataset to a target dataset.

This function defines an associate in the target SDDS dataset to match the definition of an associate in the source SDDS dataset.

Parameters
targetPointer to the SDDS_DATASET structure representing the target dataset.
sourcePointer to the SDDS_DATASET structure representing the source dataset.
nameThe name of the associate in the source dataset to be transferred.
newNameThe name of the associate in the target dataset. If NULL, the original name is used.
Returns
1 on success; 0 on failure. On failure, an error message is recorded.

Definition at line 149 of file SDDS_transfer.c.

149 {
151
152 if (!name || SDDS_StringIsBlank(name)) {
153 SDDS_SetError("Unable to transfer associate definition--NULL or blank name passed (SDDS_TransferAssociateDefinition)");
154 return 0;
155 }
156 if (!newName)
157 newName = name;
158 if ((asdef = SDDS_GetAssociateDefinition(target, name))) {
160 SDDS_SetError("Unable to transfer associate definition--associate already present (SDDS_TransferAssociateDefinition)");
161 return 0;
162 }
163 if (!(asdef = SDDS_GetAssociateDefinition(source, newName))) {
164 SDDS_SetError("Unable to transfer associate definition--unknown associate named (SDDS_TransferAssociateDefinition)");
165 return 0;
166 }
167 if (SDDS_DefineAssociate(target, newName, asdef->filename, asdef->path, asdef->description, asdef->contents, asdef->sdds) < 0) {
169 SDDS_SetError("Unable to transfer associate definition--call to define associate failed (SDDS_TransferAssociateDefinition)");
170 return 0;
171 }
173 return 1;
174}
ASSOCIATE_DEFINITION * SDDS_GetAssociateDefinition(SDDS_DATASET *SDDS_dataset, char *name)
Retrieves the definition of a specified associate from the SDDS dataset.
Definition SDDS_utils.c:949
int32_t SDDS_FreeAssociateDefinition(ASSOCIATE_DEFINITION *source)
Frees memory allocated for an associate definition.

◆ SDDS_TransferColumnDefinition()

epicsShareFuncSDDS int32_t SDDS_TransferColumnDefinition ( SDDS_DATASET * target,
SDDS_DATASET * source,
char * name,
char * newName )
extern

Transfers a column definition from a source dataset to a target dataset.

This function defines a column in the target SDDS dataset to match the definition of a column in the source SDDS dataset.

Parameters
targetPointer to the SDDS_DATASET structure representing the target dataset.
sourcePointer to the SDDS_DATASET structure representing the source dataset.
nameThe name of the column in the source dataset to be transferred.
newNameThe name of the column in the target dataset. If NULL, the original name is used.
Returns
1 on success; 0 on failure. On failure, an error message is recorded.

Definition at line 35 of file SDDS_transfer.c.

35 {
36 COLUMN_DEFINITION *coldef;
37
38 if (!name || SDDS_StringIsBlank(name)) {
39 SDDS_SetError("Unable to transfer column definition--NULL or blank name passed (SDDS_TransferColumnDefinition)");
40 return 0;
41 }
42 if (!newName)
43 newName = name;
44 if (!(coldef = SDDS_GetColumnDefinition(source, name))) {
45 SDDS_SetError("Unable to transfer column definition--unknown column named (SDDS_TransferColumnDefinition)");
46 return 0;
47 }
48 if (SDDS_GetColumnIndex(target, newName) >= 0) {
49 SDDS_SetError("Unable to transfer column definition--column already present (SDDS_TransferColumnDefinition)");
50 return 0;
51 }
52 if (SDDS_DefineColumn(target, newName, coldef->symbol, coldef->units, coldef->description, coldef->format_string, coldef->type, coldef->field_length) < 0) {
54 SDDS_SetError("Unable to transfer column definition--call to define column failed (SDDS_TransferColumnDefinition)");
55 return 0;
56 }
58 return 1;
59}

◆ SDDS_TransferParameterDefinition()

epicsShareFuncSDDS int32_t SDDS_TransferParameterDefinition ( SDDS_DATASET * target,
SDDS_DATASET * source,
char * name,
char * newName )
extern

Transfers a parameter definition from a source dataset to a target dataset.

This function defines a parameter in the target SDDS dataset to match the definition of a parameter in the source SDDS dataset.

Parameters
targetPointer to the SDDS_DATASET structure representing the target dataset.
sourcePointer to the SDDS_DATASET structure representing the source dataset.
nameThe name of the parameter in the source dataset to be transferred.
newNameThe name of the parameter in the target dataset. If NULL, the original name is used.
Returns
1 on success; 0 on failure. On failure, an error message is recorded.

Definition at line 73 of file SDDS_transfer.c.

73 {
75
76 if (!name || SDDS_StringIsBlank(name)) {
77 SDDS_SetError("Unable to transfer parameter definition--NULL or blank name passed (SDDS_TransferParameterDefinition)");
78 return 0;
79 }
80 if (!newName)
81 newName = name;
82 if (!(pardef = SDDS_GetParameterDefinition(source, name))) {
83 SDDS_SetError("Unable to transfer parameter definition--unknown parameter named (SDDS_TransferParameterDefinition)");
84 return 0;
85 }
86 if (SDDS_GetParameterIndex(target, newName) >= 0) {
87 SDDS_SetError("Unable to transfer parameter definition--parameter already present (SDDS_TransferParameterDefinition)");
88 return 0;
89 }
90 if (SDDS_DefineParameter(target, newName, pardef->symbol, pardef->units, pardef->description, pardef->format_string, pardef->type, NULL) < 0) {
92 SDDS_SetError("Unable to transfer parameter definition--call to define parameter failed (SDDS_TransferParameterDefinition)");
93 return 0;
94 }
96 return 1;
97}

◆ SDDS_UnescapeQuotes()

epicsShareFuncSDDS void SDDS_UnescapeQuotes ( char * s,
char quote_char )
extern

Removes escape characters from quote characters within a string.

This function scans the input string s and removes backslashes (\) that precede the specified quote_char, effectively unescaping the quotes. This is useful for processing strings that have been prepared with escaped quotes.

Parameters
[in,out]sPointer to the string in which quotes will be unescaped. The string will be modified in place.
[in]quote_charThe quote character to unescape (e.g., ").
Note
The function modifies the string s by shifting characters to remove the escape backslashes. It assumes that s is properly null-terminated.
See also
SDDS_EscapeQuotes

Definition at line 1998 of file SDDS_utils.c.

1998 {
1999 char *ptr;
2000 ptr = s;
2001 while (*ptr) {
2002 if (*ptr == quote_char && ptr != s && *(ptr - 1) == '\\')
2003 strcpy(ptr - 1, ptr);
2004 else
2005 ptr++;
2006 }
2007}

◆ SDDS_UpdatePage()

epicsShareFuncSDDS int32_t SDDS_UpdatePage ( SDDS_DATASET * SDDS_dataset,
uint32_t mode )
extern

Updates the current page of the SDDS dataset.

This function finalizes and writes the current page of the SDDS dataset based on the specified mode. The mode can be either FLUSH_TABLE, indicating that the current page is complete and should be written to disk, or 0 for other update operations. Depending on the data mode (ASCII or Binary), the function delegates the update process to the appropriate handler.

Parameters
[in,out]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
[in]modeThe update mode, which can be:
  • FLUSH_TABLE: Indicates that the current page is complete and should be written to disk.
  • 0: Represents a standard update without flushing the table.
Returns
  • 1 on successful update of the current page.
  • 0 if an error occurred during the update process. An error message is set internally in this case.
Precondition
  • The dataset must be initialized and configured for output.
  • A page must have been started before calling this function.
Postcondition
  • The current page is updated and, if specified, written to the output file.
  • The dataset state is synchronized with the file to ensure data integrity.
Note
  • The function supports parallel I/O modes if enabled.
  • The FLUSH_TABLE mode ensures that all buffered data is written to the disk, which can be useful for data integrity.
Warning
  • Attempting to update a page without starting one will result in an error.
  • Concurrent access to the dataset while updating pages may lead to undefined behavior.

Definition at line 1292 of file SDDS_output.c.

1292 {
1293 int32_t result;
1294 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_UpdatePage"))
1295 return 0;
1296 if (SDDS_dataset->layout.disconnected) {
1297 SDDS_SetError("Can't write page--file is disconnected (SDDS_UpdatePage)");
1298 return 0;
1299 }
1300 if (SDDS_dataset->page_started == 0) {
1301 SDDS_SetError("Can't update page--no page started (SDDS_UpdatePage)");
1302 return 0;
1303 }
1304 if (SDDS_dataset->layout.data_mode.mode == SDDS_ASCII)
1305 result = SDDS_UpdateAsciiPage(SDDS_dataset, mode);
1306 else if (SDDS_dataset->layout.data_mode.mode == SDDS_BINARY)
1307 result = SDDS_UpdateBinaryPage(SDDS_dataset, mode);
1308 else {
1309 SDDS_SetError("Unable to update page--unknown data mode (SDDS_UpdatePage)");
1310 return 0;
1311 }
1312 if (result == 1)
1313 if (SDDS_SyncDataSet(SDDS_dataset) != 0)
1314 return 0;
1315 return (result);
1316}
int32_t SDDS_UpdateAsciiPage(SDDS_DATASET *SDDS_dataset, uint32_t mode)
Updates the current ASCII page of an SDDS dataset with new data.
int32_t SDDS_UpdateBinaryPage(SDDS_DATASET *SDDS_dataset, uint32_t mode)
Updates the binary page of an SDDS dataset.
int32_t SDDS_SyncDataSet(SDDS_DATASET *SDDS_dataset)
Synchronizes the SDDS dataset with the disk by flushing buffered data.

◆ SDDS_UpdateRowCount()

epicsShareFuncSDDS int32_t SDDS_UpdateRowCount ( SDDS_DATASET * SDDS_dataset)
extern

Updates the row count in the SDDS file for fixed row count mode.

Parameters
SDDS_datasetThe SDDS dataset to update.
Returns
1 on success, 0 on error.

Definition at line 1727 of file SDDS_input.c.

1727 {
1728 FILE *fp;
1729 SDDS_FILEBUFFER *fBuffer;
1730 int64_t offset, rows;
1731 int32_t rows32;
1732 char *outputEndianess = NULL;
1733
1734 if ((SDDS_dataset->layout.gzipFile) || (SDDS_dataset->layout.lzmaFile))
1735 return (1);
1736 if (!(fp = SDDS_dataset->layout.fp)) {
1737 SDDS_SetError("Unable to update page--file pointer is NULL (SDDS_UpdateRowCount)");
1738 return (0);
1739 }
1740#if DEBUG
1741 fprintf(stderr, "Updating rowcount in file %s with pointer %p\n", SDDS_dataset->layout.filename ? SDDS_dataset->layout.filename : "NULL", fp);
1742#endif
1743 fBuffer = &SDDS_dataset->fBuffer;
1744 if (!SDDS_FlushBuffer(fp, fBuffer)) {
1745 SDDS_SetError("Unable to write page--buffer flushing problem (SDDS_UpdateRowCount)");
1746 return (0);
1747 }
1748 offset = ftell(fp);
1749 if (SDDS_fseek(fp, SDDS_dataset->rowcount_offset, 0) == -1) {
1750 SDDS_SetError("Unable to update page--failure doing fseek (SDDS_UpdateRowCount)");
1751 return (0);
1752 }
1753 rows = SDDS_CountRowsOfInterest(SDDS_dataset) + SDDS_dataset->first_row_in_mem;
1754 if (SDDS_dataset->layout.data_mode.mode == SDDS_ASCII) {
1755 fprintf(fp, "%20" PRId64 "\n", rows);
1756 } else {
1757
1758 if (rows > INT32_MAX) {
1759 // Don't go over this limit because it has a different format
1760 SDDS_SetError("Unable to update page--failure writing number of rows (SDDS_UpdateRowCount)");
1761 return (0);
1762 }
1763 rows32 = (int32_t)rows;
1764 if ((outputEndianess = getenv("SDDS_OUTPUT_ENDIANESS"))) {
1765 if (((strncmp(outputEndianess, "big", 3) == 0) && (SDDS_IsBigEndianMachine() == 0)) || ((strncmp(outputEndianess, "little", 6) == 0) && (SDDS_IsBigEndianMachine() == 1)))
1766 SDDS_SwapLong(&rows32);
1767 }
1768 if (fwrite(&rows32, sizeof(rows32), 1, fp) != 1) {
1769 SDDS_SetError("Unable to update page--failure writing number of rows (SDDS_UpdateRowCount)");
1770 return (0);
1771 }
1772 }
1773 if (SDDS_fseek(fp, offset, 0) == -1) {
1774 SDDS_SetError("Unable to update page--failure doing fseek to end of page (SDDS_UpdateRowCount)");
1775 return (0);
1776 }
1777 return (1);
1778}
int32_t SDDS_FlushBuffer(FILE *fp, SDDS_FILEBUFFER *fBuffer)
int32_t SDDS_fseek(FILE *fp, int64_t offset, int32_t dir)
Sets the file position indicator for a given file stream with retry logic.

◆ SDDS_VerifyArrayExists()

epicsShareFuncSDDS int32_t SDDS_VerifyArrayExists ( SDDS_DATASET * SDDS_dataset,
int32_t mode,
... )
extern

Verifies the existence of an array in the SDDS dataset based on specified criteria.

This function searches for an array within the SDDS dataset that matches the given criteria defined by the mode. It returns the index of the first matching array or -1 if no match is found.

The function supports the following modes:

  • FIND_SPECIFIED_TYPE:
    • Parameters: int32_t type, char *name
    • Description: Finds the first array with the specified type.
  • FIND_ANY_TYPE:
    • Parameters: char *name
    • Description: Finds the first array with any type.
  • FIND_NUMERIC_TYPE:
    • Parameters: char *name
    • Description: Finds the first array with a numeric type.
  • FIND_FLOATING_TYPE:
    • Parameters: char *name
    • Description: Finds the first array with a floating type.
  • FIND_INTEGER_TYPE:
    • Parameters: char *name
    • Description: Finds the first array with an integer type.
Parameters
[in]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset to be searched.
[in]modeSpecifies the mode for matching arrays. Valid modes are:
  • FIND_SPECIFIED_TYPE
  • FIND_ANY_TYPE
  • FIND_NUMERIC_TYPE
  • FIND_FLOATING_TYPE
  • FIND_INTEGER_TYPE
[in]...Variable arguments depending on mode:
  • FIND_SPECIFIED_TYPE: int32_t type, followed by char *name
  • Other Modes: char *name
Returns
  • Returns the index (int32_t) of the first matched array.
  • Returns -1 if no matching array is found.
Note
  • The caller must ensure that the variable arguments match the expected parameters for the specified mode.
Warning
  • Passing incorrect types or mismatched arguments may lead to undefined behavior.
See also
SDDS_GetArrayIndex, SDDS_CheckArray, SDDS_MatchArrays

Definition at line 5435 of file SDDS_utils.c.

5435 {
5436 int32_t index, type, thisType;
5437 va_list argptr;
5438 char *name;
5439
5440 va_start(argptr, mode);
5441 type = 0;
5442
5443 if (mode == FIND_SPECIFIED_TYPE)
5444 type = va_arg(argptr, int32_t);
5445 name = va_arg(argptr, char *);
5446 if ((index = SDDS_GetArrayIndex(SDDS_dataset, name)) >= 0) {
5447 thisType = SDDS_GetArrayType(SDDS_dataset, index);
5448 if (mode == FIND_ANY_TYPE || (mode == FIND_SPECIFIED_TYPE && thisType == type) || (mode == FIND_NUMERIC_TYPE && SDDS_NUMERIC_TYPE(thisType)) || (mode == FIND_FLOATING_TYPE && SDDS_FLOATING_TYPE(thisType)) || (mode == FIND_INTEGER_TYPE && SDDS_INTEGER_TYPE(thisType))) {
5449 va_end(argptr);
5450 return (index);
5451 }
5452 }
5453 va_end(argptr);
5454 return (-1);
5455}

◆ SDDS_VerifyColumnExists()

epicsShareFuncSDDS int32_t SDDS_VerifyColumnExists ( SDDS_DATASET * SDDS_dataset,
int32_t mode,
... )
extern

Verifies the existence of a column in the SDDS dataset based on specified criteria.

This function searches for a column within the SDDS dataset that matches the given criteria defined by the mode. It returns the index of the first matching column or -1 if no match is found.

The function supports the following modes:

  • FIND_SPECIFIED_TYPE:
    • Parameters: int32_t type, char *name
    • Description: Finds the first column with the specified type.
  • FIND_ANY_TYPE:
    • Parameters: char *name
    • Description: Finds the first column with any type.
  • FIND_NUMERIC_TYPE:
    • Parameters: char *name
    • Description: Finds the first column with a numeric type.
  • FIND_FLOATING_TYPE:
    • Parameters: char *name
    • Description: Finds the first column with a floating type.
  • FIND_INTEGER_TYPE:
    • Parameters: char *name
    • Description: Finds the first column with an integer type.
Parameters
[in]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset to be searched.
[in]modeSpecifies the mode for matching columns. Valid modes are:
  • FIND_SPECIFIED_TYPE
  • FIND_ANY_TYPE
  • FIND_NUMERIC_TYPE
  • FIND_FLOATING_TYPE
  • FIND_INTEGER_TYPE
[in]...Variable arguments depending on mode:
  • FIND_SPECIFIED_TYPE: int32_t type, followed by char *name
  • Other Modes: char *name
Returns
  • Returns the index (int32_t) of the first matched column.
  • Returns -1 if no matching column is found.
Note
  • The caller must ensure that the variable arguments match the expected parameters for the specified mode.
Warning
  • Passing incorrect types or mismatched arguments may lead to undefined behavior.
See also
SDDS_GetColumnIndex, SDDS_CheckColumn, SDDS_MatchColumns

Definition at line 5511 of file SDDS_utils.c.

5511 {
5512 int32_t index;
5513 int32_t type, thisType;
5514 va_list argptr;
5515 char *name;
5516
5517 va_start(argptr, mode);
5518 type = 0;
5519
5520 if (mode == FIND_SPECIFIED_TYPE)
5521 type = va_arg(argptr, int32_t);
5522 name = va_arg(argptr, char *);
5523 if ((index = SDDS_GetColumnIndex(SDDS_dataset, name)) >= 0) {
5524 thisType = SDDS_GetColumnType(SDDS_dataset, index);
5525 if (mode == FIND_ANY_TYPE || (mode == FIND_SPECIFIED_TYPE && thisType == type) || (mode == FIND_NUMERIC_TYPE && SDDS_NUMERIC_TYPE(thisType)) || (mode == FIND_FLOATING_TYPE && SDDS_FLOATING_TYPE(thisType)) || (mode == FIND_INTEGER_TYPE && SDDS_INTEGER_TYPE(thisType))) {
5526 va_end(argptr);
5527 return (index);
5528 }
5529 }
5530 va_end(argptr);
5531 return (-1);
5532}

◆ SDDS_VerifyParameterExists()

epicsShareFuncSDDS int32_t SDDS_VerifyParameterExists ( SDDS_DATASET * SDDS_dataset,
int32_t mode,
... )
extern

Verifies the existence of a parameter in the SDDS dataset based on specified criteria.

This function searches for a parameter within the SDDS dataset that matches the given criteria defined by the mode. It returns the index of the first matching parameter or -1 if no match is found.

The function supports the following modes:

  • FIND_SPECIFIED_TYPE:
    • Parameters: int32_t type, char *name
    • Description: Finds the first parameter with the specified type.
  • FIND_ANY_TYPE:
    • Parameters: char *name
    • Description: Finds the first parameter with any type.
  • FIND_NUMERIC_TYPE:
    • Parameters: char *name
    • Description: Finds the first parameter with a numeric type.
  • FIND_FLOATING_TYPE:
    • Parameters: char *name
    • Description: Finds the first parameter with a floating type.
  • FIND_INTEGER_TYPE:
    • Parameters: char *name
    • Description: Finds the first parameter with an integer type.
Parameters
[in]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset to be searched.
[in]modeSpecifies the mode for matching parameters. Valid modes are:
  • FIND_SPECIFIED_TYPE
  • FIND_ANY_TYPE
  • FIND_NUMERIC_TYPE
  • FIND_FLOATING_TYPE
  • FIND_INTEGER_TYPE
[in]...Variable arguments depending on mode:
  • FIND_SPECIFIED_TYPE: int32_t type, followed by char *name
  • Other Modes: char *name
Returns
  • Returns the index (int32_t) of the first matched parameter.
  • Returns -1 if no matching parameter is found.
Note
  • The caller must ensure that the variable arguments match the expected parameters for the specified mode.
Warning
  • Passing incorrect types or mismatched arguments may lead to undefined behavior.
See also
SDDS_GetParameterIndex, SDDS_CheckParameter, SDDS_MatchParameters

Definition at line 5588 of file SDDS_utils.c.

5588 {
5589 int32_t index, type, thisType;
5590 va_list argptr;
5591 char *name;
5592
5593 va_start(argptr, mode);
5594 type = 0;
5595
5596 if (mode == FIND_SPECIFIED_TYPE)
5597 type = va_arg(argptr, int32_t);
5598 name = va_arg(argptr, char *);
5599 if ((index = SDDS_GetParameterIndex(SDDS_dataset, name)) >= 0) {
5600 thisType = SDDS_GetParameterType(SDDS_dataset, index);
5601 if (mode == FIND_ANY_TYPE || (mode == FIND_SPECIFIED_TYPE && thisType == type) || (mode == FIND_NUMERIC_TYPE && SDDS_NUMERIC_TYPE(thisType)) || (mode == FIND_FLOATING_TYPE && SDDS_FLOATING_TYPE(thisType)) || (mode == FIND_INTEGER_TYPE && SDDS_INTEGER_TYPE(thisType))) {
5602 va_end(argptr);
5603 return (index);
5604 }
5605 }
5606 va_end(argptr);
5607 return (-1);
5608}

◆ SDDS_VerifyPrintfFormat()

epicsShareFuncSDDS int32_t SDDS_VerifyPrintfFormat ( const char * string,
int32_t type )
extern

Verifies that a printf format string is compatible with a specified data type.

This function checks whether the provided printf format string is appropriate for the given SDDS data type. It ensures that the format specifier matches the type, preventing potential formatting errors during data output.

Parameters
[in]stringThe printf format string to be verified.
[in]typeThe data type against which the format string is verified. Must be one of the SDDS type constants:
  • SDDS_LONGDOUBLE
  • SDDS_DOUBLE
  • SDDS_FLOAT
  • SDDS_LONG
  • SDDS_LONG64
  • SDDS_ULONG
  • SDDS_ULONG64
  • SDDS_SHORT
  • SDDS_USHORT
  • SDDS_STRING
  • SDDS_CHARACTER
Returns
Returns 1 if the format string is valid for the specified type; otherwise, returns 0 and records an error message.
Note
This function does not modify the format string; it only validates its compatibility with the given type.
See also
SDDS_SetError

Definition at line 816 of file SDDS_utils.c.

816 {
817 char *percent, *s;
818 int32_t len, tmp;
819
820 s = (char *)string;
821 do {
822 if ((percent = strchr(s, '%'))) {
823 if (*(percent + 1) != '%')
824 break;
825 s = percent + 1;
826 }
827 } while (percent);
828 if (!percent || !*++percent)
829 return (0);
830
831 s = percent;
832
833 switch (type) {
834 case SDDS_LONGDOUBLE:
835 case SDDS_DOUBLE:
836 case SDDS_FLOAT:
837 if ((len = strcspn(s, "fegEG")) == strlen(s))
838 return (0);
839 if (len == 0)
840 return (1);
841 if ((tmp = strspn(s, "-+.0123456789 ")) < len)
842 return (0);
843 break;
844 case SDDS_LONG:
845 case SDDS_LONG64:
846 if ((len = strcspn(s, "d")) == strlen(s))
847 return (0);
848 /* if (*(s+len-1)!='l')
849 return(0); */
850 if (--len == 0)
851 return (1);
852 if ((tmp = strspn(s, "-+.0123456789 ")) < len)
853 return (0);
854 break;
855 case SDDS_ULONG:
856 case SDDS_ULONG64:
857 if ((len = strcspn(s, "u")) == strlen(s))
858 return (0);
859 /* if (*(s+len-1)!='l')
860 return(0); */
861 if (--len == 0)
862 return (1);
863 if ((tmp = strspn(s, "-+.0123456789 ")) < len)
864 return (0);
865 break;
866 case SDDS_SHORT:
867 if ((len = strcspn(s, "d")) == strlen(s))
868 return (0);
869 if (*(s + len - 1) != 'h')
870 return (0);
871 if (--len == 0)
872 return (1);
873 if ((tmp = strspn(s, "-+.0123456789 ")) < len)
874 return (0);
875 break;
876 case SDDS_USHORT:
877 if ((len = strcspn(s, "u")) == strlen(s))
878 return (0);
879 if (*(s + len - 1) != 'h')
880 return (0);
881 if (--len == 0)
882 return (1);
883 if ((tmp = strspn(s, "-+.0123456789 ")) < len)
884 return (0);
885 break;
886 case SDDS_STRING:
887 if ((len = strcspn(s, "s")) == strlen(s))
888 return (0);
889 if (len == 0)
890 return (1);
891 if ((tmp = strspn(s, "-0123456789")) < len)
892 return (0);
893 break;
894 case SDDS_CHARACTER:
895 if ((len = strcspn(s, "c")) == strlen(s))
896 return (0);
897 if (len != 0)
898 return (0);
899 break;
900 default:
901 return (0);
902 }
903 /* no errors found--its probably okay */
904 return (1);
905}

◆ SDDS_Warning()

epicsShareFuncSDDS void SDDS_Warning ( char * message)
extern

Prints a warning message to stderr.

This function outputs a warning message to the specified FILE stream, typically stderr. If a program name has been registered using SDDS_RegisterProgramName, it is included in the warning message.

Parameters
[in]messageThe warning message to be printed. If NULL, a default message "?" is used.
Note
This function does not record the warning as an error; it only prints the message.
See also
SDDS_RegisterProgramName

Definition at line 402 of file SDDS_utils.c.

402 {
403 char *programName = SDDS_GetRegisteredProgramNameCopy();
404 if (programName)
405 fprintf(stderr, "Warning (%s): %s\n", programName, message ? message : "?");
406 else
407 fprintf(stderr, "Warning: %s\n", message ? message : "?");
408 free(programName);
409}

◆ SDDS_WriteBinaryString()

epicsShareFuncSDDS int32_t SDDS_WriteBinaryString ( char * string,
FILE * fp,
SDDS_FILEBUFFER * fBuffer )
extern

Writes a binary string to a file with buffering.

This function writes a binary string to the specified file by first writing the length of the string followed by the string's content to ensure proper binary formatting. If the input string is NULL, an empty string is written instead. The writing operation utilizes a buffered approach to enhance performance.

Parameters
[in]stringThe null-terminated string to be written. If NULL, an empty string is written.
[in]fpThe file pointer to write to. Must be an open file in binary write mode.
[in,out]fBufferPointer to the file buffer used for buffered writing operations.
Returns
int32_t Returns 1 on success, 0 on failure.
Return values
1Operation was successful.
0An error occurred during writing.

Definition at line 2642 of file SDDS_binary.c.

2642 {
2643 int32_t length;
2644 static const char dummy_string[] = "";
2645 if (!string)
2646 string = (char *)dummy_string;
2647 length = strlen(string);
2648 if (!SDDS_BufferedWrite(&length, sizeof(length), fp, fBuffer)) {
2649 SDDS_SetError("Unable to write string--error writing length");
2650 return (0);
2651 }
2652 if (length && !SDDS_BufferedWrite(string, sizeof(*string) * length, fp, fBuffer)) {
2653 SDDS_SetError("Unable to write string--error writing contents");
2654 return (0);
2655 }
2656 return (1);
2657}
int32_t SDDS_BufferedWrite(void *target, int64_t targetSize, FILE *fp, SDDS_FILEBUFFER *fBuffer)

◆ SDDS_WriteLayout()

epicsShareFuncSDDS int32_t SDDS_WriteLayout ( SDDS_DATASET * SDDS_dataset)
extern

Writes the SDDS layout header to the output file.

This function serializes and writes the layout information of the SDDS dataset to the output file. The layout defines the structure of the data tables, including parameters, arrays, columns, and associates. The function handles different file types, including standard, gzip-compressed, and LZMA-compressed files, and ensures that the layout is written in the correct byte order and format based on the dataset's configuration.

Parameters
[in,out]SDDS_datasetPointer to the SDDS_DATASET structure whose layout is to be written.
Returns
  • 1 on successful writing of the layout.
  • 0 if an error occurred during the writing process. An internal error message is set in this case.
Precondition
  • The dataset must be initialized and configured for output.
  • The layout must have been saved internally using SDDS_SaveLayout before calling this function.
  • The dataset must not be disconnected from the output file.
  • The layout must not have been previously written to the file.
Postcondition
  • The layout header is written to the output file in the appropriate format.
  • The dataset's internal state is updated to reflect that the layout has been written.
Note
  • The function automatically determines the layout version based on the data types used in parameters, arrays, and columns.
  • Environment variable SDDS_OUTPUT_ENDIANESS can influence the byte order declared in the layout.
  • The function handles both binary and ASCII modes, adjusting the layout accordingly.
Warning
  • Attempting to write the layout after it has already been written will result in an error.
  • The function does not support writing layouts to disconnected files.
  • Ensure that the output file is properly opened and writable before calling this function.

Definition at line 900 of file SDDS_output.c.

900 {
901 SDDS_LAYOUT *layout;
902#if defined(zLib)
903 gzFile gzfp;
904#endif
905 FILE *fp;
906 struct lzmafile *lzmafp;
907 int64_t i;
908 char *outputEndianess = NULL;
909
910#if SDDS_MPI_IO
911 if (SDDS_dataset->parallel_io)
912 return SDDS_MPI_WriteLayout(SDDS_dataset);
913#endif
914 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_WriteLayout"))
915 return 0;
916
917 if (!SDDS_SaveLayout(SDDS_dataset))
918 return 0;
919
920 layout = &SDDS_dataset->layout;
921
922 if (SDDS_dataset->layout.disconnected) {
923 SDDS_SetError("Can't write layout--file is disconnected (SDDS_WriteLayout)");
924 return 0;
925 }
926
927 if (layout->layout_written) {
928 SDDS_SetError("Can't write layout--already written to file (SDDS_WriteLayout)");
929 return 0;
930 }
931
932 if ((outputEndianess = getenv("SDDS_OUTPUT_ENDIANESS"))) {
933 if (strncmp(outputEndianess, "big", 3) == 0)
934 layout->byteOrderDeclared = SDDS_BIGENDIAN;
935 else if (strncmp(outputEndianess, "little", 6) == 0)
936 layout->byteOrderDeclared = SDDS_LITTLEENDIAN;
937 }
938
939 if (!layout->byteOrderDeclared)
940 layout->byteOrderDeclared = SDDS_IsBigEndianMachine() ? SDDS_BIGENDIAN : SDDS_LITTLEENDIAN;
941
942 layout->version = 1;
943 for (i = 0; i < layout->n_parameters; i++) {
944 if ((layout->parameter_definition[i].type == SDDS_ULONG) || (layout->parameter_definition[i].type == SDDS_USHORT)) {
945 layout->version = 2;
946 break;
947 }
948 }
949 for (i = 0; i < layout->n_arrays; i++) {
950 if ((layout->array_definition[i].type == SDDS_ULONG) || (layout->array_definition[i].type == SDDS_USHORT)) {
951 layout->version = 2;
952 break;
953 }
954 }
955 for (i = 0; i < layout->n_columns; i++) {
956 if ((layout->column_definition[i].type == SDDS_ULONG) || (layout->column_definition[i].type == SDDS_USHORT)) {
957 layout->version = 2;
958 break;
959 }
960 }
961 if ((layout->data_mode.column_major) && (layout->data_mode.mode == SDDS_BINARY)) {
962 layout->version = 3;
963 }
964 for (i = 0; i < layout->n_parameters; i++) {
965 if (layout->parameter_definition[i].type == SDDS_LONGDOUBLE) {
966 layout->version = 4;
967 break;
968 }
969 }
970 for (i = 0; i < layout->n_arrays; i++) {
971 if (layout->array_definition[i].type == SDDS_LONGDOUBLE) {
972 layout->version = 4;
973 break;
974 }
975 }
976 for (i = 0; i < layout->n_columns; i++) {
977 if (layout->column_definition[i].type == SDDS_LONGDOUBLE) {
978 layout->version = 4;
979 break;
980 }
981 }
982 if ((LDBL_DIG != 18) && (layout->version == 4)) {
983 if (getenv("SDDS_LONGDOUBLE_64BITS") == NULL) {
984 SDDS_SetError("Error: Operating system does not support 80bit float variables used by SDDS_LONGDOUBLE (SDDS_WriteLayout)\nSet SDDS_LONGDOUBLE_64BITS environment variable to read old files that used 64bit float variables for SDDS_LONGDOUBLE");
985 return 0;
986 }
987 }
988 for (i = 0; i < layout->n_parameters; i++) {
989 if ((layout->parameter_definition[i].type == SDDS_ULONG64) || (layout->parameter_definition[i].type == SDDS_LONG64)) {
990 layout->version = 5;
991 break;
992 }
993 }
994 for (i = 0; i < layout->n_arrays; i++) {
995 if ((layout->array_definition[i].type == SDDS_ULONG64) || (layout->array_definition[i].type == SDDS_LONG64)) {
996 layout->version = 5;
997 break;
998 }
999 }
1000 for (i = 0; i < layout->n_columns; i++) {
1001 if ((layout->column_definition[i].type == SDDS_ULONG64) || (layout->column_definition[i].type == SDDS_LONG64)) {
1002 layout->version = 5;
1003 break;
1004 }
1005 }
1006
1007 // force layout version 5 because the row and column indexes are now 64bit long integers
1008 // layout->version = 5;
1009
1010#if defined(zLib)
1011 if (SDDS_dataset->layout.gzipFile) {
1012 if (!(gzfp = layout->gzfp)) {
1013 SDDS_SetError("Can't write SDDS layout--file pointer is NULL (SDDS_WriteLayout)");
1014 return 0;
1015 }
1016
1017 /* write out the layout data */
1018 if (!SDDS_GZipWriteVersion(layout->version, gzfp)) {
1019 SDDS_SetError("Can't write SDDS layout--error writing version (SDDS_WriteLayout)");
1020 return 0;
1021 }
1022 if (layout->version < 3) {
1023 if (SDDS_dataset->layout.data_mode.mode == SDDS_BINARY) {
1024 if (layout->byteOrderDeclared == SDDS_BIGENDIAN)
1025 gzprintf(gzfp, "!# big-endian\n");
1026 else
1027 gzprintf(gzfp, "!# little-endian\n");
1028 }
1029 if (SDDS_dataset->layout.data_mode.fixed_row_count) {
1030 gzprintf(gzfp, "!# fixed-rowcount\n");
1031 }
1032 }
1033 if (!SDDS_GZipWriteDescription(layout->description, layout->contents, gzfp)) {
1034 SDDS_SetError("Can't write SDDS layout--error writing description (SDDS_WriteLayout)");
1035 return 0;
1036 }
1037
1038 for (i = 0; i < layout->n_parameters; i++)
1039 if (!SDDS_GZipWriteParameterDefinition(layout->parameter_definition + i, gzfp)) {
1040 SDDS_SetError("Unable to write layout--error writing parameter definition (SDDS_WriteLayout)");
1041 return 0;
1042 }
1043
1044 for (i = 0; i < layout->n_arrays; i++)
1045 if (!SDDS_GZipWriteArrayDefinition(layout->array_definition + i, gzfp)) {
1046 SDDS_SetError("Unable to write layout--error writing array definition (SDDS_WriteLayout)");
1047 return 0;
1048 }
1049
1050 for (i = 0; i < layout->n_columns; i++)
1051 if (!SDDS_GZipWriteColumnDefinition(layout->column_definition + i, gzfp)) {
1052 SDDS_SetError("Unable to write layout--error writing column definition (SDDS_WriteLayout)");
1053 return 0;
1054 }
1055
1056# if RW_ASSOCIATES != 0
1057 for (i = 0; i < layout->n_associates; i++)
1058 if (!SDDS_GZipWriteAssociateDefinition(layout->associate_definition + i, gzfp)) {
1059 SDDS_SetError("Unable to write layout--error writing associated file data (SDDS_WriteLayout)");
1060 return 0;
1061 }
1062# endif
1063
1064 if (!SDDS_GZipWriteDataMode(layout, gzfp)) {
1065 SDDS_SetError("Unable to write layout--error writing data mode (SDDS_WriteLayout)");
1066 return 0;
1067 }
1068
1069 layout->layout_written = 1;
1070 /*gzflush(gzfp, Z_FULL_FLUSH); */
1071 } else {
1072#endif
1073 if (SDDS_dataset->layout.lzmaFile) {
1074 if (!(lzmafp = layout->lzmafp)) {
1075 SDDS_SetError("Can't write SDDS layout--file pointer is NULL (SDDS_WriteLayout)");
1076 return 0;
1077 }
1078
1079 /* write out the layout data */
1080 if (!SDDS_LZMAWriteVersion(layout->version, lzmafp)) {
1081 SDDS_SetError("Can't write SDDS layout--error writing version (SDDS_WriteLayout)");
1082 return 0;
1083 }
1084 if (layout->version < 3) {
1085 if (SDDS_dataset->layout.data_mode.mode == SDDS_BINARY) {
1086 if (layout->byteOrderDeclared == SDDS_BIGENDIAN)
1087 lzma_printf(lzmafp, "!# big-endian\n");
1088 else
1089 lzma_printf(lzmafp, "!# little-endian\n");
1090 }
1091 if (SDDS_dataset->layout.data_mode.fixed_row_count) {
1092 lzma_printf(lzmafp, "!# fixed-rowcount\n");
1093 }
1094 }
1095 if (!SDDS_LZMAWriteDescription(layout->description, layout->contents, lzmafp)) {
1096 SDDS_SetError("Can't write SDDS layout--error writing description (SDDS_WriteLayout)");
1097 return 0;
1098 }
1099 for (i = 0; i < layout->n_parameters; i++)
1100 if (!SDDS_LZMAWriteParameterDefinition(layout->parameter_definition + i, lzmafp)) {
1101 SDDS_SetError("Unable to write layout--error writing parameter definition (SDDS_WriteLayout)");
1102 return 0;
1103 }
1104 for (i = 0; i < layout->n_arrays; i++)
1105 if (!SDDS_LZMAWriteArrayDefinition(layout->array_definition + i, lzmafp)) {
1106 SDDS_SetError("Unable to write layout--error writing array definition (SDDS_WriteLayout)");
1107 return 0;
1108 }
1109 for (i = 0; i < layout->n_columns; i++)
1110 if (!SDDS_LZMAWriteColumnDefinition(layout->column_definition + i, lzmafp)) {
1111 SDDS_SetError("Unable to write layout--error writing column definition (SDDS_WriteLayout)");
1112 return 0;
1113 }
1114
1115#if RW_ASSOCIATES != 0
1116 for (i = 0; i < layout->n_associates; i++)
1117 if (!SDDS_LZMAWriteAssociateDefinition(layout->associate_definition + i, lzmafp)) {
1118 SDDS_SetError("Unable to write layout--error writing associated file data (SDDS_WriteLayout)");
1119 return 0;
1120 }
1121#endif
1122
1123 if (!SDDS_LZMAWriteDataMode(layout, lzmafp)) {
1124 SDDS_SetError("Unable to write layout--error writing data mode (SDDS_WriteLayout)");
1125 return 0;
1126 }
1127
1128 layout->layout_written = 1;
1129 } else {
1130
1131 if (!(fp = layout->fp)) {
1132 SDDS_SetError("Can't write SDDS layout--file pointer is NULL (SDDS_WriteLayout)");
1133 return 0;
1134 }
1135
1136 /* write out the layout data */
1137 if (!SDDS_WriteVersion(layout->version, fp)) {
1138 SDDS_SetError("Can't write SDDS layout--error writing version (SDDS_WriteLayout)");
1139 return 0;
1140 }
1141 if (layout->version < 3) {
1142 if (SDDS_dataset->layout.data_mode.mode == SDDS_BINARY) {
1143 if (layout->byteOrderDeclared == SDDS_BIGENDIAN)
1144 fprintf(fp, "!# big-endian\n");
1145 else
1146 fprintf(fp, "!# little-endian\n");
1147 }
1148 if (SDDS_dataset->layout.data_mode.fixed_row_count) {
1149 fprintf(fp, "!# fixed-rowcount\n");
1150 }
1151 }
1152 if (!SDDS_WriteDescription(layout->description, layout->contents, fp)) {
1153 SDDS_SetError("Can't write SDDS layout--error writing description (SDDS_WriteLayout)");
1154 return 0;
1155 }
1156
1157 for (i = 0; i < layout->n_parameters; i++)
1158 if (!SDDS_WriteParameterDefinition(layout->parameter_definition + i, fp)) {
1159 SDDS_SetError("Unable to write layout--error writing parameter definition (SDDS_WriteLayout)");
1160 return 0;
1161 }
1162
1163 for (i = 0; i < layout->n_arrays; i++)
1164 if (!SDDS_WriteArrayDefinition(layout->array_definition + i, fp)) {
1165 SDDS_SetError("Unable to write layout--error writing array definition (SDDS_WriteLayout)");
1166 return 0;
1167 }
1168
1169 for (i = 0; i < layout->n_columns; i++)
1170 if (!SDDS_WriteColumnDefinition(layout->column_definition + i, fp)) {
1171 SDDS_SetError("Unable to write layout--error writing column definition (SDDS_WriteLayout)");
1172 return 0;
1173 }
1174
1175#if RW_ASSOCIATES != 0
1176 for (i = 0; i < layout->n_associates; i++)
1177 if (!SDDS_WriteAssociateDefinition(layout->associate_definition + i, fp)) {
1178 SDDS_SetError("Unable to write layout--error writing associated file data (SDDS_WriteLayout)");
1179 return 0;
1180 }
1181#endif
1182
1183 if (!SDDS_WriteDataMode(layout, fp)) {
1184 SDDS_SetError("Unable to write layout--error writing data mode (SDDS_WriteLayout)");
1185 return 0;
1186 }
1187
1188 layout->layout_written = 1;
1189 fflush(fp);
1190 }
1191#if defined(zLib)
1192 }
1193#endif
1194 if (SDDS_SyncDataSet(SDDS_dataset) != 0)
1195 return 0;
1196 return (1);
1197}
int32_t SDDS_LZMAWriteVersion(int32_t version_number, struct lzmafile *lzmafp)
Writes the SDDS protocol version to an LZMA-compressed file.
Definition SDDS_write.c:77
int32_t SDDS_LZMAWriteArrayDefinition(ARRAY_DEFINITION *array_definition, struct lzmafile *lzmafp)
Writes an array definition to an LZMA-compressed file.
Definition SDDS_write.c:722
int32_t SDDS_LZMAWriteColumnDefinition(COLUMN_DEFINITION *column, struct lzmafile *lzmafp)
Writes a column definition to an LZMA-compressed file.
Definition SDDS_write.c:356
int32_t SDDS_WriteAssociateDefinition(ASSOCIATE_DEFINITION *associate, FILE *fp)
Writes an associate definition to a standard file.
Definition SDDS_write.c:493
int32_t SDDS_LZMAWriteDescription(char *description, char *contents, struct lzmafile *lzmafp)
Writes the SDDS description section to an LZMA-compressed file.
Definition SDDS_write.c:280
int32_t SDDS_WriteVersion(int32_t version_number, FILE *fp)
Writes the SDDS protocol version to a standard file.
Definition SDDS_write.c:59
int32_t SDDS_WriteColumnDefinition(COLUMN_DEFINITION *column, FILE *fp)
Writes a column definition to a standard file.
Definition SDDS_write.c:329
int32_t SDDS_LZMAWriteDataMode(SDDS_LAYOUT *layout, struct lzmafile *lzmafp)
Writes the data mode section to an LZMA-compressed file.
Definition SDDS_write.c:614
int32_t SDDS_WriteArrayDefinition(ARRAY_DEFINITION *array_definition, FILE *fp)
Writes an array definition to a standard file.
Definition SDDS_write.c:692
int32_t SDDS_LZMAWriteAssociateDefinition(ASSOCIATE_DEFINITION *associate, struct lzmafile *lzmafp)
Writes an associate definition to an LZMA-compressed file.
Definition SDDS_write.c:520
int32_t SDDS_WriteDataMode(SDDS_LAYOUT *layout, FILE *fp)
Writes the data mode section to a standard file.
Definition SDDS_write.c:576
int32_t SDDS_WriteParameterDefinition(PARAMETER_DEFINITION *parameter, FILE *fp)
Writes a parameter definition to a standard file.
Definition SDDS_write.c:411
int32_t SDDS_WriteDescription(char *description, char *contents, FILE *fp)
Writes the SDDS description section to a standard file.
Definition SDDS_write.c:256
int32_t SDDS_LZMAWriteParameterDefinition(PARAMETER_DEFINITION *parameter, struct lzmafile *lzmafp)
Writes a parameter definition to an LZMA-compressed file.
Definition SDDS_write.c:438
int32_t SDDS_MPI_WriteLayout(SDDS_DATASET *SDDS_dataset)
Writes the layout of the SDDS dataset to the MPI file.

◆ SDDS_WriteNonNativeBinaryArrays()

int32_t SDDS_WriteNonNativeBinaryArrays ( SDDS_DATASET * SDDS_dataset)

Writes non-native endian binary arrays to an SDDS dataset.

This function iterates through all array definitions in the specified SDDS dataset and writes their binary data to the underlying file. It handles various data types, including short, unsigned short, long, unsigned long, long long, unsigned long long, float, double, and long double. For string arrays, it writes each string individually, ensuring proper memory management and byte order conversion. The function supports different compression formats, including uncompressed, LZMA-compressed, and GZIP-compressed files. After writing, it swaps the endianness of the array data to match the system's native byte order.

Parameters
[in,out]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset to write to.
Returns
int32_t Returns 1 on successful writing of all arrays, or 0 if an error occurred.
Return values
1All non-native endian arrays were successfully written and byte-swapped.
0An error occurred during the write operation, such as I/O failures, memory allocation issues, or corrupted array definitions.
Note
This function modifies the dataset's array data during the write process. Ensure that the dataset is properly initialized and opened for writing before invoking this function. After writing, the dataset's state is updated to reflect the written arrays.

Definition at line 5477 of file SDDS_binary.c.

5477 {
5478 int32_t i, j, dimension, zero = 0;
5479 SDDS_LAYOUT *layout;
5480 FILE *fp;
5481 struct lzmafile *lzmafp;
5482 SDDS_FILEBUFFER *fBuffer;
5483#if defined(zLib)
5484 gzFile gzfp;
5485#endif
5486 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_WriteNonNativeBinaryArrays"))
5487 return (0);
5488 SDDS_SwapEndsArrayData(SDDS_dataset);
5489
5490 layout = &SDDS_dataset->layout;
5491 fBuffer = &SDDS_dataset->fBuffer;
5492#if defined(zLib)
5493 if (SDDS_dataset->layout.gzipFile) {
5494 gzfp = layout->gzfp;
5495 for (i = 0; i < layout->n_arrays; i++) {
5496 if (!SDDS_dataset->array[i].dimension) {
5497 for (j = 0; j < layout->array_definition[i].dimensions; j++)
5498 if (!SDDS_GZipBufferedWrite(&zero, sizeof(zero), gzfp, fBuffer)) {
5499 SDDS_SetError("Unable to write null array--failure writing dimensions (SDDS_WriteNonNativeBinaryArrays)");
5500 SDDS_SwapEndsArrayData(SDDS_dataset);
5501 return 0;
5502 }
5503 continue;
5504 }
5505
5506 for (j = 0; j < layout->array_definition[i].dimensions; j++) {
5507 dimension = SDDS_dataset->array[i].dimension[j];
5508 SDDS_SwapLong(&dimension);
5509 if (!SDDS_GZipBufferedWrite(&dimension, sizeof(dimension), gzfp, fBuffer)) {
5510 SDDS_SetError("Unable to write arrays--failure writing dimensions (SDDS_WriteNonNativeBinaryArrays)");
5511 SDDS_SwapEndsArrayData(SDDS_dataset);
5512 return (0);
5513 }
5514 }
5515 if (layout->array_definition[i].type == SDDS_STRING) {
5516 for (j = 0; j < SDDS_dataset->array[i].elements; j++) {
5517 if (!SDDS_GZipWriteNonNativeBinaryString(((char **)SDDS_dataset->array[i].data)[j], gzfp, fBuffer)) {
5518 SDDS_SetError("Unable to write arrays--failure writing string (SDDS_WriteNonNativeBinaryArrays)");
5519 SDDS_SwapEndsArrayData(SDDS_dataset);
5520 return (0);
5521 }
5522 }
5523 } else if (!SDDS_GZipBufferedWrite(SDDS_dataset->array[i].data, SDDS_type_size[layout->array_definition[i].type - 1] * SDDS_dataset->array[i].elements, gzfp, fBuffer)) {
5524 SDDS_SetError("Unable to write arrays--failure writing values (SDDS_WriteNonNativeBinaryArrays)");
5525 SDDS_SwapEndsArrayData(SDDS_dataset);
5526 return (0);
5527 }
5528 }
5529 } else {
5530#endif
5531 if (SDDS_dataset->layout.lzmaFile) {
5532 lzmafp = layout->lzmafp;
5533 for (i = 0; i < layout->n_arrays; i++) {
5534 if (!SDDS_dataset->array[i].dimension) {
5535 for (j = 0; j < layout->array_definition[i].dimensions; j++)
5536 if (!SDDS_LZMABufferedWrite(&zero, sizeof(zero), lzmafp, fBuffer)) {
5537 SDDS_SetError("Unable to write null array--failure writing dimensions (SDDS_WriteNonNativeBinaryArrays)");
5538 SDDS_SwapEndsArrayData(SDDS_dataset);
5539 return 0;
5540 }
5541 continue;
5542 }
5543
5544 for (j = 0; j < layout->array_definition[i].dimensions; j++) {
5545 dimension = SDDS_dataset->array[i].dimension[j];
5546 SDDS_SwapLong(&dimension);
5547 if (!SDDS_LZMABufferedWrite(&dimension, sizeof(dimension), lzmafp, fBuffer)) {
5548 SDDS_SetError("Unable to write arrays--failure writing dimensions (SDDS_WriteNonNativeBinaryArrays)");
5549 SDDS_SwapEndsArrayData(SDDS_dataset);
5550 return (0);
5551 }
5552 }
5553 if (layout->array_definition[i].type == SDDS_STRING) {
5554 for (j = 0; j < SDDS_dataset->array[i].elements; j++) {
5555 if (!SDDS_LZMAWriteNonNativeBinaryString(((char **)SDDS_dataset->array[i].data)[j], lzmafp, fBuffer)) {
5556 SDDS_SetError("Unable to write arrays--failure writing string (SDDS_WriteNonNativeBinaryArrays)");
5557 SDDS_SwapEndsArrayData(SDDS_dataset);
5558 return (0);
5559 }
5560 }
5561 } else if (!SDDS_LZMABufferedWrite(SDDS_dataset->array[i].data, SDDS_type_size[layout->array_definition[i].type - 1] * SDDS_dataset->array[i].elements, lzmafp, fBuffer)) {
5562 SDDS_SetError("Unable to write arrays--failure writing values (SDDS_WriteNonNativeBinaryArrays)");
5563 SDDS_SwapEndsArrayData(SDDS_dataset);
5564 return (0);
5565 }
5566 }
5567 } else {
5568 fp = layout->fp;
5569 for (i = 0; i < layout->n_arrays; i++) {
5570 if (!SDDS_dataset->array[i].dimension) {
5571 for (j = 0; j < layout->array_definition[i].dimensions; j++)
5572 if (!SDDS_BufferedWrite(&zero, sizeof(zero), fp, fBuffer)) {
5573 SDDS_SetError("Unable to write null array--failure writing dimensions (SDDS_WriteNonNativeBinaryArrays)");
5574 SDDS_SwapEndsArrayData(SDDS_dataset);
5575 return 0;
5576 }
5577 continue;
5578 }
5579
5580 for (j = 0; j < layout->array_definition[i].dimensions; j++) {
5581 dimension = SDDS_dataset->array[i].dimension[j];
5582 SDDS_SwapLong(&dimension);
5583 if (!SDDS_BufferedWrite(&dimension, sizeof(dimension), fp, fBuffer)) {
5584 SDDS_SetError("Unable to write arrays--failure writing dimensions (SDDS_WriteNonNativeBinaryArrays)");
5585 SDDS_SwapEndsArrayData(SDDS_dataset);
5586 return (0);
5587 }
5588 }
5589 if (layout->array_definition[i].type == SDDS_STRING) {
5590 for (j = 0; j < SDDS_dataset->array[i].elements; j++) {
5591 if (!SDDS_WriteNonNativeBinaryString(((char **)SDDS_dataset->array[i].data)[j], fp, fBuffer)) {
5592 SDDS_SetError("Unable to write arrays--failure writing string (SDDS_WriteNonNativeBinaryArrays)");
5593 SDDS_SwapEndsArrayData(SDDS_dataset);
5594 return (0);
5595 }
5596 }
5597 } else if (!SDDS_BufferedWrite(SDDS_dataset->array[i].data, SDDS_type_size[layout->array_definition[i].type - 1] * SDDS_dataset->array[i].elements, fp, fBuffer)) {
5598 SDDS_SetError("Unable to write arrays--failure writing values (SDDS_WriteNonNativeBinaryArrays)");
5599 SDDS_SwapEndsArrayData(SDDS_dataset);
5600 return (0);
5601 }
5602 }
5603 }
5604#if defined(zLib)
5605 }
5606#endif
5607 SDDS_SwapEndsArrayData(SDDS_dataset);
5608 return (1);
5609}
int32_t SDDS_WriteNonNativeBinaryString(char *string, FILE *fp, SDDS_FILEBUFFER *fBuffer)
Writes a non-native endian binary string to a file.
int32_t SDDS_LZMABufferedWrite(void *target, int64_t targetSize, struct lzmafile *lzmafp, SDDS_FILEBUFFER *fBuffer)
int32_t SDDS_LZMAWriteNonNativeBinaryString(char *string, struct lzmafile *lzmafp, SDDS_FILEBUFFER *fBuffer)
Writes a non-native endian binary string to an LZMA-compressed file.

◆ SDDS_WriteNonNativeBinaryPage()

epicsShareFuncSDDS int32_t SDDS_WriteNonNativeBinaryPage ( SDDS_DATASET * SDDS_dataset)
extern

Writes a non-native endian binary page to an SDDS dataset.

This function writes a binary page to the specified SDDS dataset, handling byte order reversal to convert between little-endian and big-endian formats. It manages various compression formats, including uncompressed, GZIP-compressed, and LZMA-compressed files. The function performs the following operations:

  • Counts the number of rows to write.
  • Writes the row count with appropriate byte order handling.
  • Writes non-native endian parameters and arrays.
  • Writes column data in either column-major or row-major format based on the dataset's configuration.
  • Flushes the buffer to ensure all data is written to the file.
Parameters
[in,out]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset to write to.
Returns
int32_t Returns 1 on successful writing of the binary page, or 0 if an error occurred.
Return values
1The binary page was successfully written and byte-swapped.
0An error occurred during the write operation, such as I/O failures, memory allocation issues, or corrupted dataset definitions.
Note
This function modifies the dataset's internal structures during the write process. Ensure that the dataset is properly initialized and opened for writing before invoking this function. After writing, the dataset's state is updated to reflect the newly written page.

Definition at line 5112 of file SDDS_binary.c.

5116{
5117 FILE *fp;
5118 struct lzmafile *lzmafp = NULL;
5119 int64_t i, rows, fixed_rows;
5120 int32_t min32 = INT32_MIN, rows32;
5121 SDDS_FILEBUFFER *fBuffer;
5122#if defined(zLib)
5123 gzFile gzfp = NULL;
5124#endif
5125
5126 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_WriteNonNativeBinaryPage"))
5127 return (0);
5128 if (!(fp = SDDS_dataset->layout.fp)) {
5129 SDDS_SetError("Unable to write page--file pointer is NULL (SDDS_WriteNonNativeBinaryPage)");
5130 return (0);
5131 }
5132 fBuffer = &SDDS_dataset->fBuffer;
5133
5134 if (!fBuffer->buffer) {
5135 int32_t bufferSize = SDDS_GetLockedDefaultIOBufferSize();
5136 if (!(fBuffer->buffer = fBuffer->data = SDDS_Malloc(sizeof(char) * bufferSize))) {
5137 SDDS_SetError("Unable to do buffered read--allocation failure (SDDS_WriteNonNativeBinaryPage)");
5138 return 0;
5139 }
5140 fBuffer->bufferSize = bufferSize;
5141 fBuffer->bytesLeft = bufferSize;
5142 }
5143 SDDS_SwapLong(&min32);
5144
5145 rows = SDDS_CountRowsOfInterest(SDDS_dataset);
5146#if defined(zLib)
5147 if (SDDS_dataset->layout.gzipFile) {
5148 if (!(gzfp = SDDS_dataset->layout.gzfp)) {
5149 SDDS_SetError("Unable to write page--file pointer is NULL (SDDS_WriteNonNativeBinaryPage)");
5150 return (0);
5151 }
5152 SDDS_dataset->rowcount_offset = gztell(gzfp);
5153 if (SDDS_dataset->layout.data_mode.fixed_row_count) {
5154 fixed_rows = ((rows / SDDS_dataset->layout.data_mode.fixed_row_increment) + 2) * SDDS_dataset->layout.data_mode.fixed_row_increment;
5155 if (fixed_rows > INT32_MAX) {
5156 if (!SDDS_GZipBufferedWrite(&min32, sizeof(min32), gzfp, fBuffer)) {
5157 SDDS_SetError("Unable to write page--failure writing number of rows (SDDS_WriteNonNativeBinaryPage)");
5158 return (0);
5159 }
5160 SDDS_SwapLong64(&fixed_rows);
5161 if (!SDDS_GZipBufferedWrite(&fixed_rows, sizeof(fixed_rows), gzfp, fBuffer)) {
5162 SDDS_SetError("Unable to write page--failure writing number of rows (SDDS_WriteNonNativeBinaryPage)");
5163 return (0);
5164 }
5165 SDDS_SwapLong64(&fixed_rows);
5166 } else {
5167 rows32 = (int32_t)fixed_rows;
5168 SDDS_SwapLong(&rows32);
5169 if (!SDDS_GZipBufferedWrite(&rows32, sizeof(rows32), gzfp, fBuffer)) {
5170 SDDS_SetError("Unable to write page--failure writing number of rows (SDDS_WriteNonNativeBinaryPage)");
5171 return (0);
5172 }
5173 }
5174 } else {
5175 if (rows > INT32_MAX) {
5176 if (!SDDS_GZipBufferedWrite(&min32, sizeof(min32), gzfp, fBuffer)) {
5177 SDDS_SetError("Unable to write page--failure writing number of rows (SDDS_WriteNonNativeBinaryPage)");
5178 return (0);
5179 }
5180 SDDS_SwapLong64(&rows);
5181 if (!SDDS_GZipBufferedWrite(&rows, sizeof(rows), gzfp, fBuffer)) {
5182 SDDS_SetError("Unable to write page--failure writing number of rows (SDDS_WriteNonNativeBinaryPage)");
5183 return (0);
5184 }
5185 SDDS_SwapLong64(&rows);
5186 } else {
5187 rows32 = (int32_t)rows;
5188 SDDS_SwapLong(&rows32);
5189 if (!SDDS_GZipBufferedWrite(&rows32, sizeof(rows32), gzfp, fBuffer)) {
5190 SDDS_SetError("Unable to write page--failure writing number of rows (SDDS_WriteNonNativeBinaryPage)");
5191 return (0);
5192 }
5193 }
5194 }
5195 } else {
5196#endif
5197 if (SDDS_dataset->layout.lzmaFile) {
5198 if (!(lzmafp = SDDS_dataset->layout.lzmafp)) {
5199 SDDS_SetError("Unable to write page--file pointer is NULL (SDDS_WriteNonNativeBinaryPage)");
5200 return (0);
5201 }
5202 SDDS_dataset->rowcount_offset = lzma_tell(lzmafp);
5203 if (SDDS_dataset->layout.data_mode.fixed_row_count) {
5204 fixed_rows = ((rows / SDDS_dataset->layout.data_mode.fixed_row_increment) + 2) * SDDS_dataset->layout.data_mode.fixed_row_increment;
5205 if (fixed_rows > INT32_MAX) {
5206 if (!SDDS_LZMABufferedWrite(&min32, sizeof(min32), lzmafp, fBuffer)) {
5207 SDDS_SetError("Unable to write page--failure writing number of rows (SDDS_WriteNonNativeBinaryPage)");
5208 return (0);
5209 }
5210 SDDS_SwapLong64(&fixed_rows);
5211 if (!SDDS_LZMABufferedWrite(&fixed_rows, sizeof(fixed_rows), lzmafp, fBuffer)) {
5212 SDDS_SetError("Unable to write page--failure writing number of rows (SDDS_WriteNonNativeBinaryPage)");
5213 return (0);
5214 }
5215 SDDS_SwapLong64(&fixed_rows);
5216 } else {
5217 rows32 = (int32_t)fixed_rows;
5218 SDDS_SwapLong(&rows32);
5219 if (!SDDS_LZMABufferedWrite(&rows32, sizeof(rows32), lzmafp, fBuffer)) {
5220 SDDS_SetError("Unable to write page--failure writing number of rows (SDDS_WriteNonNativeBinaryPage)");
5221 return (0);
5222 }
5223 }
5224 } else {
5225 if (rows > INT32_MAX) {
5226 if (!SDDS_LZMABufferedWrite(&min32, sizeof(min32), lzmafp, fBuffer)) {
5227 SDDS_SetError("Unable to write page--failure writing number of rows (SDDS_WriteNonNativeBinaryPage)");
5228 return (0);
5229 }
5230 SDDS_SwapLong64(&rows);
5231 if (!SDDS_LZMABufferedWrite(&rows, sizeof(rows), lzmafp, fBuffer)) {
5232 SDDS_SetError("Unable to write page--failure writing number of rows (SDDS_WriteNonNativeBinaryPage)");
5233 return (0);
5234 }
5235 SDDS_SwapLong64(&rows);
5236 } else {
5237 rows32 = (int32_t)rows;
5238 SDDS_SwapLong(&rows32);
5239 if (!SDDS_LZMABufferedWrite(&rows32, sizeof(rows32), lzmafp, fBuffer)) {
5240 SDDS_SetError("Unable to write page--failure writing number of rows (SDDS_WriteNonNativeBinaryPage)");
5241 return (0);
5242 }
5243 }
5244 }
5245 } else {
5246 SDDS_dataset->rowcount_offset = ftell(fp);
5247 if (SDDS_dataset->layout.data_mode.fixed_row_count) {
5248 fixed_rows = ((rows / SDDS_dataset->layout.data_mode.fixed_row_increment) + 2) * SDDS_dataset->layout.data_mode.fixed_row_increment;
5249 if (fixed_rows > INT32_MAX) {
5250 if (!SDDS_BufferedWrite(&min32, sizeof(min32), fp, fBuffer)) {
5251 SDDS_SetError("Unable to write page--failure writing number of rows (SDDS_WriteNonNativeBinaryPage)");
5252 return (0);
5253 }
5254 SDDS_SwapLong64(&fixed_rows);
5255 if (!SDDS_BufferedWrite(&fixed_rows, sizeof(fixed_rows), fp, fBuffer)) {
5256 SDDS_SetError("Unable to write page--failure writing number of rows (SDDS_WriteNonNativeBinaryPage)");
5257 return (0);
5258 }
5259 SDDS_SwapLong64(&fixed_rows);
5260 } else {
5261 rows32 = (int32_t)fixed_rows;
5262 SDDS_SwapLong(&rows32);
5263 if (!SDDS_BufferedWrite(&rows32, sizeof(rows32), fp, fBuffer)) {
5264 SDDS_SetError("Unable to write page--failure writing number of rows (SDDS_WriteNonNativeBinaryPage)");
5265 return (0);
5266 }
5267 }
5268 } else {
5269 if (rows > INT32_MAX) {
5270 if (!SDDS_BufferedWrite(&min32, sizeof(min32), fp, fBuffer)) {
5271 SDDS_SetError("Unable to write page--failure writing number of rows (SDDS_WriteNonNativeBinaryPage)");
5272 return (0);
5273 }
5274 SDDS_SwapLong64(&rows);
5275 if (!SDDS_BufferedWrite(&rows, sizeof(rows), fp, fBuffer)) {
5276 SDDS_SetError("Unable to write page--failure writing number of rows (SDDS_WriteNonNativeBinaryPage)");
5277 return (0);
5278 }
5279 SDDS_SwapLong64(&rows);
5280 } else {
5281 rows32 = (int32_t)rows;
5282 SDDS_SwapLong(&rows32);
5283 if (!SDDS_BufferedWrite(&rows32, sizeof(rows32), fp, fBuffer)) {
5284 SDDS_SetError("Unable to write page--failure writing number of rows (SDDS_WriteNonNativeBinaryPage)");
5285 return (0);
5286 }
5287 }
5288 }
5289 }
5290#if defined(zLib)
5291 }
5292#endif
5293 if (!SDDS_WriteNonNativeBinaryParameters(SDDS_dataset)) {
5294 SDDS_SetError("Unable to write page--parameter writing problem (SDDS_WriteNonNativeBinaryPage)");
5295 return 0;
5296 }
5297 if (!SDDS_WriteNonNativeBinaryArrays(SDDS_dataset)) {
5298 SDDS_SetError("Unable to write page--array writing problem (SDDS_WriteNonNativeBinaryPage)");
5299 return 0;
5300 }
5301 SDDS_SwapEndsColumnData(SDDS_dataset);
5302 if (SDDS_dataset->layout.n_columns) {
5303 if (SDDS_dataset->layout.data_mode.column_major) {
5304 if (!SDDS_WriteNonNativeBinaryColumns(SDDS_dataset)) {
5305 SDDS_SetError("Unable to write page--column writing problem (SDDS_WriteNonNativeBinaryPage)");
5306 return 0;
5307 }
5308 } else {
5309 for (i = 0; i < SDDS_dataset->n_rows; i++) {
5310 if (SDDS_dataset->row_flag[i]) {
5311 if (!SDDS_WriteNonNativeBinaryRow(SDDS_dataset, i)) {
5312 SDDS_SetError("Unable to write page--row writing problem (SDDS_WriteNonNativeBinaryPage)");
5313 return 0;
5314 }
5315 }
5316 }
5317 }
5318 }
5319 SDDS_SwapEndsColumnData(SDDS_dataset);
5320#if defined(zLib)
5321 if (SDDS_dataset->layout.gzipFile) {
5322 if (!SDDS_GZipFlushBuffer(gzfp, fBuffer)) {
5323 SDDS_SetError("Unable to write page--buffer flushing problem (SDDS_WriteNonNativeBinaryPage)");
5324 return 0;
5325 }
5326 } else {
5327#endif
5328 if (SDDS_dataset->layout.lzmaFile) {
5329 if (!SDDS_LZMAFlushBuffer(lzmafp, fBuffer)) {
5330 SDDS_SetError("Unable to write page--buffer flushing problem (SDDS_WriteNonNativeBinaryPage)");
5331 return 0;
5332 }
5333 } else {
5334 if (!SDDS_FlushBuffer(fp, fBuffer)) {
5335 SDDS_SetError("Unable to write page--buffer flushing problem (SDDS_WriteNonNativeBinaryPage)");
5336 return 0;
5337 }
5338 }
5339#if defined(zLib)
5340 }
5341#endif
5342 SDDS_dataset->last_row_written = SDDS_dataset->n_rows - 1;
5343 SDDS_dataset->n_rows_written = rows;
5344 SDDS_dataset->writing_page = 1;
5345 return (1);
5346}
int32_t SDDS_SwapEndsColumnData(SDDS_DATASET *SDDSin)
Swaps the endianness of the column data in an SDDS dataset.
int32_t SDDS_WriteNonNativeBinaryRow(SDDS_DATASET *SDDS_dataset, int64_t row)
Writes a non-native endian binary row to an SDDS dataset.
int32_t SDDS_WriteNonNativeBinaryArrays(SDDS_DATASET *SDDS_dataset)
Writes non-native endian binary arrays to an SDDS dataset.
int32_t SDDS_WriteNonNativeBinaryColumns(SDDS_DATASET *SDDS_dataset)
Writes non-native endian binary columns of an SDDS dataset to the associated file.
int32_t SDDS_WriteNonNativeBinaryParameters(SDDS_DATASET *SDDS_dataset)
Writes non-native endian binary parameters to an SDDS dataset.
int32_t SDDS_LZMAFlushBuffer(struct lzmafile *lzmafp, SDDS_FILEBUFFER *fBuffer)

◆ SDDS_WriteNonNativeBinaryParameters()

int32_t SDDS_WriteNonNativeBinaryParameters ( SDDS_DATASET * SDDS_dataset)

Writes non-native endian binary parameters to an SDDS dataset.

This function iterates through all parameter definitions in the specified SDDS dataset and writes their binary data to the underlying file. It handles various data types, including short, unsigned short, long, unsigned long, long long, unsigned long long, float, double, and long double. For string parameters, it writes each string individually, ensuring proper memory management and byte order conversion. Parameters with fixed values are skipped during the write process. The function supports different compression formats, including uncompressed, LZMA-compressed, and GZIP-compressed files.

Parameters
[in,out]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset to write to.
Returns
int32_t Returns 1 on successful writing of all parameters, or 0 if an error occurred.
Return values
1All non-native endian parameters were successfully written and byte-swapped.
0An error occurred during the write operation, such as I/O failures, memory allocation issues, or corrupted parameter definitions.
Note
This function modifies the dataset's parameter data during the write process. Ensure that the dataset is properly initialized and opened for writing before invoking this function. After writing, the dataset's state is updated to reflect the written parameters.

Definition at line 5369 of file SDDS_binary.c.

5369 {
5370 int32_t i;
5371 SDDS_LAYOUT *layout;
5372 FILE *fp;
5373 struct lzmafile *lzmafp;
5374 SDDS_FILEBUFFER *fBuffer;
5375#if defined(zLib)
5376 gzFile gzfp;
5377#endif
5378
5379 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_WriteNonNativeBinaryParameters"))
5380 return (0);
5381
5382 SDDS_SwapEndsParameterData(SDDS_dataset);
5383
5384 layout = &SDDS_dataset->layout;
5385 fBuffer = &SDDS_dataset->fBuffer;
5386#if defined(zLib)
5387 if (SDDS_dataset->layout.gzipFile) {
5388 if (!(gzfp = layout->gzfp)) {
5389 SDDS_SetError("Unable to write parameters--file pointer is NULL (SDDS_WriteNonNativeBinaryParameters)");
5390 return (0);
5391 }
5392 for (i = 0; i < layout->n_parameters; i++) {
5393 if (layout->parameter_definition[i].fixed_value)
5394 continue;
5395 if (layout->parameter_definition[i].type == SDDS_STRING) {
5396 if (!SDDS_GZipWriteNonNativeBinaryString(*((char **)SDDS_dataset->parameter[i]), gzfp, fBuffer)) {
5397 SDDS_SetError("Unable to write parameters--failure writing string (SDDS_WriteNonNativeBinaryParameters)");
5398 SDDS_SwapEndsParameterData(SDDS_dataset);
5399 return (0);
5400 }
5401 } else if (!SDDS_GZipBufferedWrite(SDDS_dataset->parameter[i], SDDS_type_size[layout->parameter_definition[i].type - 1], gzfp, fBuffer)) {
5402 SDDS_SetError("Unable to write parameters--failure writing value (SDDS_WriteBinaryParameters)");
5403 SDDS_SwapEndsParameterData(SDDS_dataset);
5404 return (0);
5405 }
5406 }
5407 } else {
5408#endif
5409 if (SDDS_dataset->layout.lzmaFile) {
5410 if (!(lzmafp = layout->lzmafp)) {
5411 SDDS_SetError("Unable to write parameters--file pointer is NULL (SDDS_WriteNonNativeBinaryParameters)");
5412 return (0);
5413 }
5414 for (i = 0; i < layout->n_parameters; i++) {
5415 if (layout->parameter_definition[i].fixed_value)
5416 continue;
5417 if (layout->parameter_definition[i].type == SDDS_STRING) {
5418 if (!SDDS_LZMAWriteNonNativeBinaryString(*((char **)SDDS_dataset->parameter[i]), lzmafp, fBuffer)) {
5419 SDDS_SetError("Unable to write parameters--failure writing string (SDDS_WriteNonNativeBinaryParameters)");
5420 SDDS_SwapEndsParameterData(SDDS_dataset);
5421 return (0);
5422 }
5423 } else if (!SDDS_LZMABufferedWrite(SDDS_dataset->parameter[i], SDDS_type_size[layout->parameter_definition[i].type - 1], lzmafp, fBuffer)) {
5424 SDDS_SetError("Unable to write parameters--failure writing value (SDDS_WriteBinaryParameters)");
5425 SDDS_SwapEndsParameterData(SDDS_dataset);
5426 return (0);
5427 }
5428 }
5429 } else {
5430 fp = layout->fp;
5431 for (i = 0; i < layout->n_parameters; i++) {
5432 if (layout->parameter_definition[i].fixed_value)
5433 continue;
5434 if (layout->parameter_definition[i].type == SDDS_STRING) {
5435 if (!SDDS_WriteNonNativeBinaryString(*((char **)SDDS_dataset->parameter[i]), fp, fBuffer)) {
5436 SDDS_SetError("Unable to write parameters--failure writing string (SDDS_WriteNonNativeBinaryParameters)");
5437 SDDS_SwapEndsParameterData(SDDS_dataset);
5438 return (0);
5439 }
5440 } else if (!SDDS_BufferedWrite(SDDS_dataset->parameter[i], SDDS_type_size[layout->parameter_definition[i].type - 1], fp, fBuffer)) {
5441 SDDS_SetError("Unable to write parameters--failure writing value (SDDS_WriteBinaryParameters)");
5442 SDDS_SwapEndsParameterData(SDDS_dataset);
5443 return (0);
5444 }
5445 }
5446 }
5447#if defined(zLib)
5448 }
5449#endif
5450
5451 SDDS_SwapEndsParameterData(SDDS_dataset);
5452 return (1);
5453}

◆ SDDS_WriteNonNativeBinaryRow()

int32_t SDDS_WriteNonNativeBinaryRow ( SDDS_DATASET * SDDS_dataset,
int64_t row )

Writes a non-native endian binary row to an SDDS dataset.

This function writes a single row of data to the specified SDDS dataset, handling byte order reversal to convert between little-endian and big-endian formats. It supports various compression formats, including uncompressed, GZIP-compressed, and LZMA-compressed files. The function iterates through all column definitions, writing each column's data appropriately based on its type. For string columns, it ensures proper memory management and byte order conversion by utilizing specialized string writing functions. For non-string data types, it writes the binary data directly with the correct byte ordering.

Parameters
[in,out]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset to write to.
[in]rowThe index of the row to write to the dataset.
Returns
int32_t Returns 1 on successful writing of the binary row, or 0 if an error occurred.
Return values
1The binary row was successfully written and byte-swapped.
0An error occurred during the write operation, such as I/O failures or corrupted data.
Note
This function modifies the dataset's internal data structures during the write process. Ensure that the dataset is properly initialized and opened for writing before invoking this function. After writing, the dataset's state is updated to reflect the newly written row.

Definition at line 5632 of file SDDS_binary.c.

5632 {
5633 int64_t i, type, size;
5634 SDDS_LAYOUT *layout;
5635 FILE *fp;
5636 struct lzmafile *lzmafp;
5637 SDDS_FILEBUFFER *fBuffer;
5638#if defined(zLib)
5639 gzFile gzfp;
5640#endif
5641
5642 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_WriteNonNativeBinaryRow"))
5643 return (0);
5644 layout = &SDDS_dataset->layout;
5645 fBuffer = &SDDS_dataset->fBuffer;
5646#if defined(zLib)
5647 if (SDDS_dataset->layout.gzipFile) {
5648 gzfp = layout->gzfp;
5649 for (i = 0; i < layout->n_columns; i++) {
5650 if ((type = layout->column_definition[i].type) == SDDS_STRING) {
5651 if (!SDDS_GZipWriteNonNativeBinaryString(*((char **)SDDS_dataset->data[i] + row), gzfp, fBuffer)) {
5652 SDDS_SetError("Unable to write rows--failure writing string (SDDS_WriteNonNativeBinaryRows)");
5653 return (0);
5654 }
5655 } else {
5656 size = SDDS_type_size[type - 1];
5657 if (!SDDS_GZipBufferedWrite((char *)SDDS_dataset->data[i] + row * size, size, gzfp, fBuffer)) {
5658 SDDS_SetError("Unable to write row--failure writing value (SDDS_WriteNonNativeBinaryRow)");
5659 return (0);
5660 }
5661 }
5662 }
5663 } else {
5664#endif
5665 if (SDDS_dataset->layout.lzmaFile) {
5666 lzmafp = layout->lzmafp;
5667 for (i = 0; i < layout->n_columns; i++) {
5668 if ((type = layout->column_definition[i].type) == SDDS_STRING) {
5669 if (!SDDS_LZMAWriteNonNativeBinaryString(*((char **)SDDS_dataset->data[i] + row), lzmafp, fBuffer)) {
5670 SDDS_SetError("Unable to write rows--failure writing string (SDDS_WriteNonNativeBinaryRows)");
5671 return (0);
5672 }
5673 } else {
5674 size = SDDS_type_size[type - 1];
5675 if (!SDDS_LZMABufferedWrite((char *)SDDS_dataset->data[i] + row * size, size, lzmafp, fBuffer)) {
5676 SDDS_SetError("Unable to write row--failure writing value (SDDS_WriteNonNativeBinaryRow)");
5677 return (0);
5678 }
5679 }
5680 }
5681 } else {
5682 fp = layout->fp;
5683 for (i = 0; i < layout->n_columns; i++) {
5684 if ((type = layout->column_definition[i].type) == SDDS_STRING) {
5685 if (!SDDS_WriteNonNativeBinaryString(*((char **)SDDS_dataset->data[i] + row), fp, fBuffer)) {
5686 SDDS_SetError("Unable to write rows--failure writing string (SDDS_WriteNonNativeBinaryRows)");
5687 return (0);
5688 }
5689 } else {
5690 size = SDDS_type_size[type - 1];
5691 if (!SDDS_BufferedWrite((char *)SDDS_dataset->data[i] + row * size, size, fp, fBuffer)) {
5692 SDDS_SetError("Unable to write row--failure writing value (SDDS_WriteNonNativeBinaryRow)");
5693 return (0);
5694 }
5695 }
5696 }
5697 }
5698#if defined(zLib)
5699 }
5700#endif
5701 return (1);
5702}

◆ SDDS_WriteNonNativeBinaryString()

int32_t SDDS_WriteNonNativeBinaryString ( char * string,
FILE * fp,
SDDS_FILEBUFFER * fBuffer )

Writes a non-native endian binary string to a file.

This function writes a binary string to the specified file pointer, handling non-native endianness. It first writes the length of the string as a 32-bit integer with byte order swapped. If the string is not to be skipped, it then writes the string data itself followed by a null terminator. If the input string is NULL, an empty string is written instead.

Parameters
[in]stringThe string to write. If NULL, an empty string is written.
[in]fpPointer to the FILE where the string will be written.
[in]fBufferPointer to the SDDS_FILEBUFFER structure used for buffered writing.
Returns
int32_t Returns 1 on successful writing of the string, or 0 if an error occurred.
Return values
1The string was successfully written and byte-swapped.
0An error occurred during the write operation, such as I/O failures or memory allocation issues.
Note
The caller is responsible for ensuring that the file pointer fp is valid and open for writing. This function does not perform memory allocation for the string; it assumes that the string is already allocated and managed appropriately.

Definition at line 5724 of file SDDS_binary.c.

5724 {
5725 int32_t length;
5726 static const char dummy_string[] = "";
5727 if (!string)
5728 string = (char *)dummy_string;
5729 length = strlen(string);
5730 SDDS_SwapLong(&length);
5731 if (!SDDS_BufferedWrite(&length, sizeof(length), fp, fBuffer)) {
5732 SDDS_SetError("Unable to write string--error writing length");
5733 return (0);
5734 }
5735 SDDS_SwapLong(&length);
5736 if (length && !SDDS_BufferedWrite(string, sizeof(*string) * length, fp, fBuffer)) {
5737 SDDS_SetError("Unable to write string--error writing contents");
5738 return (0);
5739 }
5740 return (1);
5741}

◆ SDDS_WritePage()

epicsShareFuncSDDS int32_t SDDS_WritePage ( SDDS_DATASET * SDDS_dataset)
extern

Writes the current data table to the output file.

This function serializes and writes the current data table of the SDDS dataset to the output file. It must be preceded by a call to SDDS_WriteLayout to ensure that the dataset layout is properly defined in the output file. Depending on the data mode (ASCII or Binary), the function delegates the writing process to the appropriate handler.

Parameters
[in,out]SDDS_datasetPointer to the SDDS_DATASET structure representing the dataset.
Returns
  • 1 on successful writing of the data table.
  • 0 if an error occurred during the write process. An error message is set internally in this case.
Precondition
  • The dataset must be initialized and configured for output.
  • SDDS_WriteLayout must have been called successfully before writing any pages.
Postcondition
  • The current data table is written to the output file.
  • The dataset state is synchronized with the file to ensure data integrity.
Note
  • The function supports parallel I/O modes if enabled.
  • Ensure that the dataset is not disconnected from the output file before calling this function.
Warning
  • Attempting to write a page without defining the layout first will result in an error.
  • Concurrent access to the dataset while writing pages may lead to undefined behavior.

Definition at line 1229 of file SDDS_output.c.

1229 {
1230 int32_t result;
1231#if SDDS_MPI_IO
1232 if (SDDS_dataset->parallel_io)
1233 return SDDS_MPI_WritePage(SDDS_dataset);
1234#endif
1235 if (!SDDS_CheckDataset(SDDS_dataset, "SDDS_WritePage"))
1236 return 0;
1237 if (!SDDS_dataset->layout.layout_written) {
1238 SDDS_SetError("Unable to write page--layout not written (SDDS_WritePage)");
1239 return 0;
1240 }
1241 if (SDDS_dataset->layout.disconnected) {
1242 SDDS_SetError("Can't write page--file is disconnected (SDDS_WritePage)");
1243 return 0;
1244 }
1245 if (SDDS_dataset->layout.data_mode.mode == SDDS_ASCII)
1246 result = SDDS_WriteAsciiPage(SDDS_dataset);
1247 else if (SDDS_dataset->layout.data_mode.mode == SDDS_BINARY)
1248 result = SDDS_WriteBinaryPage(SDDS_dataset);
1249 else {
1250 SDDS_SetError("Unable to write page--unknown data mode (SDDS_WritePage)");
1251 return 0;
1252 }
1253 if (result == 1)
1254 if (SDDS_SyncDataSet(SDDS_dataset) != 0)
1255 return 0;
1256 return (result);
1257}
int32_t SDDS_WriteAsciiPage(SDDS_DATASET *SDDS_dataset)
Writes a page of data in ASCII format to the SDDS dataset.
Definition SDDS_ascii.c:410
int32_t SDDS_WriteBinaryPage(SDDS_DATASET *SDDS_dataset)
int32_t SDDS_MPI_WritePage(SDDS_DATASET *SDDS_dataset)
Writes a page of data to the MPI file associated with the SDDS dataset.

◆ SDDS_WriteTypedValue()

epicsShareFuncSDDS int32_t SDDS_WriteTypedValue ( void * data,
int64_t index,
int32_t type,
char * format,
FILE * fp )
extern

Writes a typed value to an ASCII file stream.

This function writes a value of a specified SDDS data type to an ASCII file stream. The data is provided as a void pointer, and the function handles various data types by casting the pointer appropriately based on the type parameter. For string data, special characters are escaped according to SDDS conventions.

Parameters
dataPointer to the data to be written. Should be castable to the type specified by type.
indexArray index of the data to be printed; use 0 if not an array.
typeThe SDDS data type of the data variable. Possible values include SDDS_SHORT, SDDS_LONG, SDDS_FLOAT, etc.
formatOptional printf format string to use; pass NULL to use the default format for the data type.
fpThe FILE pointer to the ASCII file stream where the data will be written.
Returns
Returns 1 on success; 0 on error (e.g., if data or fp is NULL, or an unknown data type is specified).

Definition at line 57 of file SDDS_ascii.c.

57 {
58 char c, *s;
59 short hasWhitespace;
60
61 if (!data) {
62 SDDS_SetError("Unable to write value--data pointer is NULL (SDDS_WriteTypedValue)");
63 return (0);
64 }
65 if (!fp) {
66 SDDS_SetError("Unable to print value--file pointer is NULL (SDDS_WriteTypedValue)");
67 return (0);
68 }
69 switch (type) {
70 case SDDS_SHORT:
71 fprintf(fp, format ? format : "%hd", *((short *)data + index));
72 break;
73 case SDDS_USHORT:
74 fprintf(fp, format ? format : "%hu", *((unsigned short *)data + index));
75 break;
76 case SDDS_LONG:
77 fprintf(fp, format ? format : "%" PRId32, *((int32_t *)data + index));
78 break;
79 case SDDS_ULONG:
80 fprintf(fp, format ? format : "%" PRIu32, *((uint32_t *)data + index));
81 break;
82 case SDDS_LONG64:
83 fprintf(fp, format ? format : "%" PRId64, *((int64_t *)data + index));
84 break;
85 case SDDS_ULONG64:
86 fprintf(fp, format ? format : "%" PRIu64, *((uint64_t *)data + index));
87 break;
88 case SDDS_FLOAT:
89 fprintf(fp, format ? format : "%15.8e", *((float *)data + index));
90 break;
91 case SDDS_DOUBLE:
92 fprintf(fp, format ? format : "%22.15e", *((double *)data + index));
93 break;
94 case SDDS_LONGDOUBLE:
95 if (LDBL_DIG == 18) {
96 fprintf(fp, format ? format : "%22.18Le", *((long double *)data + index));
97 } else {
98 fprintf(fp, format ? format : "%22.15Le", *((long double *)data + index));
99 }
100 break;
101 case SDDS_STRING:
102 /* ignores format string */
103 s = *((char **)data + index);
104 hasWhitespace = 0;
106 fputc('"', fp);
107 hasWhitespace = 1;
108 }
109 while (s && *s) {
110 c = *s++;
111 if (c == '!')
112 fputs("\\!", fp);
113 else if (c == '\\')
114 fputs("\\\\", fp);
115 else if (c == '"')
116 fputs("\\\"", fp);
117 else if (c == ' ')
118 fputc(' ', fp); /* don't escape plain spaces */
119 else if (isspace(c) || !isprint(c))
120 fprintf(fp, "\\%03o", c);
121 else
122 fputc(c, fp);
123 }
124 if (hasWhitespace)
125 fputc('"', fp);
126 break;
127 case SDDS_CHARACTER:
128 /* ignores format string */
129 c = *((char *)data + index);
130 if (c == '!')
131 fputs("\\!", fp);
132 else if (c == '\\')
133 fputs("\\\\", fp);
134 else if (c == '"')
135 fputs("\\\"", fp);
136 else if (!c || isspace(c) || !isprint(c))
137 fprintf(fp, "\\%03o", c);
138 else
139 fputc(c, fp);
140 break;
141 default:
142 SDDS_SetError("Unable to write value--unknown data type (SDDS_WriteTypedValue)");
143 return (0);
144 }
145 return (1);
146}

◆ SDDS_ZeroMemory()

epicsShareFuncSDDS int32_t SDDS_ZeroMemory ( void * mem,
int64_t n_bytes )
extern

Sets a block of memory to zero.

This function zero-initializes a specified number of bytes in a memory block. It is a wrapper around the standard memset function, providing a convenient way to clear memory.

Parameters
[in,out]memPointer to the memory block to be zeroed.
[in]n_bytesThe number of bytes to set to zero.
Returns
Returns 1 on successful memory zeroing. Returns 0 if the input memory pointer mem is NULL.
Note
The function does not perform any bounds checking. It is the caller's responsibility to ensure that the memory block is large enough to accommodate n_bytes.
See also
memset

Definition at line 2051 of file SDDS_utils.c.

2051 {
2052 if (mem) {
2053 memset(mem, 0, n_bytes);
2054 return 1;
2055 }
2056 return 0;
2057
2058 /*
2059 char *c;
2060
2061 if (!(c = (char*)mem))
2062 return(0);
2063 while (n_bytes--)
2064 *c++ = 0;
2065 return(1);
2066 */
2067}