Beispiel #1
0
int
pkg_plugins_shutdown_zfssnap(void)
{
	properties_free(plugins_zfssnap_p);
	close(plugins_zfssnap_fd);
	
	return (EPKG_OK);
}
Beispiel #2
0
properties
properties_read(int fd)
{
    properties head, ptr;
    char hold_n[PROPERTY_MAX_NAME + 1];
    char hold_v[PROPERTY_MAX_VALUE + 1];
    char buf[BUFSIZ * 4];
    int bp, n, v, max;
    enum { LOOK, COMMENT, NAME, VALUE, MVALUE, COMMIT, FILL, STOP } state, last_state;
    int ch = 0, blevel = 0;

    n = v = bp = max = 0;
    head = ptr = NULL;
    state = last_state = LOOK;
    while (state != STOP) {
	if (state != COMMIT) {
	    if (bp == max) {
		last_state = state;
		state = FILL;
	    } else
		ch = buf[bp++];
	}
	switch(state) {
	case FILL:
	    if ((max = read(fd, buf, sizeof buf)) < 0) {
		properties_free(head);
		return (NULL);
	    }
	    if (max == 0) {
		state = STOP;
	    } else {
		/*
		 * Restore the state from before the fill (which will be
		 * initialised to LOOK for the first FILL). This ensures that
		 * if we were part-way through eg., a VALUE state, when the
		 * buffer ran out, that the previous operation will be allowed
		 * to complete.
		 */
		state = last_state;
		ch = buf[0];
		bp = 0;
	    }
	    continue;

	case LOOK:
	    if (isspace((unsigned char)ch))
		continue;
	    /* Allow shell or lisp style comments */
	    else if (ch == '#' || ch == ';') {
		state = COMMENT;
		continue;
	    }
	    else if (isalnum((unsigned char)ch) || ch == '_') {
		if (n >= PROPERTY_MAX_NAME) {
		    n = 0;
		    state = COMMENT;
		}
		else {
		    hold_n[n++] = ch;
		    state = NAME;
		}
	    }
	    else
		state = COMMENT;	/* Ignore the rest of the line */
	    break;

	case COMMENT:
	    if (ch == '\n')
		state = LOOK;
	    break;

	case NAME:
	    if (ch == '\n' || !ch) {
		hold_n[n] = '\0';
		hold_v[0] = '\0';
		v = n = 0;
		state = COMMIT;
	    }
	    else if (isspace((unsigned char)ch))
		continue;
	    else if (ch == '=') {
		hold_n[n] = '\0';
		v = n = 0;
		state = VALUE;
	    }
	    else
		hold_n[n++] = ch;
	    break;

	case VALUE:
	    if (v == 0 && ch == '\n') {
	        hold_v[v] = '\0';
	        v = n = 0;
	        state = COMMIT;
	    } 
	    else if (v == 0 && isspace((unsigned char)ch))
		continue;
	    else if (ch == '{') {
		state = MVALUE;
		++blevel;
	    }
	    else if (ch == '\n' || !ch) {
		hold_v[v] = '\0';
		v = n = 0;
		state = COMMIT;
	    }
	    else {
		if (v >= PROPERTY_MAX_VALUE) {
		    state = COMMENT;
		    v = n = 0;
		    break;
		}
		else
		    hold_v[v++] = ch;
	    }
	    break;

	case MVALUE:
	    /* multiline value */
	    if (v >= PROPERTY_MAX_VALUE) {
		warn("properties_read: value exceeds max length");
		state = COMMENT;
		n = v = 0;
	    }
	    else if (ch == '}' && !--blevel) {
		hold_v[v] = '\0';
		v = n = 0;
		state = COMMIT;
	    }
	    else {
		hold_v[v++] = ch;
		if (ch == '{')
		    ++blevel;
	    }
	    break;

	case COMMIT:
	    if (head == NULL) {
		if ((head = ptr = property_alloc(hold_n, hold_v)) == NULL)
		    return (NULL);
	    } else {
		if ((ptr->next = property_alloc(hold_n, hold_v)) == NULL) {
		    properties_free(head);
		    return (NULL);
		}
		ptr = ptr->next;
	    }
	    state = LOOK;
	    v = n = 0;
	    break;

	case STOP:
	    /* we don't handle this here, but this prevents warnings */
	    break;
	}
    }
    if (head == NULL && (head = property_alloc(NULL, NULL)) == NULL)
	return (NULL);

    return (head);
}
Beispiel #3
0
/**
* Read the properties file specified by <tt>filename</tt> 
* into the array of <tt>properties</tt>, 
* using the specified port library to allocate memory. 
* The array is terminated with null-keyed element, 
* though one can obtain number of elements directly
* via last argument.
*
* @param[in] portLibrary - The port library used to interact with the platform.
* @param[in] filename - The file from which to read data using hyfile* functions.
* @param[out] properties - An array that will contain property file entries.
* @param[out] number - Optional parameter, number of elements in the returned array.
*
* @return JNI_OK on success, or a JNI error code on failure.
*/
jint 
properties_load(HyPortLibrary * portLibrary, const char *filename, 
                          key_value_pair** properties, U_32 *number)
{
    PORT_ACCESS_FROM_PORT (portLibrary);    
    void *handle;
    I_64 seekResult;
    IDATA fileSize;
    char *scanCursor, *scanLimit;
    char *start, *delim, *end;
    key_value_pair *props;
    unsigned arraySize;
    unsigned count = 0;
    jint status = JNI_OK;

    /* Determine the file size, fail if > 2G */
    seekResult = hyfile_length (filename);
    if ((seekResult <= 0) || (seekResult > 0x7FFFFFFF))
    {
        return JNI_ERR;
    }
    scanCursor = hymmap_map_file(filename, &handle);
    if (!scanCursor) {
        return JNI_ERR;
    }

#ifdef ZOS
    /* Convert the scan buffer into ASCII */
    scanCursor = e2a(scanCursor, seekResult);
#endif

    fileSize = (IDATA) seekResult;
    arraySize = fileSize/50 + 1;
    props = hymem_allocate_memory(sizeof(key_value_pair)*(arraySize + 1));
    if (!props) {
        status = JNI_ENOMEM;
        goto finish;
    }

    start = end = scanCursor;
    delim = NULL;
    scanLimit = scanCursor + fileSize;

    do {
        while (scanCursor < scanLimit) {
            switch(*scanCursor) {
                case '\r': 
                case '\n': 
                    end = scanCursor;
                    goto read_line;
                case '=':
                    /* remember only first occurrence which is not key itself */
                    if (delim == NULL && scanCursor > start) {
                        delim = scanCursor;
                    }
                default:
                    ++scanCursor;
                    continue;
            }
        }

read_line:
        if (scanCursor > start && start != delim && *start != '#' && *start != '!')  
            /* line is not empty, well formed and not commented out */
        {
            if (end == start) {
                /* the last line ends with EOF */
                end = scanLimit;
            }
            if (count == arraySize) 
            {
                void* re_props;
                arraySize += arraySize/2 + 1;
                re_props = hymem_reallocate_memory(props, 
                    sizeof(key_value_pair)*(arraySize + 1));
                if (!re_props) {
                    status = JNI_ENOMEM;
                    goto finish;
                }
                props = re_props;
            }
            if (!prop_alloc(portLibrary, props + count, start, delim, end)) {
                status = JNI_ENOMEM;
                goto finish;
            }
            ++count;
        }   
        start = end = ++scanCursor;
        delim = NULL;
    }
    while (scanCursor < scanLimit);

    /*set terminating NULL*/
    props[count].key = NULL; 

finish:
    hymmap_unmap_file(handle);
    if (status != JNI_OK) 
    {
        properties_free(portLibrary, props);
    }
    else 
    {
        *properties = props;
        if (number){
            *number = count;
        }
    }
    return status;
}