/** * Insert node "node" in the list starting at position "head". * Set "ocur" to be the item with the same key if it exists * or the item which follows if the node was added successfully. * Set crt_node to point to the current node with key = "node->key" * Return 0 if item existed and 1 if it was inserted */ static int qt_lf_list_insert(marked_ptr_t *head, hash_entry *node, marked_ptr_t *ocur, hash_entry **crt_node, qt_dict_key_equals_f op_equals) { so_key_t hashed_key = node->hashed_key; qt_key_t key = node->key; while (1) { marked_ptr_t *lprev; marked_ptr_t cur; if (qt_lf_list_find(head, hashed_key, key, &lprev, &cur, NULL, op_equals) != NULL) { // needs to set cur/prev if (ocur) { *ocur = cur; } if (crt_node) { *crt_node = PTR_OF(cur); } return 0; } node->next = (hash_entry *)CONSTRUCT(0, cur); if (qthread_cas(lprev, (marked_ptr_t)(uintptr_t)node->next, CONSTRUCT(0, node)) == CONSTRUCT(0, cur)) { if (ocur) { *ocur = cur; } if (crt_node) { *crt_node = node; } return 1; } } }
/**************************************************** Root node *****************************************************/ int Root_Read(Packet self, StringIO input) { Root this=(Root)self; this->__super__->Read(self, input); switch(this->packet.link_type) { case DLT_EN10MB: this->packet.eth = (Packet)CONSTRUCT(ETH_II, Packet, super.Con, self, self); return CALL(this->packet.eth, Read, input); case DLT_IEEE802_11: this->packet.eth = (Packet)CONSTRUCT(IEEE80211, Packet, super.Con,self, self); return CALL(this->packet.eth, Read, input); case DLT_LINUX_SLL: this->packet.eth = (Packet)CONSTRUCT(Cooked, Packet, super.Con, self, self); return CALL(this->packet.eth, Read, input); case DLT_RAW: case DLT_RAW2: case DLT_RAW3: this->packet.eth = (Packet)CONSTRUCT(IP, Packet, super.Con, self, self); return CALL(this->packet.eth, Read, input); default: DEBUG("unable to parse link type of %u\n", this->packet.link_type); return -1; }; };
int remove_node(marked_ptr_t* head, hash_key_t key) { marked_ptr_t cur; marked_ptr_t* prev; while(1) { if(lf_table_find(head, key, &prev, &cur) == NULL) { return 0; } if (CAS(prev, CONSTRUCT(0, cur), CONSTRUCT(1, cur)) != CONSTRUCT(0, cur)) {continue;} if (CAS(prev, CONSTRUCT(1, cur), PTR_OF(cur)->next) == CONSTRUCT(1, cur)) { free(PTR_OF(cur)); // problem here } else { lf_table_find(head, key, NULL, NULL); // use find to remove the marked node } return 1; } }
static int qt_lf_list_delete(marked_ptr_t *head, so_key_t hashed_key, qt_key_t key, qt_dict_key_equals_f op_equals, qt_dict_cleanup_f cleanup) { while (1) { marked_ptr_t *lprev; marked_ptr_t lcur; marked_ptr_t lnext; if (qt_lf_list_find(head, hashed_key, key, &lprev, &lcur, &lnext, op_equals) == NULL) { qthread_debug(ALWAYS_OUTPUT, "### inside delete - return 0\n"); return 0; } if (qthread_cas_ptr(&PTR_OF(lcur)->next, (void*)CONSTRUCT(0, lnext), (void*)CONSTRUCT(1, lnext)) != (void *)CONSTRUCT(0, lnext)) { qthread_debug(ALWAYS_OUTPUT, "### inside delete - cas failed continue\n"); continue; } if (qthread_cas(lprev, CONSTRUCT(0, lcur), CONSTRUCT(0, lnext)) == CONSTRUCT(0, lcur)) { if (cleanup != NULL) { cleanup(PTR_OF(lcur)->key, NULL); } qpool_free(hash_entry_pool, PTR_OF(lcur)); } else { qt_lf_list_find(head, hashed_key, key, NULL, NULL, NULL, op_equals); // needs to set cur/prev/next } return 1; } }
END_VIRTUAL /**************************************************** IEEE 802 11 wireless headers *****************************************************/ int IEEE80211_Read(Packet self, StringIO input) { IEEE80211 this=(IEEE80211)self; int len; len = this->__super__->Read(self, input); /** Now depending on the ethernet type we dispatch another parser */ switch(this->packet.type) { case 0x800: this->packet.payload = (Packet)CONSTRUCT(IP, Packet, super.Con, self, self); len += CALL(this->packet.payload, Read, input); break; case 0x8864: this->packet.payload = (Packet)CONSTRUCT(PPPOE, Packet, super.Con, self, self); len += CALL(this->packet.payload, Read, input); break; default: #ifdef __VERBOSE_DEBUG__ DEBUG("Unknown ethernet payload type 0x%x.\n", this->packet.type); #endif break; }; return len; };
void* lf_table_put_if_absent(LF_HashTable* table, void* key, void* value) { marked_ptr_t* prev; marked_ptr_t cur; marked_ptr_t new_node; uint32_t index; index = HASH(key); while(1) { if(lf_table_find(&table->buckets[index], CONSTRUCT(0, key), &prev, &cur) != NULL) { return PTR_OF(cur)->value; } new_node = CONSTRUCT(0, malloc(sizeof(Node))); PTR_OF(new_node)->value = value; PTR_OF(new_node)->key = CONSTRUCT(0, key); PTR_OF(new_node)->next = *prev; if(CAS(prev, cur, CONSTRUCT(0, new_node)) == cur) { break; } } INCR(&table->size, 1); return NULL; }
END_VIRTUAL /**************************************************** IP header *****************************************************/ int IP_Read(Packet self, StringIO input) { IP this=(IP)self; int len; len=this->__super__->Read(self, input); /** The _ types are filled in to provide multiple access methods */ this->packet._src = this->packet.header.saddr; this->packet._dest = this->packet.header.daddr; /** Sometimes we get trailing trash at the end of a packet, since the dissectors which follow us would not know how long the packet actually is - it is up to us to set the size of it. */ if(input->size > self->start + this->packet.header.tot_len) { CALL(input,truncate, self->start + this->packet.header.tot_len); }; /** Now choose the dissector for the next layer */ switch(this->packet.header.protocol) { case 0x6: this->packet.payload = (Packet)CONSTRUCT(TCP, Packet, super.Con, self, self); break; case 0x11: this->packet.payload = (Packet)CONSTRUCT(UDP, Packet, super.Con, self, self); break; default: #ifdef __VERBOSE_DEBUG__ DEBUG("Unknown IP payload type 0x%x.\n", this->packet.protocol); #endif return len; }; /** Now we seek to the spot in the input stream where the payload is supposed to start. This could be a few bytes after our current position in case the packet has options that we did not account for. */ CALL(input, seek, self->start + this->packet.header.ihl * 4, SEEK_SET); CALL(this->packet.payload, Read, input); return input->readptr - self->start; };
END_VIRTUAL /**************************************************** PPPOE header *****************************************************/ int PPPOE_Read(Packet self, StringIO input) { PPPOE this=(PPPOE)self; int len; len = this->__super__->Read(self, input); switch(this->packet.protocol) { /** This packet carries IP */ case 0x0021: this->packet.payload = (Packet)CONSTRUCT(IP, Packet, super.Con, self, self); len += CALL(this->packet.payload, Read, input); break; default: #ifdef __VERBOSE_DEBUG__ DEBUG("Unknown PPPOE payload type 0x%x.\n", this->packet.protocol); #endif break; }; return len; };
int main() { Base base; CONSTRUCT( Base, base ) base.a = 0; Derived derived; CONSTRUCT_DERIVED_CLASS( Derived, Base, derived ) derived.b = 1; derived.a = 1; CALL_METHOD(Both, base) CALL_METHOD(Both, derived) CALL_METHOD(OnlyDerived, derived) CALL_METHOD(Virtual, base) CALL_METHOD(Virtual, derived) Base reallyDerived = *(reinterpret_cast<Base*>(&derived)); CALL_METHOD(Both, reallyDerived) CALL_METHOD(Virtual, reallyDerived) return 0; }
END_VIRTUAL /**************************************************** Cooked headers *****************************************************/ int Cooked_Read(Packet self, StringIO input) { Cooked this=(Cooked)self; int len; len=this->__super__->Read(self, input); switch(this->packet.type) { case 0x800: this->packet.payload = (Packet)CONSTRUCT(IP, Packet, super.Con, self, self); len += CALL(this->packet.payload, Read, input); break; default: #ifdef __VERBOSE_DEBUG__ DEBUG("Unknown ethernet payload type 0x%x.\n", this->packet.type); #endif break; }; return len; };
int lf_table_remove(LF_HashTable* table, void* key) { if(remove_node(&table->buckets[HASH(key)], CONSTRUCT(0,key))) { INCR(&table->size, -1); return 1; } return 0; }
END_CLASS static ImageWorker ImageWorker_Con(ImageWorker self, AFF4Image parent, int segment_count) { self->image = parent; self->segment_count = segment_count; self->bevy = CONSTRUCT(StringIO, StringIO, Con, self); return self; };
/** * Insert node "node" in the list starting at position "head". * If item exists replace it (force insert) */ static void qt_lf_force_list_insert(marked_ptr_t *head, hash_entry *node, qt_dict_key_equals_f op_equals) { so_key_t hashed_key = node->hashed_key; qt_key_t key = node->key; while (1) { marked_ptr_t *lprev; marked_ptr_t cur; marked_ptr_t lnext; if (qt_lf_list_find(head, hashed_key, key, &lprev, &cur, &lnext, op_equals) != NULL) { // needs to set cur/prev/next node->next = (hash_entry *)CONSTRUCT(0, lnext); } else { node->next = (hash_entry *)CONSTRUCT(0, cur); } if (qthread_cas(lprev, CONSTRUCT(0, cur), CONSTRUCT(0, node)) == CONSTRUCT(0, cur)) { return; } } }
END_VIRTUAL /**************************************************** Ethernet headers *****************************************************/ int Eth2_Read(Packet self, StringIO input) { ETH_II this=(ETH_II)self; int len; /** Call our superclass's Read method - this will populate most of our own struct. We will automatically consume as much of input as we can handle so far. */ len=this->__super__->Read(self, input); /** Now depending on the ethernet type we dispatch another parser */ switch(this->packet.type) { case 0x800: this->packet.payload = (Packet)CONSTRUCT(IP, Packet, super.Con, self, self); len += CALL(this->packet.payload, Read, input); break; case 0x8864: this->packet.payload = (Packet)CONSTRUCT(PPPOE, Packet, super.Con, self, self); len += CALL(this->packet.payload, Read, input); break; default: #ifdef __VERBOSE_DEBUG__ DEBUG("Unknown ethernet payload type 0x%x.\n", this->packet.type); #endif break; }; return len; };
static void initialize_bucket(qt_hash h, size_t bucket) { size_t parent = GET_PARENT(bucket); marked_ptr_t cur; if (h->B[parent] == UNINITIALIZED) { initialize_bucket(h, parent); } hash_entry *dummy = qpool_alloc(hash_entry_pool); assert(dummy); dummy->hashed_key = so_dummykey(bucket); dummy->key = NULL; dummy->value = NULL; dummy->next = (hash_entry*)UNINITIALIZED; if (!qt_lf_list_insert(&(h->B[parent]), dummy, &cur, NULL, h->op_equals)) { qpool_free(hash_entry_pool, dummy); dummy = PTR_OF(cur); while (h->B[bucket] != CONSTRUCT(0, dummy)) ; } else { h->B[bucket] = CONSTRUCT(0, dummy); } }
/** Dissects the current packet returning a PyPacket object */ static PyObject *PyPCAP_dissect(PyPCAP *self, PyObject *args, PyObject *kwds) { Root root; PyPacket *result; int packet_id=-1; static char *kwlist[] = {"id", NULL}; if(!PyArg_ParseTupleAndKeywords(args, kwds, "|i", kwlist, &packet_id)) return NULL; if(packet_id<0) { packet_id = self->packet_id; self->packet_id++; }; // Get the next packet: result = (PyPacket *)PyPCAP_next(self); if(!result) return NULL; // Copy the data into the dissection_buffer: CALL(self->dissection_buffer, truncate, 0); CALL(self->dissection_buffer, write, (char *)&self->packet_header->header, 16); CALL(self->dissection_buffer, write, self->packet_header->header.data, self->packet_header->header.caplen); CALL(self->dissection_buffer, seek, 16, SEEK_SET); // Attach a dissection object to the packet: root = CONSTRUCT(Root, Packet, super.Con, result->obj, NULL); root->packet.link_type = self->file_header->header.linktype; root->packet.packet_id = packet_id; // Read the data: root->super.Read((Packet)root, self->dissection_buffer); /* // Create a new PyPacket object to return: result = PyObject_CallMethod(g_pypacket_module, "PyPacket", "N", PyCObject_FromVoidPtr(root, NULL), "PcapPacketHeader"); talloc_unlink(self->buffer, root); */ ((PcapPacketHeader)(result->obj))->header.root = root; return (PyObject *)result; };
// old public method static inline qt_hash qt_hash_create(qt_dict_key_equals_f eq, qt_dict_hash_f hash, qt_dict_cleanup_f cleanup) { qt_hash tmp; if (hash_entry_pool == NULL) { if (qthread_cas_ptr(&hash_entry_pool, NULL, (void *)1) == NULL) { hash_entry_pool = qpool_create(sizeof(hash_entry)); } else { while (hash_entry_pool == (void *)1) SPINLOCK_BODY(); } } tmp = MALLOC(sizeof(qt_dictionary)); assert(tmp); tmp->op_equals = eq; tmp->op_hash = hash; tmp->op_cleanup = cleanup; assert(tmp); if (hard_max_buckets == 0) { hard_max_buckets = pagesize / sizeof(marked_ptr_t); } tmp->B = calloc(hard_max_buckets, sizeof(marked_ptr_t)); assert(tmp->B); tmp->size = 2; tmp->count = 0; { hash_entry *dummy = qpool_alloc(hash_entry_pool); assert(dummy); memset(dummy, 0, sizeof(hash_entry)); tmp->B[0] = CONSTRUCT(0, dummy); } return tmp; }
static int Reassembler_init(Reassembler *self, PyObject *args, PyObject *kwds) { int initial_con_id; static char *kwlist[] = {"initial_id", "packet_callback", NULL}; if(!PyArg_ParseTupleAndKeywords(args, kwds, "|iO", kwlist, &initial_con_id, &self->packet_callback)) return -1; /** Make sure that packet_callback is callable: */ if(self->packet_callback && !PyCallable_Check(self->packet_callback)) { PyErr_Format(PyExc_RuntimeError, "Callback must be callable"); return -1; // Make sure we keep a reference to this callback } else Py_INCREF(self->packet_callback); self->hash = CONSTRUCT(TCPHashTable, TCPHashTable, Con, NULL, initial_con_id); self->hash->callback = callback; self->hash->con_id=0; // We pass ourselves to all the callbacks self->hash->reassembler = self; return 0; };
void game::init_construction() { int id = -1; int tl, cl, sl; #define CONSTRUCT(name, difficulty, able, done) \ sl = -1; id++; \ constructions.push_back( new constructable(id, name, difficulty, able, done)) #define STAGE(...)\ tl = 0; cl = 0; sl++; \ constructions[id]->stages.push_back(construction_stage(__VA_ARGS__)); #define TOOL(...) setvector(constructions[id]->stages[sl].tools[tl], \ __VA_ARGS__); tl++ #define COMP(...) setvector(constructions[id]->stages[sl].components[cl], \ __VA_ARGS__); cl++ /* CONSTRUCT( name, time, able, done ) * Name is the name as it appears in the menu; 30 characters or less, please. * time is the time in MINUTES that it takes to finish this construction. * note that 10 turns = 1 minute. * able is a function which returns true if you can build it on a given tile * See construction.h for options, and this file for definitions. * done is a function which runs each time the construction finishes. * This is useful, for instance, for removing the trap from a pit, or placing * items after a deconstruction. */ CONSTRUCT(_("Dig Pit"), 0, &construct::able_dig, &construct::done_pit); STAGE(t_pit_shallow, 10); TOOL(itm_shovel, NULL); STAGE(t_pit, 10); TOOL(itm_shovel, NULL); CONSTRUCT(_("Spike Pit"), 0, &construct::able_pit, &construct::done_trap_pit); STAGE(t_pit_spiked, 5); COMP(itm_spear_wood, 4, NULL); CONSTRUCT(_("Fill Pit"), 0, &construct::able_pit, &construct::done_fill_pit); STAGE(t_pit_shallow, 5); TOOL(itm_shovel, NULL); STAGE(t_dirt, 5); TOOL(itm_shovel, NULL); CONSTRUCT(_("Clean Broken Window"), 0, &construct::able_broken_window, &construct::done_nothing); STAGE(t_window_empty, 5); CONSTRUCT(_("Remove Window Pane"), 1, &construct::able_window_pane, &construct::done_window_pane); STAGE(t_window_empty, 10); TOOL(itm_hammer, itm_rock, itm_hatchet, NULL); TOOL(itm_screwdriver, itm_knife_butter, itm_toolset, NULL); CONSTRUCT(_("Repair Door"), 1, &construct::able_door_broken, &construct::done_nothing); STAGE(t_door_c, 10); TOOL(itm_hammer, itm_hatchet, itm_nailgun, NULL); COMP(itm_2x4, 3, NULL); COMP(itm_nail, 12, NULL); CONSTRUCT(_("Board Up Door"), 0, &construct::able_door, &construct::done_nothing); STAGE(t_door_boarded, 8); TOOL(itm_hammer, itm_hatchet, itm_nailgun, NULL); COMP(itm_2x4, 4, NULL); COMP(itm_nail, 8, NULL); CONSTRUCT(_("Board Up Window"), 0, &construct::able_window, &construct::done_nothing); STAGE(t_window_boarded, 5); TOOL(itm_hammer, itm_hatchet, itm_nailgun, NULL); COMP(itm_2x4, 4, NULL); COMP(itm_nail, 8, NULL); CONSTRUCT(_("Build Wall"), 2, &construct::able_empty, &construct::done_nothing); STAGE(t_wall_half, 10); TOOL(itm_hammer, itm_hatchet, itm_nailgun, NULL); COMP(itm_2x4, 10, NULL); COMP(itm_nail, 20, NULL); STAGE(t_wall_wood, 10); TOOL(itm_hammer, itm_hatchet, itm_nailgun, NULL); COMP(itm_2x4, 10, NULL); COMP(itm_nail, 20, NULL); CONSTRUCT(_("Build Window"), 3, &construct::able_wall_wood, &construct::done_nothing); STAGE(t_window_empty, 10); TOOL(itm_saw, NULL); STAGE(t_window, 5); COMP(itm_glass_sheet, 1, NULL); CONSTRUCT(_("Build Door"), 4, &construct::able_wall_wood, &construct::done_nothing); STAGE(t_door_frame, 15); TOOL(itm_saw, NULL); STAGE(t_door_b, 15); TOOL(itm_hammer, itm_hatchet, itm_nailgun, NULL); COMP(itm_2x4, 4, NULL); COMP(itm_nail, 12, NULL); STAGE(t_door_c, 15); TOOL(itm_hammer, itm_hatchet, itm_nailgun, NULL); COMP(itm_2x4, 4, NULL); COMP(itm_nail, 12, NULL); /* Removed until we have some way of auto-aligning fences! CONSTRUCT("Build Fence", 1, 15, &construct::able_empty); STAGE(t_fence_h, 10); TOOL(itm_hammer, itm_hatchet, NULL); COMP(itm_2x4, 5, itm_nail, 8, NULL); */ CONSTRUCT(_("Build Roof"), 4, &construct::able_between_walls, &construct::done_nothing); STAGE(t_floor, 40); TOOL(itm_hammer, itm_hatchet, itm_nailgun, NULL); COMP(itm_2x4, 8, NULL); COMP(itm_nail, 40, NULL); }
static int iosource_init(iosource *self, PyObject *args, PyObject *kwds) { char *keywords[] = { "opts", NULL}; char *drivername; PyObject *opts = NULL; IOOptions options = NULL; PyObject *tmp; if(!PyArg_ParseTupleAndKeywords(args, kwds, "|O", keywords, &opts)) { return -1; }; if(!PyList_Check(opts)) { PyErr_Format(PyExc_TypeError, "Options must be a list of tuples"); return -1; }; if(!opts) { PyErr_Format(PyExc_Exception, "No options provided to driver"); return -1; }; options = CONSTRUCT(IOOptions, IOOptions, add, NULL, NULL, NULL, NULL); { int i=0; for(i=0;i<PyList_Size(opts);i++) { PyObject *temp,*key,*value; char *keyc, *valuec; temp = PyList_GetItem(opts,i); if(!PyList_Check(temp)) { tmp = PyObject_Str(temp); PyErr_Format(PyExc_TypeError, "Element must be a list, not %s", PyString_AsString(tmp)); Py_DECREF(tmp); return -1; }; key = PyList_GetItem(temp,0); if(!key) return -1; value = PyList_GetItem(temp,1); if(!value) return -1; key = PyObject_Str(key); keyc = PyString_AsString(key); if(!keyc) { talloc_free(options); PyErr_Format(PyExc_Exception, "Not a string - driver options must be encoded as strings."); return -1; }; value = PyObject_Str(value); valuec= PyString_AsString(value); if(!valuec) { talloc_free(options); PyErr_Format(PyExc_Exception, "Not a string - driver options must be encoded as strings."); return -1; }; CONSTRUCT(IOOptions, IOOptions, add,options, options, keyc, valuec); }; }; drivername = CALL(options, get_value, "subsys"); if(!drivername) { PyErr_Format(PyExc_TypeError, "No iodriver specified"); return -1; }; TRY { self->driver = iosubsys_Open(drivername, options); } EXCEPT(E_ANY) { talloc_free(options); PyErr_Format(map_exceptions_for_python(__EXCEPT__), "Unable to open iosource"); return -1; }; // We failed to instantiate this driver if(!self->driver) { talloc_free(options); PyErr_Format(map_errors_for_python(), "%s", _error_buff); return -1; }; //Check that all the options have been consumed: if(!list_empty(&options->list)) { IOOptions first; list_next(first, &options->list, list); PyErr_Format(PyExc_RuntimeError, "Subsystem %s does not accept parameter %s", drivername, first->name); talloc_free(options); return -1; }; //Now ensure that the options are stolen to the iosource: talloc_steal(self->driver, options); self->size = self->driver->size; return 0; };
/** This function handles a single connection */ void handle_connection(int fd) { unsigned char key[16]; char challenge[SIZEOF_CHALLENGE]; int len; int version; int length; char *filename; int target_fd; uint32_t calculated_length; RC4 rc4; uint64_t image_size; StringIO queue; // Read the challenge: len = read(fd, challenge, SIZEOF_CHALLENGE); if(len < SIZEOF_CHALLENGE) { DEBUG("Unable to read challenge from socket\n"); return; }; // Try to calculate the session key from this: if(!ecc_get_key((char *)key, challenge, Priv)) { DEBUG("Unable to decode challenge\n"); return; }; // Prepare the key: rc4 = CONSTRUCT(RC4, RC4, Con, NULL, key, sizeof(key)); queue = CONSTRUCT(StringIO, StringIO, Con, rc4); if(!read_from_network(fd, (unsigned char *)&version, sizeof(version), rc4)) { DEBUG("Cant read version\n"); return; }; version = ntohl(version); if(version != REMOTE_VERSION) { DEBUG("Client version not supported\n"); return; }; if(!read_from_network(fd, (unsigned char *)&length, sizeof(length), rc4)) return; length = ntohl(length); // Make sure the filename is not too large if(length > 1024) return; filename = talloc_zero_size(NULL, length+1); if(!read_from_network(fd, (unsigned char *)filename, length, rc4)) return; target_fd = open(filename, O_RDONLY); if(target_fd < 0) { DEBUG("Cant open %s..\n", filename); return; }; //Figure out the image size: image_size = lseek(target_fd, 0, SEEK_END); while(1) { uint64_t offset; uint32_t length; char buff[BUFF_SIZE]; if(!read_from_network(fd, (unsigned char *)&offset, sizeof(offset), rc4)) return; offset = ntohll(offset); if(!read_from_network(fd, (unsigned char *)&length, sizeof(length), rc4)) return; length = ntohl(length); // Send out the total length of the data - which may be less than // requested if the image is smaller { uint32_t c_calc_len; calculated_length = min(image_size, offset+length) - offset; c_calc_len = htonl(calculated_length); queue_for_sending(queue, (unsigned char *)&c_calc_len, sizeof(c_calc_len), rc4); }; if(lseek(target_fd, offset, SEEK_SET) != offset) { DEBUG("Unable to seek to %llu\n", offset); return; }; //DEBUG("Will need to read %u from %llu\n", calculated_length, offset); while(calculated_length > 0) { int l = read(target_fd, buff, min(calculated_length, BUFF_SIZE)); if(l==0) { break; }; if(l<0) return; queue_for_sending(queue, (unsigned char *)buff, l, rc4); // If the queue is too full, we need to flush it if(queue->size > 64000) if(!write_to_network(fd, queue)) return; calculated_length -= l; }; if(!write_to_network(fd, queue)) return; }; };
void* lf_table_get(LF_HashTable* table, void* key) { return lf_table_find(&table->buckets[HASH(key)], CONSTRUCT(0,key), NULL, NULL); }
void game::init_construction() { int id = -1; int tl, cl, sl; #define CONSTRUCT(name, difficulty, able, done) \ sl = -1; id++; \ constructions.push_back( new constructable(id, name, difficulty, able, done)) #define STAGE(...)\ tl = -1; cl = -1; sl++; \ constructions[id]->stages.push_back(construction_stage(__VA_ARGS__)); #define TOOL(item) ++tl; constructions[id]->stages[sl].tools[tl].push_back(component(item, -1)) #define TOOLCONT(item) constructions[id]->stages[sl].tools[tl].push_back(component(item, -1)) #define COMP(item, amount) ++cl; constructions[id]->stages[sl].components[cl].push_back(component(item,amount)) #define COMPCONT(item, amount) constructions[id]->stages[sl].components[cl].push_back(component(item,amount)) /* CONSTRUCT( name, time, able, done ) * Name is the name as it appears in the menu; 30 characters or less, please. * time is the time in MINUTES that it takes to finish this construction. * note that 10 turns = 1 minute. * able is a function which returns true if you can build it on a given tile * See construction.h for options, and this file for definitions. * done is a function which runs each time the construction finishes. * This is useful, for instance, for removing the trap from a pit, or placing * items after a deconstruction. */ CONSTRUCT("Dig Pit", 0, &construct::able_dig, &construct::done_nothing); STAGE(t_pit_shallow, 10); TOOL("shovel"); TOOLCONT("primitive_shovel"); TOOLCONT("digging_stick"); STAGE(t_pit, 10); TOOL("shovel"); TOOLCONT("primitive_shovel"); CONSTRUCT("Spike Pit", 0, &construct::able_pit, &construct::done_nothing); STAGE(t_pit_spiked, 5); COMP("spear_wood", 4); COMPCONT("pointy_stick", 4); CONSTRUCT("Fill Pit", 0, &construct::able_pit, &construct::done_nothing); STAGE(t_pit_shallow, 5); TOOL("shovel"); TOOLCONT("primitive_shovel"); STAGE(t_dirt, 5); TOOL("shovel"); TOOLCONT("primitive_shovel"); CONSTRUCT("Chop Down Tree", 0, &construct::able_tree, &construct::done_tree); STAGE(t_dirt, 10); TOOL("ax"); TOOLCONT("primitive_axe"); TOOLCONT("chainsaw_on"); CONSTRUCT("Chop Up Log", 0, &construct::able_log, &construct::done_log); STAGE(t_dirt, 20); TOOL("ax"); TOOLCONT("primitive_axe"); TOOLCONT("chainsaw_on"); CONSTRUCT("Move Furniture", -1, &construct::able_furniture, &construct::done_furniture); STAGE(t_null, 1); CONSTRUCT("Clean Broken Window", 0, &construct::able_broken_window, &construct::done_nothing); STAGE(t_window_empty, 5); /* CONSTRUCT("Remove Window Pane", 1, &construct::able_window_pane, &construct::done_window_pane); STAGE(t_window_empty, 10); TOOL("hammer"); TOOLCONT("primitive_hammer"); TOOLCONT("rock"); TOOLCONT("hatchet"); TOOL("screwdriver"); TOOLCONT("knife_butter"); TOOLCONT("toolset"); */ CONSTRUCT("Repair Door", 1, &construct::able_door_broken, &construct::done_nothing); STAGE(t_door_c, 10); TOOL("hammer"); TOOLCONT("primitive_hammer"); TOOLCONT("hatchet"); TOOLCONT("nailgun"); COMP("2x4", 3); COMP("nail", 12); CONSTRUCT("Board Up Door", 0, &construct::able_door, &construct::done_nothing); STAGE(t_door_boarded, 8); TOOL("hammer"); TOOLCONT("hammer_sledge"); TOOLCONT("primitive_hammer"); TOOLCONT("hatchet"); TOOLCONT("nailgun"); COMP("2x4", 4); COMP("nail", 8); CONSTRUCT("Board Up Window", 0, &construct::able_window, &construct::done_nothing); STAGE(t_window_boarded, 5); TOOL("hammer"); TOOLCONT("hammer_sledge"); TOOLCONT("primitive_hammer"); TOOLCONT("hatchet"); TOOLCONT("nailgun"); COMP("2x4", 4); COMP("nail", 8); CONSTRUCT("Build Wall", 2, &construct::able_empty, &construct::done_nothing); STAGE(t_wall_half, 10); TOOL("hammer"); TOOLCONT("primitive_hammer"); TOOLCONT("hatchet"); TOOLCONT("nailgun"); COMP("2x4", 10); COMP("nail", 20); STAGE(t_wall_wood, 10); TOOL("hammer"); TOOLCONT("primitive_hammer"); TOOLCONT("hatchet"); TOOLCONT("nailgun"); COMP("2x4", 10); COMP("nail", 20); CONSTRUCT("Build Log Wall", 2, &construct::able_pit, &construct::done_nothing); STAGE(t_wall_log_half, 20); TOOL("shovel"); TOOLCONT("primitive_shovel"); COMP("log", 2); COMP("stick", 3); COMPCONT("2x4", 6); STAGE(t_wall_log, 20); TOOL("shovel"); TOOLCONT("primitive_shovel"); COMP("log", 2); COMP("stick", 3); COMPCONT("2x4", 6); CONSTRUCT("Build Palisade Wall", 2, &construct::able_pit, &construct::done_nothing); STAGE(t_palisade, 20); TOOL("shovel"); TOOLCONT("primitive_shovel"); COMP("log", 3); COMP("rope_6", 2); CONSTRUCT("Build Rope & Pulley System", 2, &construct::able_empty, &construct::done_nothing); STAGE(t_palisade_pulley, 0); COMP("rope_30", 1); COMP("stick", 8); COMPCONT("2x4", 8); CONSTRUCT("Build Palisade Gate", 2, &construct::able_pit, &construct::done_nothing); STAGE(t_palisade_gate, 20); TOOL("shovel"); TOOLCONT("primitive_shovel"); COMP("log", 2); COMP("2x4", 3); COMP("rope_6", 2); CONSTRUCT("Build Window", 2, &construct::able_make_window, &construct::done_nothing); STAGE(t_window_empty, 10); TOOL("hammer"); TOOLCONT("primitive_hammer"); TOOLCONT("hatchet"); TOOLCONT("nailgun"); COMP("2x4", 15); COMPCONT("log", 2); COMP("nail", 30); STAGE(t_window, 5); COMP("glass_sheet", 1); STAGE(t_window_domestic, 5); TOOL("saw"); COMP("nail", 4); COMP("sheet", 2); COMP("stick", 1); COMP("string_36", 1); CONSTRUCT("Build Door", 2, &construct::able_empty, &construct::done_nothing); STAGE(t_door_frame, 15); TOOL("hammer"); TOOLCONT("primitive_hammer"); TOOLCONT("hatchet"); TOOLCONT("nailgun"); COMP("2x4", 12); COMP("nail", 24); STAGE(t_door_c, 15); TOOL("hammer"); TOOLCONT("primitive_hammer"); TOOLCONT("hatchet"); TOOLCONT("nailgun"); COMP("2x4", 4); COMP("nail", 12); CONSTRUCT("Build Wire Fence",3, &construct::able_dig, &construct::done_nothing); STAGE(t_chainfence_posts, 20); TOOL("hammer"); TOOLCONT("primitive_hammer"); TOOLCONT("hatchet"); TOOLCONT("rock"); COMP("pipe", 6); COMP("scrap", 8); STAGE(t_chainfence_v, 20); COMP("wire", 20); CONSTRUCT("Realign Fence", 0, &construct::able_chainlink, &construct::done_nothing); STAGE(t_chainfence_h, 0); STAGE(t_chainfence_v, 0); CONSTRUCT("Build Wire Gate", 3, &construct::able_between_walls, &construct::done_nothing); STAGE(t_chaingate_c, 15); COMP("wire", 20); COMP("steel_chunk", 3); COMPCONT("scrap", 12); COMP("pipe", 6); /* Removed until we have some way of auto-aligning fences! CONSTRUCT("Build Fence", 1, 15, &construct::able_empty); STAGE(t_fence_h, 10); TOOL("hammer"); TOOLCONT("primitive_hammer"); TOOLCONT("hatchet"); COMP("2x4", 5); COMPCONT("nail", 8); */ CONSTRUCT("Build Roof", 3, &construct::able_between_walls, &construct::done_nothing); STAGE(t_floor, 40); TOOL("hammer"); TOOLCONT("primitive_hammer"); TOOLCONT("hatchet"); TOOLCONT("nailgun"); COMP("2x4", 8); COMP("nail", 40); CONSTRUCT("Build Log & Sod Roof", 3, &construct::able_between_walls, &construct::done_nothing); STAGE(t_floor, 80); TOOL("hammer"); TOOLCONT("primitive_hammer"); TOOLCONT("hatchet"); TOOL("shovel"); TOOLCONT("primitive_shovel"); COMP("log", 2); COMP("stick", 4); COMPCONT("2x4", 8); // Base stuff CONSTRUCT("Build Bulletin Board", 0, &construct::able_empty, &construct::done_nothing); STAGE(t_bulletin, 10) TOOL("saw"); TOOL("hammer"); TOOLCONT("hatchet"); TOOLCONT("nailgun"); COMP("2x4", 4); COMP("nail", 8); // Household stuff CONSTRUCT("Build Dresser", 1, &construct::able_indoors, &construct::done_nothing); STAGE(t_dresser, 20); TOOL("saw"); TOOL("hammer"); TOOLCONT("primitive_hammer"); TOOLCONT("hatchet"); TOOLCONT("nailgun"); COMP("nail", 8); COMP("2x4", 6); CONSTRUCT("Build Bookcase", 1, &construct::able_indoors, &construct::done_nothing); STAGE(t_bookcase, 20); TOOL("saw"); TOOL("hammer"); TOOLCONT("primitive_hammer"); TOOLCONT("hatchet"); TOOLCONT("nailgun"); COMP("nail", 16); COMP("2x4", 12); CONSTRUCT("Build Locker", 1, &construct::able_indoors, &construct::done_nothing); STAGE(t_locker, 20); TOOL("hammer"); TOOLCONT("primitive_hammer"); TOOLCONT("hatchet"); TOOL("wrench"); COMP("sheet_metal", 2); COMP("pipe", 8); CONSTRUCT("Build Metal Rack", 1, &construct::able_indoors, &construct::done_nothing); STAGE(t_rack, 20); TOOL("hammer"); TOOLCONT("primitive_hammer"); TOOLCONT("hatchet"); TOOL("wrench"); COMP("pipe", 12); CONSTRUCT("Build Counter", 0, &construct::able_indoors, &construct::done_nothing); STAGE(t_counter, 20); TOOL("hammer"); TOOLCONT("primitive_hammer"); TOOLCONT("hatchet"); TOOLCONT("nailgun"); COMP("nail", 8); COMP("2x4", 6); CONSTRUCT("Build Makeshift Bed", 0, &construct::able_indoors, &construct::done_nothing); STAGE(t_makeshift_bed, 20); TOOL("hammer"); TOOLCONT("primitive_hammer"); TOOLCONT("hatchet"); TOOLCONT("nailgun"); COMP("nail", 8); COMP("2x4", 10); COMP("blanket", 1); CONSTRUCT("Tape up window", 0, &construct::able_window_pane, &construct::done_tape); STAGE(t_null, 2); COMP("duct_tape", 50); CONSTRUCT("Deconstruct Furniture", 0, &construct::able_deconstruct, &construct::done_deconstruct); STAGE(t_null, 20); TOOL("hammer"); TOOLCONT("primitive_hammer"); TOOLCONT("hatchet"); TOOLCONT("nailgun"); TOOL("screwdriver"); TOOLCONT("toolset"); CONSTRUCT("Start vehicle construction", 0, &construct::able_empty, &construct::done_vehicle); STAGE(t_null, 10); COMP("frame", 1); CONSTRUCT("Fence Posts", 0, &construct::able_dig, &construct::done_nothing); STAGE(t_fence_post, 5); TOOL("hammer"); TOOLCONT("primitive_hammer"); TOOLCONT("shovel"); TOOLCONT("primitive_shovel"); TOOLCONT("rock"); TOOLCONT("hatchet"); TOOLCONT("ax"); TOOLCONT("primitive_axe"); COMP("pointy_stick", 2); COMPCONT("spear_wood", 2); CONSTRUCT("Build Wood Stove", 0, &construct::able_empty, &construct::done_nothing); STAGE(t_woodstove, 10); TOOL("hacksaw"); COMP("metal_tank", 1); COMP("pipe", 1); CONSTRUCT("Build Stone Fireplace", 0, &construct::able_empty, &construct::done_nothing); STAGE(t_fireplace, 40); TOOL("hammer"); TOOLCONT("primitive_hammer"); TOOLCONT("shovel"); TOOLCONT("primitive_shovel"); COMP("rock", 40); }
void* lf_table_find(marked_ptr_t* head, hash_key_t key, marked_ptr_t** prev, marked_ptr_t* cur) { marked_ptr_t* tp_prev; marked_ptr_t tp_cur; marked_ptr_t* tp_next; hash_key_t cur_key; void* cur_value; if(PTR_OF(*head) == NULL) { if(prev) {*prev = head;}; if(cur){*cur = *head;}; return NULL; } while(1) { tp_prev = head; tp_cur = *head; while(1) { if (PTR_OF(tp_cur) == NULL) { if(prev){*prev = tp_prev;}; if(cur){*cur = tp_cur;}; return NULL; } tp_next = &PTR_OF(tp_cur)->next; cur_key = PTR_OF(tp_cur)->key; cur_value = PTR_OF(tp_cur)->value; if(*tp_prev != tp_cur) { break; // someone has mucked with the list, start over } if(MARK_OF(tp_cur)) { if (CAS(tp_prev, CONSTRUCT(1, tp_cur), tp_next) == CONSTRUCT(1, tp_cur)) { free(PTR_OF(tp_cur)); tp_cur = *tp_next; continue; } else { break; //start over } } if (key >= cur_key) { if(prev){*prev = tp_prev;}; if(cur){*cur = tp_cur;}; return key == cur_key ? cur_value : NULL; } tp_prev = tp_next; tp_cur = *tp_next; } } }
void Exception::construct() { CONSTRUCT(); //cout << "Constructing exception " << ptrStr(this) << "\n"; }
void QepcadCls::CSORCELLTR_MOD(Word c, Word Pp, Word PpO, Word PpN, Word P) { Word f,s,sh,M,K,C,Pps,L,T,B,E,I,A,a,b,k; Word PP,NP,L_P,TP,i,ta,t; Step0: k = LELTI(c,LEVEL); s = LELTI(c,SAMPLE); sh = CONVERT(s,k); SLELTI(c,SAMPLE,sh); /* Trick CONSTRUCT into working for us by wrapping the elements of Pp (which are SACLIB polynomials) in a dummy QEPCAD projection polynomial/factor data structure. */ Word PpM = NIL; for(Word PpR = CINV(Pp),j=LENGTH(Pp); PpR != NIL; PpR = RED(PpR),--j) PpM = COMP( LIST5(FIRST(PpR),LIST3(LFS("P"),k+1,j),0,PO_FAC,0) ,PpM); CONSTRUCT(c,k,GVNFV,PpM,GVNIP); Step5: /* Add two new fields to each cell to make it an RCell. */ T = NIL; for(A = LELTI(c,CHILD); A != NIL; A = RED(A)) { T = COMP(CCONC(FIRST(A),LIST2(NIL,NIL)),T); } SLELTI(c,CHILD,CINV(T)); Step6: /* Add truth values and other information. */ /* Get mask for pivot pol's, i.e. a list of 1's and zeros corresponding to PpO, where the non-pivot pol positions are 1, and the pivot pol positions are zero. */ SEPPIVNONPIV(LELTI(P,k+1),k+1,&PP,&NP); /* Get list of pivot pol's for this level. */ if ( (NP != NIL) && SINTER(LELTI(GVPIVOT,k+1),LLPFZC(c,P)) != NIL ) { PP = LELTI(P,k+1); NP = NIL; } L_P = NIL; ta = FIRST(LELTI(FIRST(LELTI(c,CHILD)),SIGNPF)); /* signiture of a sector on level k+1 pols. */ for(TP = LELTI(P,k+1); TP != NIL; TP = RED(TP)) { /* Subtle point: a pivot pol might vanish identically in this stack, which would mess everything up. If this pol does vanish identically in the stack, don't include it in the mask! */ ADV(ta,&i,&ta); /* sign of current pol in a sector: if 0 then pol vanishes in stack. */ if ( PFPIPFL(FIRST(TP),PP) && i ) { L_P = COMP(0,L_P); } else L_P = COMP(1,L_P); } L_P = INV(L_P); A = LELTI(c,CHILD); /* Stack with more cells, i.e. new. */ B = LELTI(LELTI(c,INCELL),CHILD); /* Stack with fewer cells, i.e. old. */ ADV(B,&b,&B); ADV(A,&a,&A); while (A != NIL) { SLELTI(a,INCELL,b); SLELTI(a,TRUTH,LELTI(b,TRUTH)); SLELTI(a,HOWTV,LELTI(b,HOWTV)); ADV(A,&a,&A); if (LELTI(b,MULSUB) != NIL) ADV(B,&b,&B); /* i.e. if b is a section. */ if ( ISCSOPP(a,L_P) ) { do{ ADV(B,&b,&B); } while( ! ISCSOPP(b,L_P) ); } } SLELTI(a,INCELL,b); SLELTI(a,TRUTH,LELTI(b,TRUTH)); SLELTI(a,HOWTV,LELTI(b,HOWTV)); Return: /* */ return; }
void game::init_construction() { int id = -1; int tl, cl, sl; #define CONSTRUCT(name, difficulty, able, done) \ sl = -1; id++; \ constructions.push_back( new constructable(id, name, difficulty, able, done)) #define STAGE(...)\ tl = 0; cl = 0; sl++; \ constructions[id]->stages.push_back(construction_stage(__VA_ARGS__)); #define TOOL(...) setvector(constructions[id]->stages[sl].tools[tl], \ __VA_ARGS__); tl++ #define COMP(...) setvector(constructions[id]->stages[sl].components[cl], \ __VA_ARGS__); cl++ /* CONSTRUCT( name, time, able, done ) * Name is the name as it appears in the menu; 30 characters or less, please. * time is the time in MINUTES that it takes to finish this construction. * note that 10 turns = 1 minute. * able is a function which returns true if you can build it on a given tile * See construction.h for options, and this file for definitions. * done is a function which runs each time the construction finishes. * This is useful, for instance, for removing the trap from a pit, or placing * items after a deconstruction. */ CONSTRUCT("Dig Pit", 0, &construct::able_dig, &construct::done_nothing); STAGE(t_pit_shallow, 10); TOOL(itm_shovel, NULL); STAGE(t_pit, 10); TOOL(itm_shovel, NULL); CONSTRUCT("Spike Pit", 0, &construct::able_pit, &construct::done_nothing); STAGE(t_pit_spiked, 5); COMP(itm_spear_wood, 4, NULL); CONSTRUCT("Fill Pit", 0, &construct::able_pit, &construct::done_nothing); STAGE(t_pit_shallow, 5); TOOL(itm_shovel, NULL); STAGE(t_dirt, 5); TOOL(itm_shovel, NULL); CONSTRUCT("Chop Down Tree", 0, &construct::able_tree, &construct::done_tree); STAGE(t_dirt, 10); TOOL(itm_ax, itm_chainsaw_on, NULL); CONSTRUCT("Chop Up Log", 0, &construct::able_log, &construct::done_log); STAGE(t_dirt, 20); TOOL(itm_ax, itm_chainsaw_on, NULL); CONSTRUCT("Move Furniture", -1, &construct::able_furniture, &construct::done_furniture); STAGE(t_null, 1); CONSTRUCT("Clean Broken Window", 0, &construct::able_broken_window, &construct::done_nothing); STAGE(t_window_empty, 5); /* CONSTRUCT("Remove Window Pane", 1, &construct::able_window_pane, &construct::done_window_pane); STAGE(t_window_empty, 10); TOOL(itm_hammer, itm_rock, itm_hatchet, NULL); TOOL(itm_screwdriver, itm_knife_butter, itm_toolset, NULL); */ CONSTRUCT("Repair Door", 1, &construct::able_door_broken, &construct::done_nothing); STAGE(t_door_c, 10); TOOL(itm_hammer, itm_hatchet, itm_nailgun, NULL); COMP(itm_2x4, 3, NULL); COMP(itm_nail, 12, NULL); CONSTRUCT("Board Up Door", 0, &construct::able_door, &construct::done_nothing); STAGE(t_door_boarded, 8); TOOL(itm_hammer, itm_hatchet, itm_nailgun, NULL); COMP(itm_2x4, 4, NULL); COMP(itm_nail, 8, NULL); CONSTRUCT("Board Up Window", 0, &construct::able_window, &construct::done_nothing); STAGE(t_window_boarded, 5); TOOL(itm_hammer, itm_hatchet, itm_nailgun, NULL); COMP(itm_2x4, 4, NULL); COMP(itm_nail, 8, NULL); CONSTRUCT("Build Wall", 2, &construct::able_empty, &construct::done_nothing); STAGE(t_wall_half, 10); TOOL(itm_hammer, itm_hatchet, itm_nailgun, NULL); COMP(itm_2x4, 10, NULL); COMP(itm_nail, 20, NULL); STAGE(t_wall_wood, 10); TOOL(itm_hammer, itm_hatchet, itm_nailgun, NULL); COMP(itm_2x4, 10, NULL); COMP(itm_nail, 20, NULL); CONSTRUCT("Build Log Wall", 2, &construct::able_pit, &construct::done_nothing); STAGE(t_wall_log_half, 20); TOOL(itm_shovel, NULL); COMP(itm_log, 2, NULL); COMP(itm_stick, 3, NULL); STAGE(t_wall_log, 20); TOOL(itm_shovel, NULL); COMP(itm_log, 2, NULL); COMP(itm_stick, 3, NULL); CONSTRUCT("Build Palisade Wall", 2, &construct::able_pit, &construct::done_nothing); STAGE(t_palisade, 20); TOOL(itm_shovel, NULL); COMP(itm_log, 3, NULL); COMP(itm_rope_30, 1, itm_rope_6, 5, NULL); CONSTRUCT("Build Palisade Gate", 2, &construct::able_pit, &construct::done_nothing); STAGE(t_palisade_gate, 20); TOOL(itm_shovel, NULL); COMP(itm_log, 2, NULL); COMP(itm_2x4, 3, NULL); COMP(itm_rope_30, 1, itm_rope_6, 5, NULL); CONSTRUCT("Build Window", 2, &construct::able_empty, &construct::done_nothing); STAGE(t_window_empty, 10); TOOL(itm_hammer, itm_hatchet, itm_nailgun, NULL); COMP(itm_2x4, 15, itm_log, 2, NULL); COMP(itm_nail, 30, NULL); STAGE(t_window, 5); COMP(itm_glass_sheet, 1, NULL); STAGE(t_window_domestic, 5); TOOL(itm_saw, NULL); COMP(itm_nail, 4, NULL); COMP(itm_sheet, 2, NULL); COMP(itm_stick, 1, NULL); CONSTRUCT("Build Door", 2, &construct::able_empty, &construct::done_nothing); STAGE(t_door_frame, 15); TOOL(itm_hammer, itm_hatchet, itm_nailgun, NULL); COMP(itm_2x4, 12, NULL); COMP(itm_nail, 24, NULL); STAGE(t_door_c, 15); TOOL(itm_hammer, itm_hatchet, itm_nailgun, NULL); COMP(itm_2x4, 4, NULL); COMP(itm_nail, 12, NULL); CONSTRUCT("Build Wire Fence",3, &construct::able_dig, &construct::done_nothing); STAGE(t_chainfence_posts, 20); TOOL(itm_hammer, itm_hatchet, itm_rock, NULL); COMP(itm_pipe, 6, NULL); COMP(itm_scrap, 8, NULL); STAGE(t_chainfence_v, 20); COMP(itm_wire, 15, NULL); CONSTRUCT("Realign Fence", 0, &construct::able_chainlink, &construct::done_nothing); STAGE(t_chainfence_h, 0); STAGE(t_chainfence_v, 0); CONSTRUCT("Build Wire Gate", 3, &construct::able_between_walls, &construct::done_nothing); STAGE(t_chaingate_c, 15); COMP(itm_wire, 20, NULL); COMP(itm_steel_chunk, 3, itm_scrap, 12, NULL); COMP(itm_pipe, 6, NULL); /* Removed until we have some way of auto-aligning fences! CONSTRUCT("Build Fence", 1, 15, &construct::able_empty); STAGE(t_fence_h, 10); TOOL(itm_hammer, itm_hatchet, NULL); COMP(itm_2x4, 5, itm_nail, 8, NULL); */ CONSTRUCT("Build Roof", 3, &construct::able_between_walls, &construct::done_nothing); STAGE(t_floor, 40); TOOL(itm_hammer, itm_hatchet, itm_nailgun, NULL); COMP(itm_2x4, 8, NULL); COMP(itm_nail, 40, NULL); // Household stuff CONSTRUCT("Build Dresser", 1, &construct::able_indoors, &construct::done_nothing); STAGE(t_dresser, 20); TOOL(itm_saw, NULL); TOOL(itm_hammer, itm_hatchet, itm_nailgun, NULL); COMP(itm_nail, 8, NULL); COMP(itm_2x4, 6, NULL); CONSTRUCT("Build Bookcase", 1, &construct::able_indoors, &construct::done_nothing); STAGE(t_bookcase, 20); TOOL(itm_saw, NULL); TOOL(itm_hammer, itm_hatchet, itm_nailgun, NULL); COMP(itm_nail, 16, NULL); COMP(itm_2x4, 12, NULL); CONSTRUCT("Build Counter", 0, &construct::able_indoors, &construct::done_nothing); STAGE(t_counter, 20); TOOL(itm_hammer, itm_hatchet, itm_nailgun, NULL); COMP(itm_nail, 8, NULL); COMP(itm_2x4, 6, NULL); CONSTRUCT("Build Makeshift Bed", 0, &construct::able_indoors, &construct::done_nothing); STAGE(t_makeshift_bed, 20); TOOL(itm_hammer, itm_hatchet, itm_nailgun, NULL); COMP(itm_nail, 8, NULL); COMP(itm_2x4, 10, NULL); COMP(itm_sheet, 1, NULL); CONSTRUCT("Tape up window", 0, &construct::able_window, &construct::done_tape); STAGE(t_null, 2); COMP(itm_duct_tape, 50, NULL); CONSTRUCT("Deconstruct Furniture", 0, &construct::able_deconstruct, &construct::done_deconstruct); STAGE(t_null, 20); TOOL(itm_hammer, itm_hatchet, itm_nailgun, NULL); TOOL(itm_screwdriver, itm_toolset, NULL); CONSTRUCT("Start vehicle construction", 0, &construct::able_empty, &construct::done_vehicle); STAGE(t_null, 10); COMP(itm_frame, 1, NULL); CONSTRUCT("Fence Posts", 0, &construct::able_dig, &construct::done_nothing); STAGE(t_fence_post, 5); TOOL(itm_hammer, itm_shovel, itm_rock, itm_hatchet, itm_ax, NULL); COMP(itm_spear_wood, 2, NULL); }
/** The constructor - we fill our initial buffer from the fd (and detect if it has a read method in the process... We then parse the pcap file header from the fd (and detect if its a pcap file at all). */ static int PyPCAP_init(PyPCAP *self, PyObject *args, PyObject *kwds) { PyObject *fd = NULL; int len; static char *kwlist[] = {"fd", "output", "file_id", NULL}; int i; char *output=NULL; if(!PyArg_ParseTupleAndKeywords(args, kwds, "O|sL", kwlist, &fd, &output, &self->pcap_file_id)) return -1; if(output) { if(!strcmp(output, "big")) { self->output_format = FORCE_BIG_ENDIAN; } else if(!strcmp(output,"little")) { self->output_format = FORCE_LITTLE_ENDIAN; } else { PyErr_Format(PyExc_KeyError, "Unknown value (%s) for endianess - can be only 'big' or 'little'\n", output); goto fail; }; }; // Create the new buffer - the buffer is used as our talloc context: self->buffer = CONSTRUCT(StringIO, StringIO, Con, NULL); //Fill it up: if(PyPCAP_fill_buffer(self, fd)<=0) { PyErr_Format(PyExc_IOError, "Cant read file"); goto fail; }; // Look for pcap magic somewhere in our buffer: for(i=0;i<self->buffer->size; i+=1) { uint32_t test = *(uint32_t *)(self->buffer->data + i); if(test==0xD4C3B2A1 || test==0xA1B2C3D4) { CALL(self->buffer, seek, i, SEEK_SET); break; }; }; // Read the header from our buffer: self->file_header = (PcapFileHeader)CONSTRUCT(PcapFileHeader, Packet, super.Con, self->buffer, NULL); len = self->file_header->super.Read((Packet)self->file_header, self->buffer); if(self->file_header->header.magic != 0xA1B2C3D4) { PyErr_Format(PyExc_IOError, "File does not have the right magic"); goto fail; }; // Set our initial offset: self->pcap_offset = self->buffer->readptr; // Skip over the file header: // CALL(self->buffer, skip, self->buffer->readptr); // Take over the fd self->fd = fd; Py_INCREF(fd); self->dissection_buffer = CONSTRUCT(StringIO, StringIO, Con, self->buffer); // Ok we are good. return 0; fail: return -1; };
static PyObject *PyPCAP_next(PyPCAP *self) { PyObject *result; int len; int packet_offset; // Make sure our buffer is full enough: if(self->buffer->size - self->buffer->readptr < MAX_PACKET_SIZE) { len = PyPCAP_fill_buffer(self, self->fd); if(len<0) return NULL; }; packet_offset = self->buffer->readptr; /** This is an interesting side effect of the talloc reference model: talloc_reference(context, ptr) adds a new context to ptr so ptr is now effectively parented by two parents. The two parents are not equal however because a talloc free(ptr) will remove the reference first and then the original parent. This causes problems here because we create the packet_header with self->buffer as a context. However other code takes references to it - pinning it to other parents. If we did a talloc_free(self->packet_header) here we would be removing those references _instead_ of freeing the ptr from our own self->buffer reference. This will cause both memory leaks (because we will not be freeing packet_header at all, and later crashes because important references will be removed. When references begin to be used extensively I think we need to start using talloc_unlink instead of talloc_free everywhere. */ // Free old packets: if(self->packet_header) talloc_unlink(self->buffer, self->packet_header); // Make a new packet: self->packet_header = (PcapPacketHeader)CONSTRUCT(PcapPacketHeader, Packet, super.Con, self->buffer, NULL); if(self->file_header->little_endian) { self->packet_header->super.format = self->packet_header->le_format; }; // Read the packet in: len = self->packet_header->super.Read((Packet)self->packet_header, self->buffer); // Did we finish? if(len<=0) { return PyErr_Format(PyExc_StopIteration, "Done"); }; // Make sure the new packet knows its offset and where it came from: self->packet_header->header.offset = self->pcap_offset; self->packet_header->header.pcap_file_id = self->pcap_file_id; // Keep track of our own file offset: self->pcap_offset += self->buffer->readptr - packet_offset; // CALL(self->buffer, skip, self->buffer->readptr); // Adjust the output endianess if needed switch(self->output_format) { case FORCE_BIG_ENDIAN: // FIXME - Leaks!!! self->packet_header->super.format = PCAP_PKTHEADER_STRUCT; break; case FORCE_LITTLE_ENDIAN: self->packet_header->super.format = PCAP_PKTHEADER_STRUCT_LE; break; default: // Do nothing break; }; // create a new pypacket object: result = PyObject_CallMethod(g_pypacket_module, "PyPacket", "N", PyCObject_FromVoidPtr(self->packet_header,NULL), "PcapPacketHeader"); return result; };
int main(int argc, char * argv[]) { char line[2048] = {'\0'}; char string[1024] = {'\0'}; char cmd[20] = {'\0'}; int id; unsigned length; unsigned fail = 0; unsigned count = 0; unsigned size = 10; FILE * handle = fopen(argv[1], "r"); int result; regex_dfa * dfa_root = NULL; regex_nfa * nfa_root = NULL; #ifdef alg_dfa #define root dfa_root #define DESTROY regex_destroy_dfa #define CONSTRUCT regex_construct_dfa #define MATCH regex_match_dfa #endif #ifdef alg_nfa #define root nfa_root #define DESTROY regex_destroy_nfa #define CONSTRUCT regex_construct_nfa #define MATCH regex_match_nfa #endif regex_pattern * patterns = malloc(sizeof(regex_pattern) * size); int debug = argc == 3 && strcmp(argv[2], "debug") == 0; while(fscanf(handle, "%20s %1024s %u %u", cmd, string, &length, &id) == 4) { handle_escape(string); if(cmd[0] == '#') continue; if(strcmp(cmd, "add") == 0) { if(count + 1 == size) { size += 10; patterns = realloc(patterns, sizeof(regex_pattern) * size); } patterns[count].input = malloc(length); memcpy(patterns[count].input, string, length); patterns[count].length = length; patterns[count].id = id; count++; sprintf(line, "added %s with id %d\n", string, id); } if(strcmp(cmd, "commit") == 0) { DESTROY(root); root = CONSTRUCT(patterns, count); fail = (root == NULL && id != -1) || (root != NULL && id == -1); free_patterns(patterns, &count); sprintf(line, "commit %s\n", fail ? "FAIL" : "PASS"); } if(strcmp(cmd, "match") == 0) { result = MATCH(root, string, length); fail = result != id; sprintf(line, "matching againts %s with result %d (%d), %s\n", string, result, id, fail ? "FAIL" : "PASS"); } if(debug) printf("%s", line); if(fail) { break; } } DESTROY(root); free(patterns); fclose(handle); return fail; }