int InitializerToValue()

in Unix/mof/types.c [951:1526]


int InitializerToValue(
    MOF_Initializer* self,
    MI_Uint32 /*MI_Type*/ type,
    void** value)
{
    /* ATTN: this function could check integer truncation and sign errors */
    /* ATTN: handle case where ZChar is wchar_t */
    size_t i;

    /* Check arguments */
    if (!self || !value)
        return -1;

    *value = NULL;

    /* Early out for a zero-length array */
    if (self->size == 0)
        return 0;

    /* Verify that array is homogeneous (all elements have same type) */
    for (i = 1; i < self->size; i++)
    {
        if (self->data[0].type != self->data[i].type)
            return -1;
    }

    /* Verify that scalars have exactly 1 initializer */
    if (!self->isArray && self->size != 1)
        return -1;

    /* Convert to a static value */
    if (self->isArray)
    {
        switch (self->data[0].type)
        {
            case TOK_INTEGER_VALUE:
            {
                switch (type)
                {
                    case MI_UINT8A:
                    {
                        MI_Uint8A* p;
                        NEW_ARRAY_T(p, MI_Uint8, self->size);

                        for (i = 0; i < self->size; i++)
                        {
                            MI_Sint64 x = self->data[i].value.integer;
                            if (0 != _CheckRange(x, MI_UINT8))
                                return -1;

                            p->data[i] = (MI_Uint8)x;
                        }

                        *value = p;
                        return 0;
                    }
                    case MI_SINT8A:
                    {
                        MI_Sint8A* p;
                        NEW_ARRAY_T(p, MI_Sint8, self->size);

                        for (i = 0; i < self->size; i++)
                        {
                            MI_Sint64 x = self->data[i].value.integer;
                            if (0 != _CheckRange(x, MI_SINT8))
                                return -1;

                            p->data[i] = (MI_Sint8)x;
                        }

                        *value = p;
                        return 0;
                    }
                    case MI_UINT16A:
                    {
                        MI_Uint16A* p;
                        NEW_ARRAY_T(p, MI_Uint16, self->size);

                        for (i = 0; i < self->size; i++)
                        {
                            MI_Sint64 x = self->data[i].value.integer;
                            if (0 != _CheckRange(x, MI_UINT16))
                                return -1;

                            p->data[i] = (MI_Uint16)x;
                        }

                        *value = p;
                        return 0;
                    }
                    case MI_SINT16A:
                    {
                        MI_Sint16A* p;
                        NEW_ARRAY_T(p, MI_Sint16, self->size);

                        for (i = 0; i < self->size; i++)
                        {
                            MI_Sint64 x = self->data[i].value.integer;
                            if (0 != _CheckRange(x, MI_SINT16))
                                return -1;

                            p->data[i] = (MI_Sint16)x;
                        }

                        *value = p;
                        return 0;
                    }
                    case MI_UINT32A:
                    {
                        MI_Uint32A* p;
                        NEW_ARRAY_T(p, MI_Uint32, self->size);

                        for (i = 0; i < self->size; i++)
                        {
                            MI_Sint64 x = self->data[i].value.integer;
                            if (0 != _CheckRange(x, MI_UINT32))
                                return -1;

                            p->data[i] = (MI_Uint32)x;
                        }

                        *value = p;
                        return 0;
                    }
                    case MI_SINT32A:
                    {
                        MI_Sint32A* p;
                        NEW_ARRAY_T(p, MI_Sint32, self->size);

                        for (i = 0; i < self->size; i++)
                        {
                            MI_Sint64 x = self->data[i].value.integer;
                            if (0 != _CheckRange(x, MI_SINT32))
                                return -1;

                            p->data[i] = (MI_Sint32)x;
                        }

                        *value = p;
                        return 0;
                    }
                    case MI_UINT64A:
                    {
                        MI_Uint64A* p;
                        NEW_ARRAY_T(p, MI_Uint64, self->size);

                        for (i = 0; i < self->size; i++)
                        {
                            MI_Sint64 x = self->data[i].value.integer;
                            if (0 != _CheckRange(x, MI_UINT64))
                                return -1;

                            p->data[i] = (MI_Uint64)x;
                        }

                        *value = p;
                        return 0;
                    }
                    case MI_SINT64A:
                    {
                        MI_Sint64A* p;
                        NEW_ARRAY_T(p, MI_Sint64, self->size);

                        for (i = 0; i < self->size; i++)
                        {
                            MI_Sint64 x = self->data[i].value.integer;
                            if (0 != _CheckRange(x, MI_SINT64))
                                return -1;

                            p->data[i] = (MI_Sint64)x;
                        }

                        *value = p;
                        return 0;
                    }
                    case MI_STRINGA:
                    {
                        char Buf[24];
                        MI_StringA* p;
                        NEW_ARRAY_T(p, MI_String, self->size);
                        for (i = 0; i < self->size; i++)
                        {
                            if (self->data->value.integer < 0)
                            {
                                sprintf(Buf, "%ld", (long)self->data->value.integer);
                            }
                            else
                            {
                                sprintf(Buf, "%lu", (unsigned long)self->data->value.integer);
                            }
                            p->data[i] = MALLOC_T(MI_Char, strlen(Buf) + 1);
                            strcpy(p->data[i], Buf);
                        }
                        *value = p;
                        return 0;
                    }
                    default:
                        return -1;
                }
            }
            case TOK_REAL_VALUE:
            {
                switch (type)
                {
                    case MI_REAL32A:
                    {
                        MI_Real32A* p;
                        NEW_ARRAY_T(p, MI_Real32, self->size);

                        for (i = 0; i < self->size; i++)
                        {
                            p->data[i] = (MI_Real32)self->data[i].value.real;
                        }

                        *value = p;
                        return 0;
                    }
                    case MI_REAL64A:
                    {
                        MI_Real64A* p;
                        NEW_ARRAY_T(p, MI_Real64, self->size);

                        for (i = 0; i < self->size; i++)
                        {
                            p->data[i] = (MI_Real64)
                                self->data[i].value.real;
                        }

                        *value = p;
                        return 0;
                    }
                    case MI_STRINGA:
                    {
                        char Buf[24];
                        MI_StringA* p;
                        NEW_ARRAY_T(p, MI_String, self->size);
                        for (i = 0; i < self->size; i++)
                        {
                            sprintf(Buf, "%f", self->data->value.real);
                            p->data[i] = MALLOC_T(MI_Char, strlen(Buf) + 1);
                            strcpy(p->data[i], Buf);
                       }
                        *value = p;
                        return 0;
                    }
                    default:
                        return -1;
                }
                break;
            }
            case TOK_CHAR_VALUE:
            {
                switch (type)
                {
                    case MI_CHAR16A:
                    {
                        MI_Char16A* p;
                        NEW_ARRAY_T(p, MI_Char16, self->size);

                        for (i = 0; i < self->size; i++)
                        {
                            p->data[i] = (MI_Char16)self->data[i].value.character;
                        }

                        *value = p;
                        return 0;
                    }
                    default:
                        return -1;
                }
                break;
            }
            case TOK_STRING_VALUE:
            {
                switch (type)
                {
                    case MI_STRINGA:
                    {
                        MI_StringA* p;
                        NEW_ARRAY_T(p, MI_String, self->size);

                        for (i = 0; i < self->size; i++)
                        {
                            p->data[i] = self->data[i].value.string;
                            self->data[i].value.string = NULL;
                        }

                        *value = p;
                        return 0;
                    }
                    case MI_DATETIMEA:
                    {
                        MI_DatetimeA* p;
                        NEW_ARRAY_T(p, MI_Datetime, self->size);

                        for (i = 0; i < self->size; i++)
                        {
                            if (_StrToDatetime(self->data[i].value.string,
                                &p->data[i]) != 0)
                            {
                                MOF_Free(&state.heap, p);
                                return -1;
                            }

                            MOF_Free(&state.heap, self->data[i].value.string);
                            self->data[i].value.string = NULL;
                        }

                        *value = p;
                        return 0;
                    }
                    default:
                        return -1;
                }
                break;
            }
            case TOK_BOOLEAN_VALUE:
            {
                switch (type)
                {
                    case MI_BOOLEANA:
                    {
                        MI_BooleanA* p;
                        NEW_ARRAY_T(p, MI_Boolean, self->size);

                        for (i = 0; i < self->size; i++)
                        {
                            p->data[i] = (MI_Boolean)
                                self->data[i].value.boolean;
                        }

                        *value = p;
                        return 0;
                    }
                    default:
                        return -1;
                }
            }
            case TOK_INSTANCE:
            case TOK_NULL:
            {
                *value = NULL;
                return 0;
            }
            default:
                return -1;
        }
    }
    else
    {
        switch (self->data->type)
        {
            case TOK_INTEGER_VALUE:
            {
                switch (type)
                {
                    case MI_UINT8:
                    {
                        MI_Uint8* p = MALLOC_T(MI_Uint8, 1);
                        MI_Sint64 x = self->data->value.integer;
                        if (0 != _CheckRange(x, MI_UINT8))
                            return -1;

                        *p = (MI_Uint8)x;
                        *value = p;
                        return 0;
                    }
                    case MI_SINT8:
                    {
                        MI_Sint8* p = MALLOC_T(MI_Sint8, 1);
                        MI_Sint64 x = self->data->value.integer;
                        if (0 != _CheckRange(x, MI_SINT8))
                            return -1;

                        *p = (MI_Sint8)x;
                        *value = p;
                        return 0;
                    }
                    case MI_UINT16:
                    {
                        MI_Uint16* p = MALLOC_T(MI_Uint16, 1);
                        MI_Sint64 x = self->data->value.integer;
                        if (0 != _CheckRange(x, MI_UINT16))
                            return -1;

                        *p = (MI_Uint16)x;
                        *value = p;
                        return 0;
                    }
                    case MI_SINT16:
                    {
                        MI_Sint16* p = MALLOC_T(MI_Sint16, 1);
                        MI_Sint64 x = self->data->value.integer;
                        if (0 != _CheckRange(x, MI_SINT16))
                            return -1;

                        *p = (MI_Sint16)x;
                        *value = p;
                        return 0;
                    }
                    case MI_UINT32:
                    {
                        MI_Uint32* p = MALLOC_T(MI_Uint32, 1);
                        MI_Sint64 x = self->data->value.integer;
                        if (0 != _CheckRange(x, MI_UINT32))
                            return -1;

                        *p = (MI_Uint32)x;
                        *value = p;
                        return 0;
                    }
                    case MI_SINT32:
                    {
                        MI_Sint32* p = MALLOC_T(MI_Sint32, 1);
                        MI_Sint64 x = self->data->value.integer;
                        if (0 != _CheckRange(x, MI_SINT32))
                            return -1;

                        *p = (MI_Sint32)x;
                        *value = p;
                        return 0;
                    }
                    case MI_UINT64:
                    {
                        MI_Uint64* p = MALLOC_T(MI_Uint64, 1);
                        MI_Sint64 x = self->data->value.integer;
                        if (0 != _CheckRange(x, MI_UINT64))
                            return -1;

                        *p = (MI_Uint64)x;
                        *value = p;
                        return 0;
                    }
                    case MI_SINT64:
                    {
                        MI_Sint64* p = MALLOC_T(MI_Sint64, 1);
                        MI_Sint64 x = self->data->value.integer;
                        if (0 != _CheckRange(x, MI_SINT64))
                            return -1;

                        *p = (MI_Sint64)x;
                        *value = p;
                        return 0;
                    }
                    case MI_STRING:
                    {
                        char Buf[24];
                        MI_Char* p;
                        if (self->data->value.integer < 0)
                        {
                            sprintf(Buf, "%ld", (long)self->data->value.integer);
                        }
                        else
                        {
                            sprintf(Buf, "%lu", (unsigned long)self->data->value.integer);
                        }
                        p = MALLOC_T(MI_Char, strlen(Buf) + 1);
                        strcpy(p, Buf);
                        *value = p;
                        return 0;
                    }
                    default:
                        return -1;
                }
                break;
            }
            case TOK_REAL_VALUE:
            {
                switch (type)
                {
                    case MI_REAL32:
                    {
                        MI_Real32* p = MALLOC_T(MI_Real32, 1);
                        *p = (MI_Real32)self->data->value.real;
                        *value = p;
                        return 0;
                    }
                    case MI_REAL64:
                    {
                        MI_Real64* p = MALLOC_T(MI_Real64, 1);
                        *p = (MI_Real64)self->data->value.real;
                        *value = p;
                        return 0;
                    }
                    case MI_STRING:
                    {
                        char Buf[24];
                        MI_Char* p;
                        sprintf(Buf, "%f", self->data->value.real);
                        p = MALLOC_T(MI_Char, strlen(Buf) + 1);
                        strcpy(p, Buf);
                        *value = p;
                        return 0;
                    }
                    default:
                        return -1;
                }
                break;
            }
            case TOK_CHAR_VALUE:
            {
                switch (type)
                {
                    case MI_CHAR16:
                    {
                        MI_Char16* p = MALLOC_T(MI_Char16, 1);
                        *p = (MI_Char16)self->data->value.character;
                        *value = p;
                        return 0;
                    }
                    default:
                        return -1;
                }
                break;
            }
            case TOK_STRING_VALUE:
            {
                switch (type)
                {
                    case MI_STRING:
                    {
                        char *p;
                        p = self->data->value.string;
                        self->data->value.string = NULL;
                        *value = p;
                        return 0;
                    }
                    case MI_DATETIME:
                    {
                        MI_Datetime *p = MALLOC_T(MI_Datetime, 1);

                        if (_StrToDatetime(self->data->value.string, p) != 0)
                        {
                            MOF_Free(&state.heap, p);
                            return -1;
                        }

                        MOF_Free(&state.heap, self->data->value.string);
                        self->data->value.string = NULL;
                        *value = p;
                        return 0;
                    }
                    default:
                        return -1;
                }
                break;
            }
            case TOK_BOOLEAN_VALUE:
            {
                switch (type)
                {
                    case MI_BOOLEAN:
                    {
                        MI_Boolean* p = MALLOC_T(MI_Boolean, 1);
                        *p = (MI_Boolean)self->data->value.boolean;
                        *value = p;
                        return 0;
                    }
                    default:
                        return -1;
                }
                break;
            }
            case TOK_INSTANCE:
            case TOK_NULL:
            {
                *value = NULL;
                return 0;
            }
            default:
                return -1;
        }
    }

    UNREACHABLE_RETURN( return 0; )
}