Esempio n. 1
0
int main(int argc, char** argv) {
    int fh;
    char buffer[MAXBYTES];
    if (argc != 2) {
		//Parameter vorhanden?
        if (argc < 2) {
            printf("Keinen Dateinamen angegeben!");
            return EXIT_FAILURE;
		//Nur ein Parameter eingeben?
        } else {
            printf("Bitte nur einen Dateinamen angeben!");
            return EXIT_FAILURE;
        }
    } else {
        if ((fh = open(*++argv, O_RDONLY)) == -1) {
            perror(*argv);
        } else {
			//Auslesen der Offsets 0x006d und 0x0011c für Kameramodell und Datum
            read_offset(fh, -0x006d, buffer);
            printf("%s \n", buffer);
            read_offset(fh, 0x011c, buffer);
            printf("%s \n", buffer);
			//Ausgabe im Falle eines Schliessungsfehlers
            if ((close(fh)) == -1)
                perror("close() error!");
        }
    }
    return (EXIT_SUCCESS);
}
Esempio n. 2
0
static int decode_C3(void)
{
	int	secoff,tmpoff,c;
	
	secoff=0;
	do 
	{
		if (secoff)
			tmpoff = read_offset(fin);
		else
			tmpoff = fgetc(fin);

		if( tmpoff == EOF )
		{
			show_file_error( fin );
			return 0;
		}

		for (; secoff<tmpoff; secoff++) 
		{
			buf[secoff] = fgetc(fin);
			if( feof(fin) )
			{
				show_file_error( fin );
				return 0;
			}

		}
		if (secoff == (int)secsize)
			break;

		tmpoff = read_offset(fin);
		c = fgetc(fin);
		if( tmpoff == EOF || c == EOF )
		{
			show_file_error( fin );
			return 0;
		}

		for (; secoff<tmpoff; secoff++) 
		{
			buf[secoff] = c;
		}
	} while(secoff < (int)secsize);

	if( !write_sector(fout) )
		return 0;
	return 1;
}
Esempio n. 3
0
/*---------------------------------------------------------------------------*/
static int alsps_update_info(struct lps_priv *lps)
{
    int err = -EINVAL;
    unsigned int als_dat, ps_dat;
	
    unsigned int offset_data=0;
    unsigned int ps_offset;
   if (!bUpToDate)
   {
    read_offset(&offset_data);
    ps_offset = offset_data;
     FLPLOGE("alsps_update_info set ps_offset: %d\n", ps_offset);
    if ((err = ioctl(lps->fd, ALSPS_SET_PS_CALI, &ps_offset))) {
        FLPLOGE("set ps_offset: %d(%s)\n", errno, strerror(errno));
    }
    else
	{
	 bUpToDate = true;
	}
   }
   
    if (lps->fd == -1) {
        FLPLOGE("invalid fd\n");
        return -EINVAL;
    } else if ((err = ioctl(lps->fd, ALSPS_GET_PS_RAW_DATA, &ps_dat))) {
        FLPLOGE("read ps  raw: %d(%s)\n", errno, strerror(errno));
        return err;
    } else if ((err = ioctl(lps->fd, ALSPS_GET_ALS_RAW_DATA, &als_dat))) {
        FLPLOGE("read als raw: %d(%s)\n", errno, strerror(errno));
        return err;
    }
    lps->als_raw = als_dat;
    lps->ps_raw = ps_dat;
    return 0;
}
Esempio n. 4
0
// xiangfei.peng 20130513
extern int phil_add_alsps_cali_in_entry(struct lps_priv *lps)
{
	int err = -EINVAL;
	unsigned int offset_data = 0;
	read_offset(&offset_data);
	FLPLOGD("[phil] cali in entry get ps_offset: %d\n", offset_data);
	if(lps->fd < 0)
	{
		FLPLOGE("[phil] alsps open failed!\n");
		return err;
	}
	if((err = ioctl(lps->fd, ALSPS_SET_PS_CALI, &offset_data))) {
		FLPLOGE("set ps_offset: %d(%s)\n", errno, strerror(errno));
	}
	return 0;
}
Esempio n. 5
0
int main(int argc, char **argv)
{
	char offset_file[MAX_FILE_NAME];
	char *file_name, *prog;
	ino_t inode;
	off_t offset;

	prog = argv[0];

	if (argc != 2) {
		fprintf(stderr, "no filename specified\n");
		usage(prog);
		return 1;
	}

	file_name = argv[1];

	if (strlen(OFFSET_EXT) + strlen(file_name) + 1 > MAX_FILE_NAME) {
		fprintf(stderr, "%s: filename too long (max is %ld)\n",
			prog, MAX_FILE_NAME - strlen(OFFSET_EXT) - 1);
		return 1;
	}
	strncat(offset_file, file_name,
		sizeof(offset_file) - strlen(offset_file) - 1);
	strncat(offset_file, OFFSET_EXT,
		sizeof(offset_file) - strlen(offset_file) - 1);

	if (read_offset(offset_file, &inode, &offset) != 0) {
		fprintf(stderr, "%s: can't open offset file: %s\n",
			prog, strerror(errno));
		return 1;
	}

	if (print_logs(file_name, &inode, &offset) != 0) {
		fprintf(stderr, "%s: can't read '%s': %s\n",
			prog, file_name, strerror(errno));
		return 1;
	}

	if (write_offset(offset_file, inode, offset) != 0) {
		fprintf(stderr, "%s: can't write offset file: %s\n",
			prog, strerror(errno));
		return 1;
	}

	return 0;
}
Esempio n. 6
0
static size_t lha_lh1_read(void *data, uint8_t *buf)
{
    LHALH1Decoder *decoder = data;
    size_t result;
    uint16_t code;

    result = 0;

    // Read the next code from the input stream.

    if (!read_code(decoder, &code)) {
        return 0;
    }

    // The code either indicates a single byte to be output, or
    // it indicates that a block should be copied from the ring
    // buffer as it is a repeat of a sequence earlier in the
    // stream.

    if (code < 0x100) {
        output_byte(decoder, buf, &result, (uint8_t) code);
    } else {
        unsigned int count, start, i, pos, offset;

        // Read the offset into the history at which to start
        // copying.

        if (!read_offset(decoder, &offset)) {
            return 0;
        }

        count = code - 0x100U + COPY_THRESHOLD;
        start = decoder->ringbuf_pos - offset + RING_BUFFER_SIZE - 1;

        // Copy from history into output buffer:

        for (i = 0; i < count; ++i) {
            pos = (start + i) % RING_BUFFER_SIZE;

            output_byte(decoder, buf, &result,
                        decoder->ringbuf[pos]);
        }
    }

    return result;
}
Esempio n. 7
0
static int decode_C4(void)
{
	int	secoff,tmpoff;

	tmpoff = read_offset(fin);
	if( tmpoff == EOF )
	{
		show_file_error( fin );
		return 0;
	}

	for (secoff=tmpoff; secoff<(int)secsize; secoff++) {
		buf[secoff]=fgetc(fin);
		if( feof(fin) )
		{
			show_file_error( fin );
			return 0;
		}
	}
	if( !write_sector(fout) )
		return 0;
	return 1;
}
Esempio n. 8
0
off_t
FSIO::read_seek(off_t new_off, int whence)
{
    // reset error
    err = 0;

    // Compute actual offset
    off_t offset = read_offset();
    switch (whence)
    {
	case SEEK_SET:
	    break;
	case SEEK_CUR:
	    new_off += offset;
	    break;
#if 0 /* XXX PSH - SIO no longer supports file_size */
	case SEEK_END:
	    new_off += file_size();
	    break;
#endif /* 0 */
	default:
	    err = EINVAL;
	    return 0;
    }

    // see if seek is within the current region
    if (reader.creg->off <= new_off && new_off <= offset + _read_count())
    {
	reader.ptr += new_off - offset;
	return new_off;
    }

    offset = new_off;

    // relocate creg
    if (reader.creg->refcount == 0)
    {
	Byte* base = reader.remove(reader.creg);
	if (base)
	    delete[] base;
    }
    else
    {
	reader.creg->limit = reader.end;	// adjust limit
    }

    Region** rp;
    Region *reg = reader.find(new_off, rp);

    if (reg)
    {
	reader.ptr = reg->base + new_off - reg->off;
	// XXX use another field in reg so that we can continue using
	// already allocated space past where we left off. May be.
	reader.end = reg->limit;
	new_off = reg->off + reg->limit - reg->base;
    }
    else
    {
	reg = new Region;
	reg->next = *rp;
	*rp = reg;
	reg->set_buf(new Byte[bufsize], bufsize, new_off);
	reader.ptr = reader.end = reg->base;
    }
    reader.creg = reg;
    reader.eof = 0;
    if (io->seek(new_off, SEEK_SET) == -1)
    {
	err = (int)io->error();
	// XXX clean up creg -- its offset is not valid
	return 0;
    }
    return offset;
}
Esempio n. 9
0
Byte*
FSIO::_read_alloc(int& size)
{
    int count = _read_count();

    if (count == 0 && (reader.eof || err))
	return 0;

    ASSERT(reader.ptr <= reader.end);

    off_t off = read_offset();

    Byte* b = reader.ptr;
    reader.ptr += size;

    /*
     * if there isn't enough space in the current buffer,
     * update the current region.
     */
    if (reader.ptr > reader.creg->limit)
    {
	int bsize = roundup(size, bufsize);
	Byte* oldbuffer = 0;

	if (reader.creg->refcount != 0)
	{
	    /* creg is in use => allocate a new region */
	    reader.creg->limit = b;
	    reader.creg = new Region(reader.creg);
	    reader.creg->set_buf(new unsigned char[bsize], bsize);
	}
	else if (bsize != bufsize)
	{
	    /* need a bigger buffer => allocate a new buffer */
	    oldbuffer = reader.creg->base;
	    reader.creg->set_buf(new unsigned char[bsize], bsize);
	} /* else reuse existing buffer and region */

	reader.creg->flush_off = reader.creg->off = off;

	/*
	 * if there is unused but read data in the
	 * old buffer, copy it to the new buffer.
	 */
	if (count)
	    memmove(reader.creg->base, b, count);
	if (oldbuffer)
	    delete[] oldbuffer;
	b = reader.creg->base;
	reader.ptr = b + size;
	reader.end = b + count;
    }

    int readcount = (int)io->read(reader.end, _read_space());

    if (readcount <= 0)
    {
	if (readcount == 0)
	    reader.eof = 1;
	else if (io->error() != EWOULDBLOCK)
	{
	    err = (int)io->error();
	    DPRINTF(D_INFO, ("read_alloc error %d count %d\n", err, count));
	}

	/* return if the buffer is empty and we have seen eof or err */
	if (count == 0 && (reader.eof || err))
	{
	    reader.ptr = reader.end;
	    return 0;
	}

    }
    else
	reader.end += readcount;

    /* truncate request if not enough data was read in */
    if (reader.ptr > reader.end)
    {
	size = reader.end - b;
	ASSERT(size >= 0);
	reader.ptr = reader.end;
    }
    reader.creg->refcount++;
    return b;
}
Esempio n. 10
0
/**
 * Load a graph file but using a set of externally provided buffers 
 * for the data.  This might be useful in the case that you want to managed
 * memory for the graph independently of this function.  
 *
 * To maintain the graph, only the bvgraph structure, and the two
 * external ararys: gmemory and offsets are required.  Consequently,
 * a bvgraph structure can always be patched together out of these
 * functions.
 *
 * One common way of using this function would be to first
 * load a graph on the disk (bvgraph_load(...,offset_step=-1))
 * and then call bvgraph_required_memory with an alternative
 * offset step.
 *
 * @param[in] g a newly created bvgraph structure
 * @param[in] filename the base filename for a set of bvgraph files, 
 * so filename.graph and filename.properties must exist.
 * @param[in] offset_step controls how many offsets are loaded, 
 * if offset_step = -1, then the graph file isn't loaded into memory
 * if offset_step = 0, then the graph file is loaded, but no offsets
 * no other values are supported at the moment.
 * @param[in] gmemory an arry of size gmemsize for the graph 
 * (if NULL, then this parameter is treated as internal memory)
 * @param[in] gmemsize the size of the gmemory block
 * @param[in] offsets an array of offsets
 * (if NULL, then this parameter is treated as internal memory)
 * @param[in] offsetssize the number of offsets
 * @return 0 if successful;
 * bvgraph_load_error_filename_too_long - indicates the filename was too long
 */
