Example #1
0
/* create a nonterminal given only names */
struct Production *newPackratNonterminal(unsigned char *name, unsigned char ***sub)
{
    struct Production *ret = getProduction(name);
    struct Buffer_Production_p pors;
    struct Buffer_Production pthens;
    struct Production *pr;
    int ors, thens;

    ret->parser = packratNonterminal;

    /* now fill in the sub-productions */
    INIT_BUFFER(pors);
    for (ors = 0; sub[ors]; ors++) {
        INIT_BUFFER(pthens);
        for (thens = 0; sub[ors][thens]; thens++) {
            pr = getProduction(sub[ors][thens]);
            WRITE_BUFFER(pthens, &pr, 1);
        }
        pr = NULL;
        WRITE_BUFFER(pthens, &pr, 1);

        WRITE_BUFFER(pors, &pthens.buf, 1);
    }
    pr = NULL;
    WRITE_BUFFER(pors, (struct Production ***) &pr, 1);

    ret->arg = pors.buf;

    return ret;
}
Example #2
0
 struct Buffer_char cunparseJSON(Node *node)
{
    struct Buffer_char buf;
    INIT_BUFFER(buf);
    unparseJSONPrime(&buf, node);
    WRITE_ONE_BUFFER(buf, '\0');
    return buf;
}
Example #3
0
 struct Buffer_char cunparse(struct Buffer_charp *filenames, Node *node)
{
    struct Buffer_char buf;
    size_t lastFile = -1;
    INIT_BUFFER(buf);
    unparsePrime(&buf, filenames, &lastFile, node);
    WRITE_ONE_BUFFER(buf, '\0');
    return buf;
}
int main(int argc, char **argv)
{
    struct Buffer_double frameDiffs;
    int i;

    INIT_BUFFER(frameDiffs);
    READ_FILE_BUFFER(frameDiffs, stdin);

    for (i = 0; i < frameDiffs.bufused; i++) {
        printf("%f\n", frameDiffs.buf[i]);
    }

    return 0;
}
Example #5
0
File: exec.c Project: GregorR/exc
 struct Buffer_char excExec_execBuffered(
    char *const cmd[],
    struct Buffer_char input,
    int *status)
{
    int tmpi;
    int pipei[2], pipeo[2];
    pid_t pid, tmpp;
    FILE *f;
    struct Buffer_char ret;

    /* prepare to pipe it into/out of the child */
    SF(tmpi, pipe, -1, (pipei));
    SF(tmpi, pipe, -1, (pipeo));

    /* FIXME: the command should be in a spec file! */
    SF(pid, fork, -1, ())
    if (pid == 0) {
        SF(tmpi, close, -1, (pipei[1]));
        SF(tmpi, close, -1, (pipeo[0]));

        SF(tmpi, dup2, -1, (pipei[0], 0));
        SF(tmpi, dup2, -1, (pipeo[1], 1));

        SF(tmpi, close, -1, (pipei[0]));
        SF(tmpi, close, -1, (pipeo[1]));

        SF(tmpi, execvp, -1, (cmd[0], cmd));
        exit(1);

    }

    SF(tmpi, close, -1, (pipei[0]));
    SF(tmpi, close, -1, (pipeo[1]));

    /* give them the input */
    SF(tmpi, write, -1, (pipei[1], input.buf, input.bufused));
    SF(tmpi, close, -1, (pipei[1]));

    /* read in the preprocessed source */
    SF(f, fdopen, NULL, (pipeo[0], "r"));
    INIT_BUFFER(ret);
    READ_FILE_BUFFER(ret, f);
    SF(tmpi, fclose, EOF, (f));

    /* and wait for them */
    SF(tmpp, waitpid, -1, (pid, status, 0));

    return ret;
}
Example #6
0
ssize_t hfs_read_range(void* buffer, const HFSVolume *hfs, size_t size, size_t offset)
{
    debug("Reading from volume at (%d, %d)", offset, size);
    
    // Range check.
    if (hfs->length && offset > hfs->length) {
        error("Request for logical offset larger than the size of the volume (%d, %d)", offset, hfs->length);
        errno = ESPIPE; // Illegal seek
        return -1;
    }
    
    if ( hfs->length && (offset + size) > hfs->length ) {
        size = hfs->length - offset;
        debug("Adjusted read to (%d, %d)", offset, size);
    }
    
    if (size < 1) {
        error("Zero-size request.");
        errno = EINVAL;
        return -1;
    }
    
    // The range starts somewhere in this block.
    size_t start_block = (size_t)(offset / hfs->block_size);
    
    // Offset of the request within the start block.
    size_t byte_offset = (offset % hfs->block_size);
    
    // Add a block to the read if the offset is not block-aligned.
    size_t block_count = (size / hfs->block_size) + ( ((offset + size) % hfs->block_size) ? 1 : 0);
    
    // Use the calculated size instead of the passed size to account for block alignment.
    char* read_buffer; INIT_BUFFER(read_buffer, block_count * hfs->block_size);
    
    // Fetch the data into a read buffer (it may fail).
    ssize_t read_blocks = hfs_read_blocks(read_buffer, hfs, block_count, start_block);
    
    // On success, copy the output.
    if (read_blocks) memcpy(buffer, read_buffer + byte_offset, size);
    
    // Clean up.
    FREE_BUFFER(read_buffer);
    
    // The amount we added to the buffer.
    return size;
}
Example #7
0
ssize_t hfs_read_fork(void* buffer, const HFSFork *fork, size_t block_count, size_t start_block)
{
    int loopCounter = 0; // Fail-safe.
    
    // Keep the original request around
    range request = make_range(start_block, block_count);
    
    debug("Reading from CNID %u (%d, %d)", fork->cnid, request.start, request.count);
    
    // Sanity checks
    if (request.count < 1) {
        error("Invalid request size: %u blocks", request.count);
        return -1;
    }
    
    if ( request.start > fork->totalBlocks ) {
        error("Request would begin beyond the end of the file (start block: %u; file size: %u blocks.", request.start, fork->totalBlocks);
        return -1;
    }
    
    if ( range_max(request) >= fork->totalBlocks ) {
        request.count = fork->totalBlocks - request.start;
        request.count = MAX(request.count, 1);
        debug("Trimmed request to (%d, %d) (file only has %d blocks)", request.start, request.count, fork->totalBlocks);
    }
    
    char* read_buffer;
    INIT_BUFFER(read_buffer, block_count * fork->hfs.block_size);
    ExtentList *extentList = fork->extents;;
    
    // Keep track of what's left to get
    range remaining = request;
    
    while (remaining.count != 0) {
        if (++loopCounter > 2000) {
            Extent *extent = NULL;
            TAILQ_FOREACH(extent, extentList, extents) {
                printf("%10zd: %10zd %10zd\n", extent->logicalStart, extent->startBlock, extent->blockCount);
            }
            PrintExtentList(extentList, fork->totalBlocks);
            critical("We're stuck in a read loop: request (%zd, %zd); remaining (%zd, %zd)", request.start, request.count, remaining.start, remaining.count);
        }
Example #8
0
/* validate a path as OK */
void validatePath(char **path)
{
    struct Buffer_char pathok;
    struct stat sbuf;
    char *rpath;

    if (!*path) return;

    /* first make sure it's absolute */
    if (**path != '/') {
        *path = NULL;
        return;
    }

    /* then get its real path (don't worry about deallocation, there aren't
     * many of these) */
    *path = realpath(*path, NULL);
    if (*path == NULL) return;

    /* then check the ok file */
    INIT_BUFFER(pathok);
    WRITE_BUFFER(pathok, *path, strlen(*path));
    WRITE_STR_BUFFER(pathok, OKFILE);
    WRITE_STR_BUFFER(pathok, "\0");
    if (stat(pathok.buf, &sbuf) < 0) {
        /* file not found or otherwise very bad, kill it */
        *path = NULL;
        FREE_BUFFER(pathok);
        return;
    }
    FREE_BUFFER(pathok);
    if (sbuf.st_uid != geteuid()) {
        /* wrong owner */
        *path = NULL;
        return;
    }

    /* it's valid */
}
Example #9
0
int main(int argc, char **argv)
{
    struct Buffer_charp rpaths;
    struct Buffer_char options;
    char *wpath = NULL, *arg;
    char *envpaths;
    int i, j, argi, tmpi;
    unsigned long mountflags = 0;
    int allowclear = 0, clear = 0, userwpath = 1;

    INIT_BUFFER(rpaths);
    WRITE_ONE_BUFFER(rpaths, NULL); /* filled in by forced dir later */

    /* get all the paths out of the environment */
    envpaths = getenv(PATHENV);
    if (envpaths && envpaths[0]) {
        char *saveptr;
        arg = strtok_r(envpaths, ":", &saveptr);
        while (arg) {
            WRITE_ONE_BUFFER(rpaths, arg);
            arg = strtok_r(NULL, ":", &saveptr);
        }
    }

    /* get all the paths out of the args */
    for (argi = 1; argi < argc; argi++) {
        arg = argv[argi];
        if (arg[0] == '-') {
            if (!strcmp(arg, "-w") && argi < argc - 1) {
                argi++;
                wpath = argv[argi];

            } else if (!strcmp(arg, "-r")) {
                /* reset current paths (ignore environment) */
                rpaths.bufused = 1;
                allowclear = 1;

            } else if (!strcmp(arg, "--") && argi < argc - 1) {
                argi++;
                break;

            } else {
                fprintf(stderr, "Unrecognized option %s\n", arg);
            }

        } else {
            WRITE_ONE_BUFFER(rpaths, arg);

        }
    }
    if (argi >= argc) {
        if (getuid() != geteuid()) {
            fprintf(stderr, "Only root may remount an existing view\n");
            return 1;
        }
        mountflags |= MS_REMOUNT;
    }

    /* validate all our paths */
    for (i = 1; i < rpaths.bufused; i++) {
        validatePath(&rpaths.buf[i]);
    }
    validatePath(&wpath);
    rpaths.buf[0] = FORCEDIR;
    if (!wpath) {
        wpath = DEFAULTWRITEDIR;
        userwpath = 0;
    }

    /* make sure there are no duplicates */
    for (i = 1; i < rpaths.bufused; i++) {
        if (!rpaths.buf[i]) continue;
        if (!strcmp(rpaths.buf[i], wpath)) {
            rpaths.buf[i] = NULL;
            continue;
        }
        for (j = 0; j < i; j++) {
            if (rpaths.buf[j] &&
                !strcmp(rpaths.buf[i], rpaths.buf[j])) {
                rpaths.buf[i] = NULL;
                break;
            }
        }
    }

    /* are we trying to clear /usr? */
    if (rpaths.bufused == 1) {
        /* no options = unmount all */
        if (!allowclear) {
            fprintf(stderr, "To explicitly clear all /usr mounts, -r must be specified\n");
            return 1;
        }
        clear = 1;
    }

    /* perform the mount */
    if (!(mountflags & MS_REMOUNT))
        SF(tmpi, unshare, -1, (CLONE_NEWNS));
    if (clear) {
        do {
            tmpi = umount("/usr");
        } while (tmpi == 0);
        if (errno != EINVAL)
            perror("/usr");
    } else {
        /* first mount */
        INIT_BUFFER(options);
        WRITE_STR_BUFFER(options, "br:");
        WRITE_BUFFER(options, wpath, strlen(wpath) + 1);
        tmpi = mount("none", BASE, "aufs", mountflags, options.buf);
        if (tmpi == -1 && (mountflags & MS_REMOUNT)) {
            /* OK, we tried to remount, maybe it just wasn't mounted though */
            mountflags &= ~(MS_REMOUNT);
            tmpi = mount("none", BASE, "aufs", mountflags, options.buf);
        }

        /* remaining mounts */
        for (i = 0; tmpi != -1 && i < rpaths.bufused; i++) {
            if (!rpaths.buf[i]) continue;
            options.bufused = 0;
            WRITE_STR_BUFFER(options, "append:");
            WRITE_BUFFER(options, rpaths.buf[i], strlen(rpaths.buf[i]));
            if (!userwpath)
                WRITE_STR_BUFFER(options, "=rw");
            WRITE_STR_BUFFER(options, "\0");
            tmpi = mount("none", BASE, "aufs", mountflags|MS_REMOUNT, options.buf);
        }

        if (tmpi == -1) {
            perror("mount");
            return 1;
        }
    }

    /* drop privs */
    SF(tmpi, setuid, -1, (getuid()));
    SF(tmpi, setgid, -1, (getgid()));

    /* free our mount options */
    FREE_BUFFER(options);

    /* add it to the environment */
    INIT_BUFFER(options);
    for (i = 0; i < rpaths.bufused; i++) {
        arg = rpaths.buf[i];
        if (arg) {
            if (options.bufused) WRITE_STR_BUFFER(options, ":");
            WRITE_BUFFER(options, arg, strlen(arg));
        }
    }
    WRITE_STR_BUFFER(options, "\0");
    SF(tmpi, setenv, -1, (PATHENV, options.buf, 1));
    FREE_BUFFER(options);

    if (userwpath) {
        SF(tmpi, setenv, -1, (WRITEENV, wpath, 1));
    } else {
        SF(tmpi, unsetenv, -1, (WRITEENV));
    }

    /* then run it */
    if (argi < argc) {
        execvp(argv[argi], argv + argi);
        fprintf(stderr, "[usrview] ");
        perror(argv[argi]);

        return 1;

    } else {
        return 0;

    }
}
Example #10
0
static int do_spi_io(struct spi_device* lp_dev, u8* lp_send_buffer, u8* lp_recv_buffer, 
                     int buffer_size)
{
    int ret_value;
	struct spi_message msg;
    struct spi_transfer xfer = 
        {
            .len = buffer_size, 
            .tx_buf = (void*)lp_send_buffer,
            .rx_buf = (void*)lp_recv_buffer,
            .speed_hz = 1000000,
        };

    spi_message_init(&msg);
    spi_message_add_tail(&xfer, &msg);

    dev_info(&lp_dev->dev, "spi io: transfer size = %d\n", buffer_size);
    
    ret_value = spi_sync(lp_dev, &msg);

    if (IS_SUCCESS(ret_value))
    {
        dev_info(&lp_dev->dev, "spi io done.\n");
    }
    
    dev_info(&lp_dev->dev, "do_spi_io ret_value = %d\n", ret_value);

    return ret_value;
}


int do_io_transaction(struct spi_device* lp_dev, 
                      _IN_ struct spi_io_context* lp_io_context,
                      _IN_ u8* const lp_send_buffer, int send_buffer_size,
                      _OUT_ u8* lp_recv_buffer, int recv_buffer_size, 
                      _OUT_ int* lp_recved_size )
{
    int ret_value = ER_FAILED;

    int total_trafster = 0;
    int one_time_transfer = 0;
    int total_receive_size = 0;

    int remain_send_count = send_buffer_size;
    int remain_recv_count = 0;

    int is_recved_vaild_fh = 0;

    struct buffer* lp_send_operator = NULL;
    struct buffer* lp_recv_operator = NULL;

    struct buffer dummy_send_buffer;
    struct buffer dummy_recv_buffer;

    struct buffer send_buffer;
    struct buffer recv_buffer;

    INIT_BUFFER(&dummy_send_buffer,
                lp_io_context->send_dummy_buffer,
                lp_io_context->send_dummy_buffer_size);
    
    INIT_BUFFER(&dummy_recv_buffer,
                lp_io_context->recv_dummy_buffer,
                lp_io_context->recv_dummy_buffer_size);
    
    INIT_BUFFER(&send_buffer, lp_send_buffer, send_buffer_size);

    INIT_BUFFER(&recv_buffer, lp_recv_buffer, recv_buffer_size);

    /*need some check here, but still in think.*/

    total_trafster = send_buffer_size;
    while(total_trafster > 0)
    {
        int send_buffer_is_dummy;
        int recv_buffer_is_dummy;

        /*
          Step1. try calc out transfer bye count
        */
        if (0 != BUFFER_REMAIN_LENGTH(send_buffer))
        {
            lp_send_operator = &send_buffer;
            send_buffer_is_dummy = FALSE;
        }
        else
        {
            lp_send_operator = &dummy_send_buffer;
            send_buffer_is_dummy = TRUE;
        }

        if (0 != remain_recv_count 
            && is_recved_vaild_fh)
        {
            lp_recv_operator = &recv_buffer;
            recv_buffer_is_dummy = FALSE;
        }
        else
        {
            lp_recv_operator = &dummy_recv_buffer;
            recv_buffer_is_dummy = TRUE;
        }

        if (is_recved_vaild_fh)
        {
            RESET_BUFFER(&dummy_send_buffer);
            RESET_BUFFER(&dummy_recv_buffer);

            if (send_buffer_is_dummy && recv_buffer_is_dummy)
            {
                one_time_transfer = 0;
            }
            else
            {
                one_time_transfer = MIN(BUFFER_REMAIN_LENGTH(*lp_send_operator),
                                        BUFFER_REMAIN_LENGTH(*lp_recv_operator));
            }
        }
        else
        {
            /*
              can't reset dummy recv buffer because it contain last time received
              splited data
             */
            one_time_transfer = MIN(BUFFER_REMAIN_LENGTH(*lp_send_operator), 
                                    BUFFER_REMAIN_LENGTH(dummy_recv_buffer));                      
        }

        if (0 == one_time_transfer)
        {
            /*caller's receive buffer is not enough case.*/
            if ( 0 != remain_recv_count)
            {
                ret_value = ER_NO_ENOUGH_RECV_BUFFER;
            }

            break;
        }

        /*
          Step 2. Prepare and do transfer
         */
        dev_info(&lp_dev->dev, "before do_spi_io\n");
        ret_value = do_spi_io(lp_dev,
                              BUFFER_PTR(*lp_send_operator), 
                              BUFFER_PTR(*lp_recv_operator),
                              one_time_transfer);
        if (IS_FAILED(ret_value))
        {
            dev_err(&lp_dev->dev, "do_spi_io() failed! \n");
            break;
        }
        dev_info(&lp_dev->dev, "after do_spi_io\n");

        lp_send_operator->index += one_time_transfer;
        lp_recv_operator->index += one_time_transfer;

        remain_send_count = MAX(0, remain_send_count - one_time_transfer);
        remain_recv_count = MAX(0, remain_recv_count - one_time_transfer);
        total_trafster -= one_time_transfer;

        /*
          Step 3. check if we received valid frame header
         */
        if (!is_recved_vaild_fh)
        {
            int total_payload_size;
            int contained_payload_size;
            int fh_start_index;
            int is_valid_fh;
            
            is_valid_fh = verify_frame_head_and_get_payload_size(lp_recv_operator->lp_ptr, 
                                                                 BUFFER_USED_LENGTH(*lp_recv_operator),
                                                                 &total_payload_size,
                                                                 &contained_payload_size,
                                                                 &fh_start_index);
            if (IS_SUCCESS(is_valid_fh))
            {
                int copy_size = contained_payload_size + SIZE_OF_FRAME_HEAD;
                int need_recv_buffer_size = total_payload_size + SIZE_OF_FRAME_HEAD;

                /*received new frame head!*/
                remain_recv_count = total_payload_size - contained_payload_size;
                
                /*received frame head, so we update total transfer count here*/
                total_trafster = MAX(remain_recv_count, remain_send_count);

                /*
                printf("[packege check]: total payload = %d, contained = %d, fh_start = %d\n",
                       total_payload_size,
                       contained_payload_size,
                       fh_start_index);
                */

                /*copy all valid data to actual receive buffer head*/

                if (need_recv_buffer_size > BUFFER_REMAIN_LENGTH(recv_buffer))
                {
                    ret_value = ER_NO_ENOUGH_RECV_BUFFER;
                    break;
                }
                
                /*do not reset buffer, because we now support
                  received mulit-frame in one io cycle.
                 */
                //RESET_BUFFER(&recv_buffer);                

                memcpy(BUFFER_PTR(recv_buffer), 
                       lp_recv_operator->lp_ptr + fh_start_index,
                       copy_size);

                /*
                  save total received size here to support receive mulit-frame
                 */
                total_receive_size += need_recv_buffer_size;
                
                recv_buffer.index += copy_size;
                recv_buffer.length = total_receive_size;

                //                pr_err("dump: index = %d, length = %d\n",
                //       recv_buffer.index, recv_buffer.length);

                is_recved_vaild_fh = TRUE;
            }
            else
            {
                int is_recved_hf_prefix = ER_FAILED;

                remain_recv_count = 0;

                //copy SIZEOF_FRAME_HEAD bytes from tail to head
                memcpy(dummy_recv_buffer.lp_ptr,
                       BUFFER_PTR_FROM_USED_TAIL(*lp_recv_operator, SIZE_OF_FRAME_HEAD),
                       SIZE_OF_FRAME_HEAD);

                dummy_recv_buffer.index = SIZE_OF_FRAME_HEAD;

                /*check if the last SIZE_OF_FRAME_HEAD bytes contained frame head prefix,
                  we will read more data if it contained, to resovle slice case
                 */
                is_recved_hf_prefix = verify_frame_head_prefix(BUFFER_PTR_FROM_USED_TAIL(*lp_recv_operator, SIZE_OF_FRAME_HEAD),
                                                               SIZE_OF_FRAME_HEAD);
                /*
                  check if the received data included frame head prefix 0x53
                 */
                if (IS_SUCCESS(is_recved_hf_prefix))
                {
                    total_trafster += BUFFER_REMAIN_LENGTH(dummy_recv_buffer);
                    /*
                    printf("set total_transfer = %d\n", total_trafster);
                    */
                }
                
                is_recved_vaild_fh = FALSE;
            }
        }
        else
        {
            /*
              if we already received one frame, but still has some data need
              send, we need change is_recved_vaild_fh = FALSE to prepare receive
              the next frame
             */
#if 1
            if (remain_send_count > 0
                && 0 == remain_recv_count)
            {
                is_recved_vaild_fh = FALSE;
                RESET_BUFFER(&dummy_recv_buffer);
                //pr_err("psh: note: try receive mulit-frame.\n");
            }
#endif

        }
    }

#if 1   
    if (IS_FAILED(ret_value))
    {
        /*
          dump recvied buffer
         */
        
        dump_buffer(lp_recv_operator->lp_ptr, BUFFER_USED_LENGTH(*lp_recv_operator));
    }
    else
    {
        //dump_buffer(recv_buffer.lp_ptr, BUFFER_USED_LENGTH(recv_buffer));
    }
#endif


    lp_recved_size ? *lp_recved_size = BUFFER_USED_LENGTH(recv_buffer) : 0;

    return ret_value;

}
Example #11
0
File: ast.c Project: GregorR/plof3
/* turn this PSL into a PSL AST */
struct PSLAstNode *pslToAst(unsigned char *psl, size_t psllen)
{
    size_t psli, si, curtemp;
    struct Buffer_PSLAstNode astout, aststack;
    struct PSLAstNode *cur;

    INIT_BUFFER(astout);
    INIT_BUFFER(aststack);
    curtemp = 1;

    /* make the arg */
    cur = allocPSLAstNode(pslast_arg, NULL, 0, 0, NULL);
    WRITE_BUFFER(aststack, &cur, 1);

    for (psli = 0; psli < psllen; psli++) {
        int arity = 0, pushes = 0;
        unsigned short cmd = psl[psli];
        unsigned char *data = NULL;
        size_t datasz = 0;

        /* maybe it has raw data */
        if (cmd >= psl_marker) {
            psli++;
            psli += pslBignumToInt(psl + psli, &datasz);

            /* make sure this doesn't go off the edge */
            if (psli + datasz <= psllen) {
                data = psl + psli;
                psli += datasz - 1;
            }
        }

        /* now get our arity info */
        switch (cmd) {
#define FOREACH(cmd)
#define LEAKY_PUSH(x)
#define ARITY(x) arity = x;
#define PUSHES(x) pushes = x;
#define LEAKA
#define LEAKB
#define LEAKC
#define LEAKP
#define LEAKALL
#include "psl-optim.c"
#undef FOREACH
#undef LEAKY_PUSH
#undef ARITY
#undef PUSHES
#undef LEAKA
#undef LEAKB
#undef LEAKC
#undef LEAKP
#undef LEAKALL

        default:
            arity = 0;
            pushes = 0;
        }

        /* if this has data, but the data is actually code, need to put that in place */
        if (cmd == psl_code || cmd == psl_immediate) {
            cur = pslToAst(data, datasz);
            data = NULL;
            datasz = 0;
            WRITE_BUFFER(aststack, &cur, 1);
            arity++;
        }

        /* if we need to flatten the stack (we're duplicating or removing stack elements), do so */
        if ((cmd >= psl_push0 && cmd <= psl_push7) || pushes != 1) {
            struct Buffer_PSLAstNode naststack;
            INIT_BUFFER(naststack);

            for (si = 0; si < aststack.bufused; si++) {
                if (aststack.buf[si]->cmd == pslast_gettemp) {
                    /* just copy it */
                    WRITE_BUFFER(naststack, aststack.buf + si, 1);

                } else {
                    cur = allocPSLAstNode(pslast_settemp, NULL, 0,
                                          1, aststack.buf + si);
                    cur->temp0 = curtemp;
                    WRITE_BUFFER(astout, &cur, 1);

                    cur = allocPSLAstNode(pslast_gettemp, NULL, 0,
                                          0, NULL);
                    cur->temp0 = curtemp;
                    WRITE_BUFFER(naststack, &cur, 1);

                    curtemp++;
                }
            }

            /* now replace aststack with the new one */
            aststack = naststack;
        }

        /* replace pushes by gettemps */
        if (cmd >= psl_push0 && cmd <= psl_push7) {
            int depth = cmd - psl_push0;
            if (aststack.bufused < depth + 1) {
                cur = allocPSLAstNode(psl_null, NULL, 0, 0, NULL);
            } else {
                cur = BUFFER_END(aststack)[-depth-1];
            }

            WRITE_BUFFER(aststack, &cur, 1);

            /* just perform pops */
        } else if (cmd == psl_pop) {
            if (aststack.bufused > 0)
                aststack.bufused--;

            /* resolve is weird */
        } else {
            /* figure out the mixed arity of an array */
            if (cmd == psl_array) {
                arity = 1;
                if (aststack.bufused > 0 && BUFFER_TOP(aststack)->cmd == psl_integer) {
                    /* OK, good, there's an integer. If it makes sense, get the value */
                    cur = BUFFER_TOP(aststack);
                    if (cur->children[0]->cmd == psl_raw) {
                        /* hooplah! Get the int val*/
                        struct PlofRawData *rd;
                        ptrdiff_t val;
                        cur = cur->children[0];
                        rd = newPlofRawDataNonAtomic(cur->datasz);
                        memcpy(rd->data, cur->data, cur->datasz);

                        val = parseRawInt(rd);

                        /* and extend the arity */
                        if (val > 0) arity += val;
                    }
                }
            }

            /* make sure we have all the children */
            while (aststack.bufused < arity) {
                /* need to put nulls at the start */
                while (BUFFER_SPACE(aststack) < 1) EXPAND_BUFFER(aststack);
                memmove(aststack.buf + 1, aststack.buf, aststack.bufused * sizeof(struct PSLAstNode *));
                aststack.buf[0] = allocPSLAstNode(psl_null, NULL, 0, 0, NULL);
                aststack.bufused++;
            }

            /* and create the current one */
            cur = allocPSLAstNode(cmd, data, datasz, arity, BUFFER_END(aststack) - arity);
            aststack.bufused -= arity;

            /* handle resolve's weird push */
            if (cmd == psl_resolve) {
                struct PSLAstNode *tmp;
                tmp = allocPSLAstNode(pslast_gettemp, NULL, 0, 0, NULL);
                tmp->temp0 = curtemp;
                WRITE_BUFFER(aststack, &tmp, 1);

                tmp = allocPSLAstNode(pslast_gettemp, NULL, 0, 0, NULL);
                tmp->temp0 = curtemp + 1;
                WRITE_BUFFER(aststack, &tmp, 1);

                cur->temp0 = curtemp;
                cur->temp1 = curtemp + 1;

                curtemp += 2;
            }

            /* put it either on the stack or in our instruction list */
            if (pushes == 1) {
                WRITE_BUFFER(aststack, &cur, 1);
            } else {
                WRITE_BUFFER(astout, &cur, 1);
            }

            /* FIXME: array, resolve special */
        }
    }

    WRITE_BUFFER(astout, aststack.buf, aststack.bufused);
    return allocPSLAstNode(pslast_seq, NULL, 0, astout.bufused, astout.buf);
}
Example #12
0
int main(int argc, char **argv)
{
    FILE *fh;
    struct Buffer_psl file;
    char *filenm = NULL, *arg;
    struct Buffer_psl psl;
    int i, dot;
    struct PSLAstNode *ast;

    GC_INIT();

    dot = 0;
    for (i = 1; i < argc; i++) {
        arg = argv[i];
        if (arg[0] == '-') {
            if (!strcmp(arg, "-d")) {
                dot = 1;
            } else {
                usage();
                return 1;
            }
        } else {
            filenm = arg;
        }
    }

    if (filenm == NULL) {
        usage();
        return 1;
    }

    /* load in the file */
    INIT_BUFFER(file);

    /* find the file */
    fh = fopen(filenm, "rb");
    if (fh == NULL) {
        perror(filenm);
        return 1;
    }

    /* read it */
    READ_FILE_BUFFER(file, fh);
    WRITE_BUFFER(file, "\0", 1);
    file.bufused--;
    fclose(fh);

    /* FIXME: bounds checking */

    /* check what type of file it is */
    psl = readPSLFile(file.bufused, file.buf);

    ast = pslToAst(psl.buf, psl.bufused);
    if (!dot) {
        dumpPSLAst(stdout, ast, 0);
    } else {
        printf("digraph {\nnodesep=0;\nranksep=0;\n");
        dumpPSLAstDot(stdout, ast);
        printf("}\n");
    }
    return 0;
}
Example #13
0
 struct Buffer_char cunparseStrLiteral(Token *tok)
{
    struct Buffer_char buf;
    size_t i;
    char xspace[3];
    char *sl = tok->tok;
    char delimiter = sl[0];
    INIT_BUFFER(buf);

    for (i = 1; sl[i]; i++) {
        char w = sl[i];

        if (sl[i] == delimiter) break;

        if (sl[i] == '\\') {
            /* an escape sequence */
            switch (sl[++i]) {
                case '0':
                    w = '\0';
                    break;

                case 'b':
                    w = '\b';
                    break;

                case 'f':
                    w = '\f';
                    break;

                case 'n':
                    w = '\n';
                    break;

                case 'r':
                    w = '\r';
                    break;

                case 't':
                    w = '\t';
                    break;

                case 'x':
                    if (sl[++i]) {
                        xspace[0] = sl[i];
                        if (sl[++i]) {
                            xspace[1] = sl[i];
                            xspace[2] = '\0';
                        } else xspace[1] = '\0';
                    } else xspace[0] = '\0';
                    w = (char) strtol(xspace, NULL, 16);
                    break;

                default:
                    w = sl[i];
                    break;
            }
        }

        WRITE_ONE_BUFFER(buf, w);
    }

    WRITE_ONE_BUFFER(buf, '\0');

    return buf;
}