/** @brief Creates a structure MATLAB variable with the given name and fields * * @ingroup MAT * @param name Name of the structure variable to create * @param rank Rank of the variable * @param dims array of dimensions of the variable of size rank * @param fields Array of @c nfields fieldnames * @param nfields Number of fields in the structure * @param matvar Pointer to store the new structure MATLAB variable * @return @c MATIO_SUCCESS if successful, or an error value (See * @ref enum matio_error_t). */ matvar_t * Mat_VarCreateStruct(const char *name,int rank,size_t *dims,const char **fields, unsigned nfields) { int i, nmemb = 1; matvar_t *matvar; if ( NULL == dims ) return NULL; matvar = Mat_VarCalloc(); if ( NULL == matvar ) return NULL; matvar->compression = MAT_COMPRESSION_NONE; if ( NULL != name ) matvar->name = strdup(name); matvar->rank = rank; matvar->dims = malloc(matvar->rank*sizeof(*matvar->dims)); for ( i = 0; i < matvar->rank; i++ ) { matvar->dims[i] = dims[i]; nmemb *= dims[i]; } matvar->class_type = MAT_C_STRUCT; matvar->data_type = MAT_T_STRUCT; matvar->data_size = sizeof(matvar_t *); if ( nfields ) { matvar->internal->num_fields = nfields; matvar->internal->fieldnames = malloc(nfields*sizeof(*matvar->internal->fieldnames)); if ( NULL == matvar->internal->fieldnames ) { Mat_VarFree(matvar); matvar = NULL; } else { for ( i = 0; i < nfields; i++ ) { if ( NULL == fields[i] ) { Mat_VarFree(matvar); matvar = NULL; break; } else { matvar->internal->fieldnames[i] = strdup(fields[i]); } } } if ( NULL != matvar && nmemb > 0 && nfields > 0 ) { matvar_t **field_vars; matvar->nbytes = nmemb*nfields*matvar->data_size; matvar->data = malloc(matvar->nbytes); field_vars = (matvar_t**)matvar->data; for ( i = 0; i < nfields*nmemb; i++ ) field_vars[i] = NULL; } } return matvar; }
/** @if mat_devman * @brief Reads the header information for the next MAT variable in a version 4 MAT file * * @ingroup mat_internal * @param mat MAT file pointer * @retuen pointer to the MAT variable or NULL * @endif */ matvar_t * Mat_VarReadNextInfo4(mat_t *mat) { int tmp; int M,O; long nBytes; size_t err; matvar_t *matvar = NULL; if ( mat == NULL || mat->fp == NULL ) return NULL; else if ( NULL == (matvar = Mat_VarCalloc()) ) return NULL; matvar->internal->fp = mat; matvar->internal->fpos = ftell(mat->fp); err = fread(&tmp,sizeof(int),1,mat->fp); if ( !err ) { free(matvar); return NULL; } M = floor(tmp / 1000.0); tmp -= M*1000; O = floor(tmp / 100.0); tmp -= O*100; matvar->data_type = floor(tmp / 10.0); tmp -= matvar->data_type*10; /* Convert the V4 data type */ switch ( matvar->data_type ) { case 0: matvar->data_type = MAT_T_DOUBLE; break; case 1: matvar->data_type = MAT_T_SINGLE; break; case 2: matvar->data_type = MAT_T_INT32; break; case 3: matvar->data_type = MAT_T_INT16; break; case 4: matvar->data_type = MAT_T_UINT16; break; case 5: matvar->data_type = MAT_T_UINT8; break; default: matvar->data_type = -1; break; } matvar->class_type = floor(tmp); switch ( matvar->class_type ) { case 0: matvar->class_type = MAT_C_DOUBLE; break; case 1: matvar->class_type = MAT_C_CHAR; break; case 2: matvar->class_type = MAT_C_SPARSE; break; default: break; } matvar->rank = 2; /* FIXME: Check allocation */ matvar->dims = malloc(2*sizeof(int)); err = fread(matvar->dims,sizeof(int),1,mat->fp); if ( !err ) { Mat_VarFree(matvar); return NULL; } err = fread(matvar->dims+1,sizeof(int),1,mat->fp); if ( !err ) { Mat_VarFree(matvar); return NULL; } err = fread(&(matvar->isComplex),sizeof(int),1,mat->fp); if ( !err ) { Mat_VarFree(matvar); return NULL; } err = fread(&tmp,sizeof(int),1,mat->fp); if ( !err ) { Mat_VarFree(matvar); return NULL; } /* FIXME: Check allocation */ matvar->name = malloc(tmp); err = fread(matvar->name,1,tmp,mat->fp); if ( !err ) { Mat_VarFree(matvar); return NULL; } matvar->internal->datapos = ftell(mat->fp); nBytes = matvar->dims[0]*matvar->dims[1]*Mat_SizeOf(matvar->data_type); if ( matvar->isComplex ) nBytes *= 2; fseek(mat->fp,nBytes,SEEK_CUR); return matvar; }