int bvgraph_load_external(bvgraph *g,
                          const char *filename, unsigned int filenamelen, int offset_step,
                          unsigned char *gmemory, size_t gmemsize,
                          unsigned long long* offsets, int offsetssize)
{
    int rval = 0;

    assert(offset_step == 0 || offset_step == -1 || offset_step == 1);

    if (filenamelen > BVGRAPH_MAX_FILENAME_SIZE-1) { 
        return bvgraph_load_error_filename_too_long;
    }
    
    memset(g,0,sizeof(bvgraph));

    strncpy(g->filename, filename, filenamelen);
    g->filename[filenamelen] = '\0';
    g->filenamelen = filenamelen;

    g->offset_step = offset_step;

    set_defaults(g);

    rval = parse_properties(g);
    // check for any errors
    if (rval != 0) { return rval; }

    // continue processing
    if (offset_step >= 0) 
    {
        if (offset_step == 0 || offset_step == 1) {    //modified 082911
            // in this case, we ust load the graph
            // file into memory

            // first get the filesize
            unsigned long long graphfilesize;
            char *gfilename = strappend(g->filename, g->filenamelen, ".graph", 6);
            rval = fsize(gfilename, &graphfilesize);
            free(gfilename);
            if (rval) { 
                return bvgraph_call_io_error;
            }

            if (gmemory != NULL) {
                // they want to use their own memory, make sure
                // they allocated enough!
                if (gmemsize < graphfilesize) {
                    return bvgraph_load_error_buffer_too_small;
                }
                g->memory = gmemory;
                g->memory_size = gmemsize;
                g->memory_external = 1;
            } else {
                // we have to allocate the memory ourselves
                g->memory_size = (size_t)graphfilesize;
                g->memory = malloc(sizeof(unsigned char)*g->memory_size);
                if (!g->memory) {
                    return bvgraph_call_out_of_memory;
                }
                g->memory_external = 0;
            }

            // now read the file
            gfilename = strappend(g->filename, g->filenamelen, ".graph", 6);
            {
                size_t bytesread = 0;
                FILE *gfile = fopen(gfilename, "rb");
                free(gfilename);
                if (!gfile) {
                    return bvgraph_call_io_error;
                }
                bytesread = fread(g->memory, 1, g->memory_size, gfile);
                if (bytesread != graphfilesize) {
                    return bvgraph_call_io_error;
                }
                fclose(gfile);
            }
            // we now have the graph in memory!

            if (offset_step == 1) {        //modified 082911
                // now read the file
                char *ofilename = strappend(g->filename, g->filenamelen, ".offsets", 8);
                bitfile bf;
                long long off = 0;
                int64_t i;
                FILE *ofile = fopen(ofilename, "rb");

                if (offsets != NULL) {
                    g->offsets = offsets;
                    g->offsets_external = 1;
                } else {
                    // we have to allocate the memory ourselves
                    g->offsets = (unsigned long long*) malloc(sizeof(unsigned long long)*g->n);
                    g->offsets_external = 0;
                }

                if (ofile) {
                    rval = bitfile_open(ofile, &bf);
                    if (rval) {
                        return bvgraph_call_io_error;
                    }
                    for (i = 0; i < g->n; i++){
                        off = read_offset(g, &bf) + off;
                        g->offsets[i] = off;
                    }
                } else {
                    // need to build the offsets
                    bvgraph_iterator git;
                    int rval = bvgraph_nonzero_iterator(g, &git);
                    if (rval) { return rval; }
                    g->offsets[0] = 0;
                    for (; bvgraph_iterator_valid(&git); bvgraph_iterator_next(&git)) {
                        if (git.curr+1 < g->n) {
                            g->offsets[git.curr+1] = bitfile_tell(&git.bf);
                        }
                    }
                    bvgraph_iterator_free(&git);
                }
            }
        }
    }
    else
    {
        g->memory_size = 0;
    }
     
    // presently the othercases are not supported, so we don't have to
    // worry about them!

    return (0);
}
Esempio n. 11
0
static value_ptr extract_object(bplist_info_ptr bplist, uint64_t objectRef)
{
    uint64_t offset;
    value_ptr result = NULL;
    uint8_t objectTag;
    
    if (objectRef >= bplist->object_count) {
        // Out-of-range object reference.
        bplist_log("Bad binary plist: object index is out of range.\n");
        return NULL;
    }
        
    // Use cached object if it exists
    result = cache_lookup(bplist->cache, objectRef);
    if (result != NULL)  return result;
        
    // Otherwise, find object in file.
    offset = read_offset(bplist, objectRef);
    if (offset > bplist->length) {
        // Out-of-range offset.
        bplist_log("Bad binary plist: object outside container.\n");
        return NULL;
    }
    objectTag = *(bplist->data_bytes + offset);
    switch (objectTag & 0xF0) {
    case kTAG_SIMPLE:
        result = extract_simple(bplist, offset);
        break;
                
    case kTAG_INT:
        result = extract_int(bplist, offset);
        break;
                        
    case kTAG_REAL:
        result = extract_real(bplist, offset);
        break;
                        
    case kTAG_DATE:
        result = extract_date(bplist, offset);
        break;
                        
    case kTAG_DATA:
        result = extract_data(bplist, offset);
        break;
                        
    case kTAG_ASCIISTRING:
        result = extract_ascii_string(bplist, offset);
        break;
                        
    case kTAG_UNICODESTRING:
        result = extract_unicode_string(bplist, offset);
        break;
        
    case kTAG_UID:
        result = extract_uid(bplist, offset);
        break;
        
    case kTAG_ARRAY:
        result = extract_array(bplist, offset);
        break;
        
    case kTAG_DICTIONARY:
        result = extract_dictionary(bplist, offset);
        break;
        
    default:
        // Unknown tag.
        bplist_log("Bad binary plist: unknown tag 0x%X.\n", 
                   (objectTag & 0x0F) >> 4);
        result = NULL;
    }
    
    // Cache and return result.
    if (result != NULL)  
        cache_insert(&bplist->cache, objectRef, result);
    return result;
}
Esempio n. 12
0
Link interpret(Link codeblock_link ,  Link This, Link Arg){
    
    CallEnv env = callenv_new_root( codeblock_link, This, Arg);
    LinkStack stack = env->stack;
    
    
    Link b          = NULL;
    Link link       = NULL;
    Link parent     = NULL;
    Link child_key  = NULL;
    
    Link pusher     = NULL; // Anything in this variable gets pushed onto the stack
    Link trapped    = NULL; // This is the last critical caught by the trap operator
    
    int    delta = 0; // jump delta

    /* Main interpreter loop */
    while(1){

        switch( *(env->current++) ){

            case INTRO:
                env->current+=4;
                break;

            case ALLOC_MODULE:
                delta = read_offset(env);
                env->module->global_vars = linkarray_new(delta);
                break;
            
            case ALLOC_LOCAL:
                delta = read_offset(env);
                env->local = linkarray_new(delta);
                break;
                                
            case NO_OP:
                break;
            
            case RETURN: // if there is something on the env->stack stack pop it off and return it, if not return null link
                if (   stack_length(stack) - env->stack_offset ){
                    pusher = stack_pop(stack);
                }else{
                    pusher = object_create(Global->null_type);
                }
                goto done;

            case RAISE: // if there is something on the stack stack pop it off and return it, if not return null link
            
                if (  stack_length(stack) - env->stack_offset ){
                    pusher = create_critical(stack_pop(stack));
                }else{
                    pusher = create_critical(object_create(Global->null_type));
                }
                goto done;

            case PUSH_LEX:
                delta = read_offset(env);
                //fprintf(stderr , "push lex [%i]    %p\n", delta,env->function->value.codeblock->lexicals);
                pusher = link_dup(env->function->value.codeblock->lexicals->vars[delta]);
                break;
                
            case STORE_LEX:
                delta = read_offset(env);
                //fprintf(stderr , "storing lex [%i]    %p\n", delta,env->function->value.codeblock->lexicals);
                b = env->function->value.codeblock->lexicals->vars[delta];
            
                if (b){
                    if  ( (b->type == Global->function_type) && 
                          (b->value.codeblock->lexicals == env->function->value.codeblock->lexicals)
                        )  b->value.codeblock->lexical_cycles--;
                    link_free(b);
                }
                
                b = link_dup(stack_peek(stack));
                if  ( (b->type == Global->function_type) && 
                      (b->value.codeblock->lexicals == env->function->value.codeblock->lexicals)
                    )  b->value.codeblock->lexical_cycles++;
                
                env->function->value.codeblock->lexicals->vars[delta] = b;
                
                break;
            
            case DEF:
                if (env->Def) link_free(env->Def);
                env->Def = stack_pop(env->stack);
                pusher = link_dup(env->Def);
                break;
            
            case PUSH_DEF:
                if ( ! env->Def){
                    pusher = exception("NoDefObject",NULL, NULL);
                }
                pusher = link_dup(env->Def);
                break;
                
                
                
            case ALLOC_LEXICAL:
                delta = read_offset(env);
                lexicals_alloc( env->function, delta);
                //env->lexical_root = 1;
                break;
                
            case STORE_ARG:
                delta = read_offset(env);
                
                if (env->Arg->value.array->length  > delta){
                    retry_store_arg:
                    env->Arg->value.array->links[delta] =  link_dup( stack_peek(stack) );
                }else{
                    array_push(env->Arg, NULL);
                    goto retry_store_arg;
                } 
                break;
                
            case PUSH_ARG:
                delta = read_offset(env);
                if (env->Arg->value.array->length  > delta){
                    pusher = link_dup(  env->Arg->value.array->links[delta]);
                }else{
                    pusher = exception("ArgsIndexOutOfBounds", NULL, NULL);
                }
            
                break;
                
            case STORE_GVAR:
                delta = read_offset(env);
                if (env->module->global_vars->links[delta]){
                    link_free(env->module->global_vars->links[delta]);
                }
                env->module->global_vars->links[delta] = link_dup( stack_peek(stack) );
                break;

            case STORE_VAR:
                delta = read_offset(env);

                if (env->local->links[delta]){
                    link_free(env->local->links[delta]);
                }
            
                env->local->links[delta] = link_dup( stack_peek(stack) );
                break;

            case STORE_CHILD:
                link        = stack_pop(stack); // value
                child_key   = stack_pop(stack); // key to find the child
                parent      = stack_pop(stack); // parent to look in
                pusher = object_addChild(parent, link, child_key);
                goto STORE_COMMON;

            case STORE_ATTR:
                link           = stack_pop(stack); // value
                child_key      = stack_pop(stack); // key to find the child
                parent         = stack_pop(stack); // parent to look in
                pusher = addAttr(parent, link,child_key);
                goto STORE_COMMON;
                
            STORE_COMMON:
                if (! pusher){
                    pusher = exception("AssignError", NULL, NULL);
                    link_free(link);
                }
            
                link_free(child_key);
                link_free(parent);
                break;

            case LT:
                delta = compare(env);
                pusher = create_numberi( (delta < 0)  ? 1 : 0 );
                break;

            case GT:
                delta = compare(env);
                pusher = create_numberi( (delta > 0)  ? 1 : 0 );
                break;

            case EQ:
                delta = compare(env);
                pusher = create_numberi( (delta == 0)  ? 1 : 0 );
                break;

            case NE:
                delta = compare(env);
                pusher = create_numberi( (delta == 0)  ? 0 : 1 );
                break;

            case LE:
                delta = compare(env);
                pusher = create_numberi( (delta <= 0)  ? 1 : 0 );
                break;

            case GE:
                delta = compare(env);
                pusher = create_numberi( (delta >= 0)  ? 1 : 0 );
                break;
        
            case CMP:
                delta = compare(env);
                pusher = create_numberi( delta );
                break;
            
            case OR:
            case AND:
                break;

            case SUB:
                b = stack_pop(env->stack);
                link = stack_pop(env->stack);
            
                if ( (link->type == Global->number_type) && (link->type == b->type)){
                    pusher = create_number(link->value.number - b->value.number);
                    link_free(link);
                    link_free(b);
                    break;
                }            
            
                pusher = object_op_minus(link,b);
                link_free(link);
                link_free(b);
            
                break;
            
            case ADD:
                b = stack_pop(env->stack);
                link = stack_pop(env->stack);
            
                if ( (link->type == Global->number_type) && (link->type == b->type)){
                    pusher = create_number(link->value.number + b->value.number);
                    link_free(link);
                    link_free(b);
                    break;
                }            
            
                pusher = object_op_plus(link,b);
                link_free(link);
                link_free(b);
                
                break;
                        
            case DIV:
                binary_op(env , object_op_divide);
                break;
            
            case MULT:
                binary_op(env , object_op_multiply);
                break;
            
            case MOD:
                binary_op(env , object_op_modulus);
                break;
            
            case POW:
                binary_op(env , object_op_power);
                break;
            
            case NEG:
                unary_op(env, object_op_neg);
                break;
            
            case NOT:
                link = stack_pop(stack);
                pusher = create_numberi(  (object_is_true(link))  ?  0 : 1 );
                link_free(link);
                break;

            case TEST:
            case ELSE:
                break;

            case DO:
                delta = read_offset(env);
                link  = codeblock_literal2( env->function->value.codeblock->parent, delta  );
                if (env->function->value.codeblock->lexicals) {
                    lexicals_attach( env->function->value.codeblock->lexicals, link);
                }
                env = callenv_new_doblock(env,link);
                break;
            
            case PUSH_ARRAY:
                delta = read_offset(env);
                pusher =  array_new_subarray( stack , delta);
                break;
                
            case CALL:
                link   = stack_pop(stack);     // the arguments in an array
                b      = stack_pop(stack);     // the function that gets called
                parent = link_dup(env->This);  // caller
                goto CALL_COMMON;

            
            case CALL_ATTR:            
                link       = stack_pop(stack);    // arguments
                child_key  = stack_pop(stack);    // name of the function
                parent     = stack_pop(stack);    // caller
                b = getAttr(parent,child_key); // the function that gets called           
                link_free(child_key); // no longer need the attributes key
            
                if (! b) {
                    pusher = exception("AttrNotFound", NULL, NULL);
                    break;
                }
                goto CALL_COMMON;
                
            case CALL_CHILD:
                link       = stack_pop(stack);     // ARG
                child_key  = stack_pop(stack);
                parent     = stack_pop(stack);     // THIS
                b = object_getChild(parent,child_key);
                link_free(child_key);
                goto CALL_COMMON;

            CALL_COMMON:
                /* function type so we can call it inline */
                if (b->type == Global->function_type){
                    env = callenv_new_function(env, b, parent, link); // ce , func,this, arg

                /* Not a CodeBlock so we have to use its virtual call function */
                }else{
                    pusher = object_call(b,  parent, link);// function, caller, args
                    link_free(link);
                    if (parent) link_free(parent);
                    link_free(b);
                    if (! pusher) pusher = object_create(Global->null_type);
                }
                break;

            case DEL_CHILD:
                child_key      = stack_pop(stack); // key to find the child
                parent         = stack_pop(stack); // parent to look in

                /* delete child from container */
                pusher = object_delChild(parent,child_key);
                if (! pusher) pusher = exception("ChildNotFound", object_getString(child_key), NULL);
                        
                link_free(child_key);
                link_free(parent);
                break;                
                
            case DEL_ATTR:
                child_key      = stack_pop(stack); // key to find the child
                parent         = stack_pop(stack); // parent to look in

                /* delete attr from container */
                pusher = delAttr(parent,child_key);
                if (! pusher) pusher = exception("AttrNotFound", object_getString(child_key), NULL);

                link_free(child_key);
                link_free(parent);
                break;                
                
            case GET_CHILD:
                child_key      = stack_pop(stack); // key to find the child
                parent         = stack_pop(stack); // parent to look in

                pusher = object_getChild(parent, child_key);            
                if (! pusher) pusher = exception("ChildNotFound", object_getString(child_key), NULL);

                link_free(parent);
                link_free(child_key);
                break;

            case GET_ATTR:
                child_key      = stack_pop(stack); // key to find the child
                parent         = stack_pop(stack); // parent to look in

                pusher = getAttr(parent, child_key);
                if (! pusher) pusher = exception("AttrNotFound", object_getString(child_key), NULL);

                link_free(parent);
                link_free(child_key);
                break;

            case TRAP:
                break;

            case CLEAR:
                for ( delta = stack_length( stack ) ; delta > env->stack_offset ; delta--){
                    link_free( stack_pop(stack) );    
                }    
                break;
            
            case STOP:
                break;

            done:
            case END:
                for ( delta = stack_length( stack ) ; delta > env->stack_offset ; delta--){
                    link_free( stack_pop(stack) );    
                }    
                addBacktrace(pusher, env->function, env->linenum);
                env = callenv_free(env);

                if (! env) goto end;
                
                if (! pusher) pusher = object_create(Global->null_type);
                break;

            /* JUMPS */
            case JIT:  /* Jump if true */
                delta = read_offset(env);
                link = stack_peek(stack);
                if ( link->type->is_true(link) )  env->current = env->start+delta;
                break;

            case JIF:  /* Jump if false */
                delta = read_offset(env);
                link = stack_peek(stack);
                if ( ! link->type->is_true(link) )  env->current = env->start+delta;
                break;
                

            case JIF_POP:  /* Pop value then jump if value is false,  */
                delta = read_offset(env);
                link = stack_pop(stack);
                if ( ! link->type->is_true(link) )  env->current = env->start+delta;
                link_free(link);
                break;
                
            case JUMP:  /* Absolute jump */
                delta = read_offset(env);
                env->current = env->start + delta;
                break;

            case JINC: /* Jump If Not Critical */
                delta = read_offset(env);
                env->current = env->start+delta;
                break;
                
              jinc_critical:
                delta = read_offset(env);
            
                if (trapped) link_free(trapped);
                trapped = pusher->value.link;
                pusher->value.link = NULL;
                link_free(pusher);
                pusher = NULL;
                break;

            case PUSH_NULL:
                pusher = create_null();
                break;

            case PUSH_NUM:
                pusher = create_number( *((number_t *)env->current) );
                env->current+= sizeof(number_t);
                break;
            
            case PUSH_STR:
                delta = read_offset(env);
                pusher = create_string_literal( env->start + delta  );
                break;

            case PUSH_GVAR:
                delta = read_offset(env);
                pusher = link_dup(env->module->global_vars->links[delta]);
            
                if (! pusher){
                    pusher = exception("GlobalVariableUsedBeforeSet",NULL,NULL);
                }
                break;
            
            case PUSH_VAR:
                delta = read_offset(env);
             
                pusher = link_dup(env->local->links[delta]);
                
                if (! pusher){
                    pusher = exception("VariableUsedBeforeSet",NULL,NULL);;
                }
                break;
            
            case PUSH_BLOCK:
                delta = read_offset(env);
                pusher  = codeblock_literal2( env->function->value.codeblock->parent, delta  );
                if (env->function->value.codeblock->lexicals) {
                    lexicals_attach( env->function->value.codeblock->lexicals, pusher);
                }
                break;

            case PUSH_SYS:
                pusher = link_dup(Global->SYS_MODULE);
                break;
            
            case PUSH_MODULE:
                pusher = link_dup( env->function->value.codeblock->parent);
                break;
            
            case TYPEOF:
                link = stack_pop(stack);
                pusher = link_dup( link->type->type_link);
                link_free(link);
                break;
            
            case PUSH_THIS:
                pusher = link_dup(env->This);
                break;

            case PUSH_SELF:
                pusher = link_dup(env->Self);
                break;
            
            case PUSH_ARGS:
                pusher = link_dup(env->Arg);
                break;

            case PUSH_TRAPPED:
                pusher = trapped ? link_dup(trapped) : object_create(Global->null_type);
                break;
            
            case POP:
                link_free( stack_pop(stack) );
                break;

            case LINE:
                env->linenum = read_offset(env);
                break;

            default:
                fprintf(stderr," UNRECOGNIZED OPCODE ERROR %i\n", *(env->current));
                fprintf(stderr,"     near line %i\n", (int)(env->linenum));
                exit(1);
                break;
        }
                
        if (pusher) {
            
            if ( is_critical( pusher ) ){
                if ( *(env->current) == JINC)  goto jinc_critical;
                goto done;
            }
            
            stack_push(stack , pusher);
            pusher = NULL;
        }
        
    }

    end:

    if (trapped) link_free(trapped);
    return pusher;
}