From bonefish at mail.berlios.de Sun Apr 1 00:44:02 2007 From: bonefish at mail.berlios.de (bonefish at BerliOS) Date: Sun, 1 Apr 2007 00:44:02 +0200 Subject: [Haiku-commits] r20483 - haiku/trunk/src/system/kernel/cache Message-ID: <200703312244.l2VMi2AI002668@sheep.berlios.de> Author: bonefish Date: 2007-04-01 00:44:01 +0200 (Sun, 01 Apr 2007) New Revision: 20483 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20483&view=rev Modified: haiku/trunk/src/system/kernel/cache/file_cache.cpp Log: A few more changes to pages_io(): * Added a few comments. * Simplified the nested while loops by dropping the special handling for the first iovec and restructuring the innermost loop. This also rules out the possibility of a zero-length temporary vec. IMHO the readability has improved quite a bit (YMMV :-). Hopefully without introducing new bugs; please review! * Corrected computation of totalSize in case less than size has been read/written. * Also set *_numBytes in case all fileVecs have been processed. Only relevant in case the request extends beyond the end of file. Modified: haiku/trunk/src/system/kernel/cache/file_cache.cpp =================================================================== --- haiku/trunk/src/system/kernel/cache/file_cache.cpp 2007-03-31 20:27:39 UTC (rev 20482) +++ haiku/trunk/src/system/kernel/cache/file_cache.cpp 2007-03-31 22:44:01 UTC (rev 20483) @@ -415,37 +415,41 @@ TRACE(("FILE VEC [%lu] length %Ld\n", fileVecIndex, fileLeft)); + // process the complete fileVec while (fileLeft > 0) { iovec tempVecs[MAX_TEMP_IO_VECS]; - uint32 tempCount = 1; + uint32 tempCount = 0; - size = min_c(vecs[i].iov_len - vecOffset, fileLeft); + // size tracks how much of what is left of the current fileVec + // (fileLeft) has been assigned to tempVecs + size = 0; - tempVecs[0].iov_base = (void *)((addr_t)vecs[i].iov_base + vecOffset); - tempVecs[0].iov_len = size; - - if (size >= fileLeft) - vecOffset += size; - else - vecOffset = 0; - - while (size < fileLeft && ++i < count - && tempCount < MAX_TEMP_IO_VECS) { + // assign what is left of the current fileVec to the tempVecs + while (size < fileLeft && i < count + && tempCount < MAX_TEMP_IO_VECS) { + // try to satisfy one iovec per iteration (or as much as + // possible) TRACE(("fill vec %ld, offset = %lu, size = %lu\n", i, vecOffset, size)); - tempVecs[tempCount].iov_base = vecs[i].iov_base; - - // is this iovec larger than the file_io_vec? - if (vecs[i].iov_len + size > fileLeft) { - size += tempVecs[tempCount].iov_len - = vecOffset = fileLeft - size; - tempCount++; - break; + // bytes left of the current iovec + size_t vecLeft = vecs[i].iov_len - vecOffset; + if (vecLeft == 0) { + i++; + vecOffset = 0; + continue; } - size += tempVecs[tempCount].iov_len = vecs[i].iov_len; + // actually available bytes + size_t tempVecSize = min_c(vecLeft, fileLeft - size); + + tempVecs[tempCount].iov_base + = (void *)((addr_t)vecs[i].iov_base + vecOffset); + tempVecs[tempCount].iov_len = tempVecSize; tempCount++; + + size += tempVecSize; + vecOffset += tempVecSize; } size_t bytes = size; @@ -459,20 +463,21 @@ if (status < B_OK) return status; - totalSize += size; + totalSize += bytes; bytesLeft -= size; fileOffset += size; fileLeft -= size; //dprintf("-> file left = %Lu\n", fileLeft); - if (size != bytes) { - // there are no more bytes, let's bail out + if (size != bytes || i >= count) { + // there are no more bytes or iovecs, let's bail out *_numBytes = totalSize; return B_OK; } } } + *_numBytes = totalSize; return B_OK; } From mmu_man at mail.berlios.de Sun Apr 1 00:53:43 2007 From: mmu_man at mail.berlios.de (mmu_man at BerliOS) Date: Sun, 1 Apr 2007 00:53:43 +0200 Subject: [Haiku-commits] r20484 - haiku/trunk/src/add-ons/kernel/drivers/ports/usb_serial Message-ID: <200703312253.l2VMrhcQ013547@sheep.berlios.de> Author: mmu_man Date: 2007-04-01 00:53:42 +0200 (Sun, 01 Apr 2007) New Revision: 20484 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20484&view=rev Modified: haiku/trunk/src/add-ons/kernel/drivers/ports/usb_serial/driver.c Log: Add select() support for Dano & Haiku (someone will need to write tty bus manager). The supported devices list passed to the usb bus manager is now automagically generated from the other list so it's always correct (it was already out of sync). Modified: haiku/trunk/src/add-ons/kernel/drivers/ports/usb_serial/driver.c =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/ports/usb_serial/driver.c 2007-03-31 22:44:01 UTC (rev 20483) +++ haiku/trunk/src/add-ons/kernel/drivers/ports/usb_serial/driver.c 2007-03-31 22:53:42 UTC (rev 20484) @@ -24,6 +24,8 @@ off_t position, void *buf, size_t* num_bytes); static status_t usb_serial_write (void* cookie, off_t position, const void* buffer, size_t* num_bytes); +static status_t usb_serial_select (void* cookie, uint8 event, uint32 ref, selectsync *_sync); +static status_t usb_serial_deselect (void* cookie, uint8 event, selectsync *_sync); static status_t usb_serial_control (void* cookie, uint32 op, void* arg, size_t len); static status_t usb_serial_close (void* cookie); static status_t usb_serial_free (void* cookie); @@ -42,7 +44,13 @@ usb_serial_free, /* -> free cookie */ usb_serial_control, /* -> control entry point */ usb_serial_read, /* -> read entry point */ - usb_serial_write /* -> write entry point */ + usb_serial_write, /* -> write entry point */ +#if defined(B_BEOS_VERSION_DANO) || defined(__HAIKU__) + usb_serial_select, /* -> select entry point */ + usb_serial_deselect /* -> deselect entry point */ +#endif + /* readv / read_pages ??? */ + /* writev */ }; /* USB notify hooks */ static usb_notify_hooks notify_hooks = { @@ -126,6 +134,8 @@ "FTDI 8U232AM serial converter"}, }; /* supported devices*/ +usb_support_descriptor *supported_devices; +#if 0 usb_support_descriptor supported_devices[] = { {USB_DEV_CLASS_COMM, 0, 0, 0, 0}, {0, 0, 0, VND_PROLIFIC, PROD_PROLIFIC_RSAQ2 }, @@ -139,6 +149,7 @@ {0, 0, 0, VND_FTDI, PROD_8U100AX }, {0, 0, 0, VND_FTDI, PROD_8U232AM }, }; +#endif /* main devices table locking semaphore */ sem_id usb_serial_lock = -1; /* array of pointers to device objects */ @@ -195,8 +206,28 @@ usb_serial_names[0] = NULL; load_driver_symbols(DRIVER_NAME); + /* XXX: needs more error checking! */ + + // build the list of usb supported devices from our own hw list, + // so it's always up to date. + supported_devices = malloc(sizeof(usb_support_descriptor) * SIZEOF(usb_serial_hw_devices)); + // ACM devices + supported_devices[0].dev_class = USB_DEV_CLASS_COMM; + supported_devices[0].dev_subclass = 0; + supported_devices[0].dev_protocol = 0; + supported_devices[0].vendor = 0; + supported_devices[0].product = 0; + // other devices + for (i = 1; i < SIZEOF(usb_serial_hw_devices); i++){ + supported_devices[i].dev_class = 0; + supported_devices[i].dev_subclass = 0; + supported_devices[i].dev_protocol = 0; + supported_devices[i].vendor = usb_serial_hw_devices[i].vendor_id; + supported_devices[i].product = usb_serial_hw_devices[i].product_id; + } + (*usb_m->register_driver)(DRIVER_NAME, supported_devices, - SIZEOF(supported_devices), DRIVER_NAME); + SIZEOF(usb_serial_hw_devices), DRIVER_NAME); (*usb_m->install_notify)(DRIVER_NAME, ¬ify_hooks); usb_serial_lock = create_sem(1, DRIVER_NAME"_devices_table_lock"); @@ -204,9 +235,13 @@ status = B_ERROR; TRACE_ALWAYS("init_driver failed: tty_m:%08x usb_m:%08x", tty_m, usb_m); } + if (status != B_OK) + put_module(B_USB_MODULE_NAME); }else TRACE_ALWAYS("init_driver failed:%lx cannot get a module %s", status, B_USB_MODULE_NAME); + if (status != B_OK) + put_module(B_TTY_MODULE_NAME); }else TRACE_ALWAYS("init_driver failed:%lx cannot get a module %s", status, B_TTY_MODULE_NAME); @@ -222,6 +257,7 @@ TRACE_FUNCALLS("uninit_driver\n"); (*usb_m->uninstall_notify)(DRIVER_NAME); + free(supported_devices); acquire_sem(usb_serial_lock); for(i = 0; i < DEVICES_COUNT; i++) @@ -618,6 +654,50 @@ return status; } +#if defined(B_BEOS_VERSION_DANO) || defined(__HAIKU__) + +/* usb_serial_select - handle select start */ +static status_t usb_serial_select (void* cookie, uint8 event, uint32 ref, selectsync *_sync){ + status_t status = B_BAD_VALUE; + TRACE_FUNCALLS("usb_serial_select cookie:%08x event:%08x ref:%08x sync:%p\n", + cookie, event, ref, _sync); + + if(cookie){ + struct ddrover *ddr = (*tty_m->ddrstart)(NULL); + if(ddr){ + status = (*tty_m->ttyselect)(cookie, ddr, event, ref, _sync); + (*tty_m->ddrdone)(ddr); + }else + status = B_NO_MEMORY; + }else + status = ENODEV; + + TRACE_FUNCRET("usb_serial_select returns:%08x\n", status); + return status; +} + +/* usb_serial_deselect - handle select exit */ +static status_t usb_serial_deselect (void* cookie, uint8 event, selectsync *_sync){ + status_t status = B_BAD_VALUE; + TRACE_FUNCALLS("usb_serial_deselect cookie:%08x event:%08x sync:%p\n", + cookie, event, _sync); + + if(cookie){ + struct ddrover *ddr = (*tty_m->ddrstart)(NULL); + if(ddr){ + status = (*tty_m->ttydeselect)(cookie, ddr, event, _sync); + (*tty_m->ddrdone)(ddr); + }else + status = B_NO_MEMORY; + }else + status = ENODEV; + + TRACE_FUNCRET("usb_serial_deselect returns:%08x\n", status); + return status; +} + +#endif + /* usb_serial_close - handle close() calls */ static status_t usb_serial_close (void* cookie){ status_t status = ENODEV; From bonefish at mail.berlios.de Sun Apr 1 01:06:10 2007 From: bonefish at mail.berlios.de (bonefish at BerliOS) Date: Sun, 1 Apr 2007 01:06:10 +0200 Subject: [Haiku-commits] r20485 - haiku/trunk/src/system/kernel Message-ID: <200703312306.l2VN6AuL028268@sheep.berlios.de> Author: bonefish Date: 2007-04-01 01:06:09 +0200 (Sun, 01 Apr 2007) New Revision: 20485 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20485&view=rev Modified: haiku/trunk/src/system/kernel/elf.cpp Log: Reversed locking order of sImageLoadMutex and sImageMutex in unload_kernel_add_on(). The former one could lead to deadlocks with load_kernel_add_on() (e.g. occasionally the boot process would hang). Modified: haiku/trunk/src/system/kernel/elf.cpp =================================================================== --- haiku/trunk/src/system/kernel/elf.cpp 2007-03-31 22:53:42 UTC (rev 20484) +++ haiku/trunk/src/system/kernel/elf.cpp 2007-03-31 23:06:09 UTC (rev 20485) @@ -54,8 +54,9 @@ static hash_table *sImagesHash; static struct elf_image_info *sKernelImage = NULL; -static mutex sImageMutex; -static mutex sImageLoadMutex; +static mutex sImageMutex; // guards sImagesHash +static mutex sImageLoadMutex; // serializes loading/unloading add-ons + // locking order sImageLoadMutex -> sImageMutex static bool sInitialized = false; @@ -1449,19 +1450,18 @@ struct elf_image_info *image; status_t status; + mutex_lock(&sImageLoadMutex); mutex_lock(&sImageMutex); image = find_image(id); - if (image != NULL) { - mutex_lock(&sImageLoadMutex); - + if (image != NULL) status = unload_elf_image(image); - - mutex_unlock(&sImageLoadMutex); - } else + else status = B_BAD_IMAGE_ID; mutex_unlock(&sImageMutex); + mutex_unlock(&sImageLoadMutex); + return status; } From bonefish at mail.berlios.de Sun Apr 1 01:52:06 2007 From: bonefish at mail.berlios.de (bonefish at BerliOS) Date: Sun, 1 Apr 2007 01:52:06 +0200 Subject: [Haiku-commits] r20486 - haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/server Message-ID: <200703312352.l2VNq6ET024875@sheep.berlios.de> Author: bonefish Date: 2007-04-01 01:52:05 +0200 (Sun, 01 Apr 2007) New Revision: 20486 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20486&view=rev Modified: haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/server/haiku_file_cache.cpp Log: Synchronized with recent kernel file cache changes up to r20483. Modified: haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/server/haiku_file_cache.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/server/haiku_file_cache.cpp 2007-03-31 23:06:09 UTC (rev 20485) +++ haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/server/haiku_file_cache.cpp 2007-03-31 23:52:05 UTC (rev 20486) @@ -81,6 +81,7 @@ // maximum number of iovecs per request #define MAX_IO_VECS 64 // 256 kB #define MAX_FILE_IO_VECS 32 +#define MAX_TEMP_IO_VECS 8 #define CACHED_FILE_EXTENTS 2 // must be smaller than MAX_FILE_IO_VECS @@ -1058,7 +1059,7 @@ static file_extent * find_file_extent(file_cache_ref *ref, off_t offset, uint32 *_index) { - // ToDo: do binary search + // TODO: do binary search for (uint32 index = 0; index < ref->map.count; index++) { file_extent *extent = ref->map[index]; @@ -1171,37 +1172,45 @@ } +/*! + Does the dirty work of translating the request into actual disk offsets + and reads to or writes from the supplied iovecs as specified by \a doWrite. +*/ static status_t pages_io(file_cache_ref *ref, off_t offset, const iovec *vecs, size_t count, size_t *_numBytes, bool doWrite) { - TRACE(("pages_io: ref = %p, offset = %Ld, size = %lu, %s\n", ref, offset, - *_numBytes, doWrite ? "write" : "read")); + TRACE(("pages_io: ref = %p, offset = %Ld, size = %lu, vecCount = %lu, %s\n", ref, offset, + *_numBytes, count, doWrite ? "write" : "read")); // translate the iovecs into direct device accesses file_io_vec fileVecs[MAX_FILE_IO_VECS]; size_t fileVecCount = MAX_FILE_IO_VECS; size_t numBytes = *_numBytes; - status_t status = get_file_map(ref, offset, numBytes, fileVecs, &fileVecCount); + status_t status = get_file_map(ref, offset, numBytes, fileVecs, + &fileVecCount); if (status < B_OK) { TRACE(("get_file_map(offset = %Ld, numBytes = %lu) failed\n", offset, numBytes)); return status; } - // ToDo: handle array overflow gracefully! + // TODO: handle array overflow gracefully! #ifdef TRACE_FILE_CACHE dprintf("got %lu file vecs for %Ld:%lu:\n", fileVecCount, offset, numBytes); - for (size_t i = 0; i < fileVecCount; i++) - dprintf("[%lu] offset = %Ld, size = %Ld\n", i, fileVecs[i].offset, fileVecs[i].length); + for (size_t i = 0; i < fileVecCount; i++) { + dprintf(" [%lu] offset = %Ld, size = %Ld\n", + i, fileVecs[i].offset, fileVecs[i].length); + } #endif if (fileVecCount == 0) { // There are no file vecs at this offset, so we're obviously trying // to access the file outside of its bounds - TRACE(("pages_io: access outside of vnode %p at offset %Ld\n", ref->vnode, offset)); + TRACE(("pages_io: access outside of vnode %p at offset %Ld\n", + ref->vnode, offset)); return B_BAD_VALUE; } @@ -1221,9 +1230,10 @@ if (status < B_OK) return status; - // ToDo: this is a work-around for buggy device drivers! + // TODO: this is a work-around for buggy device drivers! // When our own drivers honour the length, we can: - // a) also use this direct I/O for writes (otherwise, it would overwrite precious data) + // a) also use this direct I/O for writes (otherwise, it would + // overwrite precious data) // b) panic if the term below is true (at least for writes) if (size > fileVecs[0].length) { //dprintf("warning: device driver %p doesn't respect total length in read_pages() call!\n", ref->device); @@ -1241,7 +1251,7 @@ *_numBytes = size; return B_OK; } - + fileVecIndex = 1; } else { fileVecIndex = 0; @@ -1255,73 +1265,96 @@ // first, find out where we have to continue in our iovecs uint32 i = 0; for (; i < count; i++) { - if (size <= vecs[i].iov_len) + if (size < vecs[i].iov_len) break; size -= vecs[i].iov_len; } size_t vecOffset = size; + size_t bytesLeft = numBytes - size; for (; fileVecIndex < fileVecCount; fileVecIndex++) { file_io_vec &fileVec = fileVecs[fileVecIndex]; - iovec tempVecs[8]; - uint32 tempCount = 1; + off_t fileOffset = fileVec.offset; + off_t fileLeft = fileVec.length; - tempVecs[0].iov_base = (void *)((addr_t)vecs[i].iov_base + vecOffset); + fileLeft = min_c(fileVec.length, bytesLeft); - size = min_c(vecs[i].iov_len - vecOffset, fileVec.length); - tempVecs[0].iov_len = size; + TRACE(("FILE VEC [%lu] length %Ld\n", fileVecIndex, fileLeft)); - TRACE(("fill vec %ld, offset = %lu, size = %lu\n", i, vecOffset, size)); + // process the complete fileVec + while (fileLeft > 0) { + iovec tempVecs[MAX_TEMP_IO_VECS]; + uint32 tempCount = 0; - if (size >= fileVec.length) - vecOffset += size; - else - vecOffset = 0; + // size tracks how much of what is left of the current fileVec + // (fileLeft) has been assigned to tempVecs + size = 0; - while (size < fileVec.length && ++i < count) { - tempVecs[tempCount].iov_base = vecs[i].iov_base; - tempCount++; + // assign what is left of the current fileVec to the tempVecs + while (size < fileLeft && i < count + && tempCount < MAX_TEMP_IO_VECS) { + // try to satisfy one iovec per iteration (or as much as + // possible) + TRACE(("fill vec %ld, offset = %lu, size = %lu\n", + i, vecOffset, size)); - // is this iovec larger than the file_io_vec? - if (vecs[i].iov_len + size > fileVec.length) { - size += tempVecs[tempCount].iov_len = vecOffset = fileVec.length - size; - break; + // bytes left of the current iovec + size_t vecLeft = vecs[i].iov_len - vecOffset; + if (vecLeft == 0) { + i++; + vecOffset = 0; + continue; + } + + // actually available bytes + size_t tempVecSize = min_c(vecLeft, fileLeft - size); + + tempVecs[tempCount].iov_base + = (void *)((addr_t)vecs[i].iov_base + vecOffset); + tempVecs[tempCount].iov_len = tempVecSize; + tempCount++; + + size += tempVecSize; + vecOffset += tempVecSize; } - size += tempVecs[tempCount].iov_len = vecs[i].iov_len; - } + size_t bytes = size; + if (doWrite) { + status = vfs_write_pages(ref->deviceFD, fileOffset, + tempVecs, tempCount, &bytes, false); + } else { + status = vfs_read_pages(ref->deviceFD, fileOffset, + tempVecs, tempCount, &bytes, false); + } + if (status < B_OK) + return status; - size_t bytes = size; - if (doWrite) { - status = vfs_write_pages(ref->deviceFD, fileVec.offset, tempVecs, - tempCount, &bytes, false); - } else { - status = vfs_read_pages(ref->deviceFD, fileVec.offset, tempVecs, - tempCount, &bytes, false); - } - if (status < B_OK) - return status; + totalSize += bytes; + bytesLeft -= size; + fileOffset += size; + fileLeft -= size; + //dprintf("-> file left = %Lu\n", fileLeft); - totalSize += size; - - if (size != bytes) { - // there are no more bytes, let's bail out - *_numBytes = totalSize; - return B_OK; + if (size != bytes || i >= count) { + // there are no more bytes or iovecs, let's bail out + *_numBytes = totalSize; + return B_OK; + } } } + *_numBytes = totalSize; return B_OK; } -/** This function is called by read_into_cache() (and from there only) - it - * can only handle a certain amount of bytes, and read_into_cache() makes - * sure that it matches that criterion. - */ - +/*! + This function is called by read_into_cache() (and from there only) - it + can only handle a certain amount of bytes, and read_into_cache() makes + sure that it matches that criterion. +*/ static inline status_t read_chunk_into_cache(file_cache_ref *ref, off_t offset, size_t size, int32 pageOffset, addr_t buffer, size_t bufferSize) @@ -1400,14 +1433,14 @@ } -/** This function reads \a size bytes directly from the file into the cache. - * If \a bufferSize does not equal zero, \a bufferSize bytes from the data - * read in are also copied to the provided \a buffer. - * This function always allocates all pages; it is the responsibility of the - * calling function to only ask for yet uncached ranges. - * The cache_ref lock must be hold when calling this function. - */ - +/*! + This function reads \a size bytes directly from the file into the cache. + If \a bufferSize does not equal zero, \a bufferSize bytes from the data + read in are also copied to the provided \a buffer. + This function always allocates all pages; it is the responsibility of the + calling function to only ask for yet uncached ranges. + The cache_ref lock must be hold when calling this function. +*/ static status_t read_into_cache(file_cache_ref *ref, off_t offset, size_t size, addr_t buffer, size_t bufferSize) { @@ -1750,8 +1783,7 @@ } -// #pragma mark - -// public FS API +// #pragma mark - public FS API void * From bonefish at mail.berlios.de Sun Apr 1 02:16:38 2007 From: bonefish at mail.berlios.de (bonefish at BerliOS) Date: Sun, 1 Apr 2007 02:16:38 +0200 Subject: [Haiku-commits] r20487 - haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/server Message-ID: <200704010016.l310Gcni027395@sheep.berlios.de> Author: bonefish Date: 2007-04-01 02:16:36 +0200 (Sun, 01 Apr 2007) New Revision: 20487 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20487&view=rev Modified: haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/server/haiku_file_cache.cpp Log: Disabled stealing an unused page from some cache. Unfortunately this introduced a locking problem, since vm_page_allocate_page() is invoked with a locked cache. I guess I have to rethink the design. :-/ Modified: haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/server/haiku_file_cache.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/server/haiku_file_cache.cpp 2007-03-31 23:52:05 UTC (rev 20486) +++ haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/server/haiku_file_cache.cpp 2007-04-01 00:16:36 UTC (rev 20487) @@ -366,6 +366,10 @@ // no free page +#if 0 +// TODO: Nice idea in principle, but causes a serious locking problem. +// vm_page_allocate_page() is always invoked with some cached locked at the +// same time. Thus locking a cache here to steal a page can cause a deadlock. // If the limit for allocated pages has been reached, we try to steal an // unused page. if (sPagePool.allocatedPages >= kMaxAllocatedPages @@ -431,6 +435,7 @@ return page; } } +#endif // 0 // no page yet -- allocate a new one From bonefish at mail.berlios.de Sun Apr 1 02:19:41 2007 From: bonefish at mail.berlios.de (bonefish at BerliOS) Date: Sun, 1 Apr 2007 02:19:41 +0200 Subject: [Haiku-commits] r20488 - in haiku/trunk/src/tests/add-ons/kernel/file_systems/userlandfs: . bfs Message-ID: <200704010019.l310JfI7027895@sheep.berlios.de> Author: bonefish Date: 2007-04-01 02:19:40 +0200 (Sun, 01 Apr 2007) New Revision: 20488 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20488&view=rev Added: haiku/trunk/src/tests/add-ons/kernel/file_systems/userlandfs/bfs/ haiku/trunk/src/tests/add-ons/kernel/file_systems/userlandfs/bfs/Jamfile Modified: haiku/trunk/src/tests/add-ons/kernel/file_systems/userlandfs/Jamfile Log: BFS can be built for the userland. And it even seems to work. :-P Modified: haiku/trunk/src/tests/add-ons/kernel/file_systems/userlandfs/Jamfile =================================================================== --- haiku/trunk/src/tests/add-ons/kernel/file_systems/userlandfs/Jamfile 2007-04-01 00:16:36 UTC (rev 20487) +++ haiku/trunk/src/tests/add-ons/kernel/file_systems/userlandfs/Jamfile 2007-04-01 00:19:40 UTC (rev 20488) @@ -1,5 +1,6 @@ SubDir HAIKU_TOP src tests add-ons kernel file_systems userlandfs ; +SubInclude HAIKU_TOP src tests add-ons kernel file_systems userlandfs bfs ; SubInclude HAIKU_TOP src tests add-ons kernel file_systems userlandfs r5 ; SubInclude HAIKU_TOP src tests add-ons kernel file_systems userlandfs ramfs ; SubInclude HAIKU_TOP src tests add-ons kernel file_systems userlandfs reiserfs ; Copied: haiku/trunk/src/tests/add-ons/kernel/file_systems/userlandfs/bfs/Jamfile (from rev 20433, haiku/trunk/src/add-ons/kernel/file_systems/bfs/Jamfile) =================================================================== --- haiku/trunk/src/add-ons/kernel/file_systems/bfs/Jamfile 2007-03-27 12:15:01 UTC (rev 20433) +++ haiku/trunk/src/tests/add-ons/kernel/file_systems/userlandfs/bfs/Jamfile 2007-04-01 00:19:40 UTC (rev 20488) @@ -0,0 +1,46 @@ +SubDir HAIKU_TOP src tests add-ons kernel file_systems userlandfs bfs ; + +local bfsTop = [ FDirName $(HAIKU_TOP) src add-ons kernel file_systems bfs ] ; + +SEARCH_SOURCE += $(bfsTop) ; + +# set some additional defines +{ + local defines = + #BFS_BIG_ENDIAN_ONLY + USER=1 + ; + + if $(DEBUG) = 0 { + # the gcc on BeOS doesn't compile BFS correctly with -O2 or more + OPTIM = -O1 ; + } + + defines = [ FDefines $(defines) ] ; + SubDirCcFlags $(defines) -Wall -Wno-multichar ; + SubDirC++Flags $(defines) -Wall -Wno-multichar -fno-rtti ; +} + +UsePrivateHeaders [ FDirName kernel ] ; +UsePrivateHeaders [ FDirName kernel disk_device_manager ] ; +UsePrivateHeaders [ FDirName storage ] ; + +Addon bfs + : # relpath - obsolete + : + BlockAllocator.cpp + BPlusTree.cpp + Attribute.cpp + Debug.cpp + Index.cpp + Inode.cpp + Journal.cpp + Query.cpp + Utility.cpp + Volume.cpp + + kernel_interface.cpp + + : false # is executable + : libuserlandfs_haiku_kernel.so +; From umccullough at gmail.com Sun Apr 1 05:40:28 2007 From: umccullough at gmail.com (Urias McCullough) Date: Sat, 31 Mar 2007 20:40:28 -0700 Subject: [Haiku-commits] r20447 - in haiku/trunk: build/jam headers/build/os/storage headers/build/private/kernel src/build/libhaikucompat src/kits src/kits/storage src/kits/tracker In-Reply-To: <200703281520.l2SFKB1J016461@sheep.berlios.de> References: <200703281520.l2SFKB1J016461@sheep.berlios.de> Message-ID: <1e80d8750703312040p141df97dp179defe495a6164b@mail.gmail.com> On 3/28/07, bonefish at BerliOS wrote: > > Author: bonefish > Date: 2007-03-28 17:20:08 +0200 (Wed, 28 Mar 2007) > New Revision: 20447 > ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20447&view=rev > > Added: > haiku/trunk/headers/build/os/storage/DiskDeviceDefs.h > haiku/trunk/src/build/libhaikucompat/misc.cpp > haiku/trunk/src/build/libhaikucompat/syscalls.cpp > Modified: > haiku/trunk/build/jam/BuildSetup > haiku/trunk/headers/build/private/kernel/syscalls.h > haiku/trunk/src/build/libhaikucompat/Jamfile > haiku/trunk/src/kits/Jamfile > haiku/trunk/src/kits/storage/Jamfile > haiku/trunk/src/kits/tracker/AutoMounter.cpp > Log: > Added the disk device API to the libbe_haiku.so, so that libtracker.sobuilds > again for target libbe_test. Added respective syscall stubs and other > functions > to libhaikucompat.a. With the addition of misc.cpp and syscalls.cpp to the libhaikucompat, it is no longer building for me when building with TARGET_PLATFORM=r5. Looks like it can't locate fs_volume.h - Urias -------------- next part -------------- An HTML attachment was scrubbed... URL: From superstippi at gmx.de Sun Apr 1 09:01:54 2007 From: superstippi at gmx.de (Stephan Assmus) Date: Sun, 01 Apr 2007 09:01:54 +0200 Subject: [Haiku-commits] r20479 - haiku/trunk/src/libs/icon In-Reply-To: <20070331213911.1208.4@cs.tu-berlin.de> References: <200703311814.l2VIEVb3023674@sheep.berlios.de> <20070331213911.1208.4@cs.tu-berlin.de> Message-ID: <20070401090154.427.1@stippis.mshome.net> Hi Ingo, > Did you just forget to check your changes to HaikuBuildCompatibility.h in or > is it not needed anymore? It was not needed anymore, as far as I can tell. I did the change a couple month ago. Best regards, -Stephan From axeld at mail.berlios.de Sun Apr 1 13:31:28 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Sun, 1 Apr 2007 13:31:28 +0200 Subject: [Haiku-commits] r20489 - haiku/trunk/src/tests/system/kernel/cache Message-ID: <200704011131.l31BVSGX021873@sheep.berlios.de> Author: axeld Date: 2007-04-01 13:31:22 +0200 (Sun, 01 Apr 2007) New Revision: 20489 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20489&view=rev Modified: haiku/trunk/src/tests/system/kernel/cache/pages_io_test.cpp Log: Updated the pages_io() test with Ingo's latest changes. Modified: haiku/trunk/src/tests/system/kernel/cache/pages_io_test.cpp =================================================================== --- haiku/trunk/src/tests/system/kernel/cache/pages_io_test.cpp 2007-04-01 00:19:40 UTC (rev 20488) +++ haiku/trunk/src/tests/system/kernel/cache/pages_io_test.cpp 2007-04-01 11:31:22 UTC (rev 20489) @@ -1,3 +1,9 @@ +/* + * Copyright 2004-2007, Axel D?rfler, axeld at pinc-software.de. All rights reserved. + * Distributed under the terms of the MIT License. + */ + + #include #include @@ -10,6 +16,10 @@ #define TRACE(x) printf x #define dprintf printf +#ifndef ASSERT +# define ASSERT(x) ; +#endif + // maximum number of iovecs per request #define MAX_IO_VECS 64 // 256 kB #define MAX_FILE_IO_VECS 32 @@ -489,7 +499,7 @@ size = fileVecs[0].length; } - //ASSERT(size <= fileVecs[0].length); + ASSERT(size <= fileVecs[0].length); // If the file portion was contiguous, we're already done now if (size == numBytes) @@ -530,36 +540,43 @@ fileLeft = min_c(fileVec.length, bytesLeft); -printf("FILE VEC [%lu] length %Ld\n", fileVecIndex, fileLeft); + TRACE(("FILE VEC [%lu] length %Ld\n", fileVecIndex, fileLeft)); + + // process the complete fileVec while (fileLeft > 0) { iovec tempVecs[MAX_TEMP_IO_VECS]; - uint32 tempCount = 1; + uint32 tempCount = 0; - size = min_c(vecs[i].iov_len - vecOffset, fileLeft); + // size tracks how much of what is left of the current fileVec + // (fileLeft) has been assigned to tempVecs + size = 0; - tempVecs[0].iov_base = (void *)((addr_t)vecs[i].iov_base + vecOffset); - tempVecs[0].iov_len = size; + // assign what is left of the current fileVec to the tempVecs + for (size = 0; size < fileLeft && i < count + && tempCount < MAX_TEMP_IO_VECS;) { + // try to satisfy one iovec per iteration (or as much as + // possible) + TRACE(("fill vec %ld, offset = %lu, size = %lu\n", + i, vecOffset, size)); - if (size >= fileLeft) - vecOffset += size; - else - vecOffset = 0; + // bytes left of the current iovec + size_t vecLeft = vecs[i].iov_len - vecOffset; + if (vecLeft == 0) { + vecOffset = 0; + i++; + continue; + } - while (size < fileLeft && ++i < count - && tempCount < MAX_TEMP_IO_VECS) { - TRACE(("fill vec %ld, offset = %lu, size = %lu\n", i, vecOffset, size)); - tempVecs[tempCount].iov_base = vecs[i].iov_base; + // actually available bytes + size_t tempVecSize = min_c(vecLeft, fileLeft - size); - // is this iovec larger than the file_io_vec? - if (vecs[i].iov_len + size > fileLeft) { - size += tempVecs[tempCount].iov_len - = vecOffset = fileLeft - size; - tempCount++; - break; - } + tempVecs[tempCount].iov_base + = (void *)((addr_t)vecs[i].iov_base + vecOffset); + tempVecs[tempCount].iov_len = tempVecSize; + tempCount++; - size += tempVecs[tempCount].iov_len = vecs[i].iov_len; - tempCount++; + size += tempVecSize; + vecOffset += tempVecSize; } size_t bytes = size; @@ -573,20 +590,21 @@ if (status < B_OK) return status; - totalSize += size; + totalSize += bytes; bytesLeft -= size; fileOffset += size; fileLeft -= size; - printf("-> file left = %Lu\n", fileLeft); + //dprintf("-> file left = %Lu\n", fileLeft); - if (size != bytes) { - // there are no more bytes, let's bail out + if (size != bytes || i >= count) { + // there are no more bytes or iovecs, let's bail out *_numBytes = totalSize; return B_OK; } } } + *_numBytes = totalSize; return B_OK; } From axeld at pinc-software.de Sun Apr 1 13:34:34 2007 From: axeld at pinc-software.de (Axel =?iso-8859-15?q?D=F6rfler?=) Date: Sun, 01 Apr 2007 13:34:34 +0200 CEST Subject: [Haiku-commits] r20483 - haiku/trunk/src/system/kernel/cache In-Reply-To: <200703312244.l2VMi2AI002668@sheep.berlios.de> Message-ID: <2427272475-BeMail@zon> bonefish at BerliOS wrote: > A few more changes to pages_io(): > * Added a few comments. > * Simplified the nested while loops by dropping the special handling > for the > first iovec and restructuring the innermost loop. This also rules > out > the possibility of a zero-length temporary vec. IMHO the > readability > has improved quite a bit (YMMV :-). Hopefully without introducing > new > bugs; please review! Looks okay, but I'm not sure if I find it easier to read :-) After all, the vecOffset is a special case that only affects the first iovec; now, you have doubled the number of loops without good reason. BTW, I've updated the pages_io_test.cpp as well, in case you missed that one :) > * Corrected computation of totalSize in case less than size has been > read/written. Thanks, I missed that one :-) > * Also set *_numBytes in case all fileVecs have been processed. Only > relevant in case the request extends beyond the end of file. In that case, it would already have dropped out earlier in the loop, so I don't think this is necessary. Bye, Axel. From axeld at mail.berlios.de Sun Apr 1 13:38:39 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Sun, 1 Apr 2007 13:38:39 +0200 Subject: [Haiku-commits] r20490 - haiku/trunk/src/add-ons/kernel/network/protocols/ipv4 Message-ID: <200704011138.l31Bcd6B022240@sheep.berlios.de> Author: axeld Date: 2007-04-01 13:38:37 +0200 (Sun, 01 Apr 2007) New Revision: 20490 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20490&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp Log: You also have to recompute the checksum in case the source address was updated, patch by Hugo Santos. Modified: haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp 2007-04-01 11:31:22 UTC (rev 20489) +++ haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp 2007-04-01 11:38:37 UTC (rev 20490) @@ -984,8 +984,11 @@ return bufferHeader.Status(); ipv4_header &header = bufferHeader.Data(); - if (header.source == 0) + if (header.source == 0) { header.source = source.sin_addr.s_addr; + header.checksum = gBufferModule->checksum(buffer, + sizeof(ipv4_header), sizeof(ipv4_header), true); + } bufferHeader.Detach(); } From axeld at mail.berlios.de Sun Apr 1 13:48:07 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Sun, 1 Apr 2007 13:48:07 +0200 Subject: [Haiku-commits] r20491 - haiku/trunk/src/add-ons/kernel/network/stack Message-ID: <200704011148.l31Bm7Xf022873@sheep.berlios.de> Author: axeld Date: 2007-04-01 13:48:07 +0200 (Sun, 01 Apr 2007) New Revision: 20491 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20491&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp haiku/trunk/src/add-ons/kernel/network/stack/domains.cpp haiku/trunk/src/add-ons/kernel/network/stack/domains.h haiku/trunk/src/add-ons/kernel/network/stack/interfaces.cpp haiku/trunk/src/add-ons/kernel/network/stack/interfaces.h haiku/trunk/src/add-ons/kernel/network/stack/link.cpp Log: SIOCGIFCONF will now also report the size of the written buffer in ifconf.ifc_len to cover the case the list of interfaces changed since SIOCGIFCOUNT was called. Patch by Hugo Santos. Modified: haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp 2007-04-01 11:38:37 UTC (rev 20490) +++ haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp 2007-04-01 11:48:07 UTC (rev 20491) @@ -280,7 +280,12 @@ if (user_memcpy(&config, value, sizeof(struct ifconf)) < B_OK) return B_BAD_ADDRESS; - return list_domain_interfaces(config.ifc_buf, config.ifc_len); + status_t result = list_domain_interfaces(config.ifc_buf, + (size_t *)&config.ifc_len); + if (result != B_OK) + return result; + + return user_memcpy(value, &config, sizeof(struct ifconf)); } case SIOCGRTSIZE: Modified: haiku/trunk/src/add-ons/kernel/network/stack/domains.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/domains.cpp 2007-04-01 11:38:37 UTC (rev 20490) +++ haiku/trunk/src/add-ons/kernel/network/stack/domains.cpp 2007-04-01 11:48:07 UTC (rev 20491) @@ -1,5 +1,5 @@ /* - * Copyright 2006, Haiku, Inc. All Rights Reserved. + * Copyright 2006-2007, Haiku, Inc. All Rights Reserved. * Distributed under the terms of the MIT License. * * Authors: @@ -99,12 +99,13 @@ returned. */ status_t -list_domain_interfaces(void *buffer, size_t size) +list_domain_interfaces(void *buffer, size_t *_bufferSize) { BenaphoreLocker locker(sDomainLock); + uint8 *current = (uint8 *)buffer; + const uint8 *bufferEnd = current + (*_bufferSize); net_domain_private *domain = NULL; - size_t spaceLeft = size; while (true) { domain = (net_domain_private *)list_get_next_item(&sDomains, domain); @@ -118,8 +119,8 @@ if (interface == NULL) break; - size = IF_NAMESIZE + (interface->address ? interface->address->sa_len : 2); - if (spaceLeft < size) + size_t size = IF_NAMESIZE + (interface->address ? interface->address->sa_len : 2); + if ((current + size) > bufferEnd) return ENOBUFS; ifreq request; @@ -132,14 +133,14 @@ request.ifr_addr.sa_family = AF_UNSPEC; } - if (user_memcpy(buffer, &request, size) < B_OK) + if (user_memcpy(current, &request, size) < B_OK) return B_BAD_ADDRESS; - buffer = (void *)((addr_t)buffer + size); - spaceLeft -= size; + current += size; } } + *_bufferSize = current - (uint8 *)buffer; return B_OK; } Modified: haiku/trunk/src/add-ons/kernel/network/stack/domains.h =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/domains.h 2007-04-01 11:38:37 UTC (rev 20490) +++ haiku/trunk/src/add-ons/kernel/network/stack/domains.h 2007-04-01 11:48:07 UTC (rev 20491) @@ -1,5 +1,5 @@ /* - * Copyright 2006, Haiku, Inc. All Rights Reserved. + * Copyright 2006-2007, Haiku, Inc. All Rights Reserved. * Distributed under the terms of the MIT License. * * Authors: @@ -30,7 +30,7 @@ status_t uninit_domains(); uint32 count_domain_interfaces(); -status_t list_domain_interfaces(void *buffer, size_t size); +status_t list_domain_interfaces(void *buffer, size_t *_bufferSize); status_t add_interface_to_domain(net_domain *domain, struct ifreq& request); status_t remove_interface_from_domain(net_interface *interface); Modified: haiku/trunk/src/add-ons/kernel/network/stack/interfaces.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/interfaces.cpp 2007-04-01 11:38:37 UTC (rev 20490) +++ haiku/trunk/src/add-ons/kernel/network/stack/interfaces.cpp 2007-04-01 11:48:07 UTC (rev 20491) @@ -258,12 +258,13 @@ returned. */ status_t -list_device_interfaces(void *buffer, size_t size) +list_device_interfaces(void *buffer, size_t *_bufferSize) { BenaphoreLocker locker(sInterfaceLock); + uint8 *current = (uint8 *)buffer; + const uint8 *bufferEnd = current + (*_bufferSize); net_device_interface *interface = NULL; - size_t spaceLeft = size; while (true) { interface = (net_device_interface *)list_get_next_item(&sInterfaces, @@ -275,17 +276,17 @@ strlcpy(request.ifr_name, interface->name, IF_NAMESIZE); get_device_interface_address(interface, &request.ifr_addr); - size = IF_NAMESIZE + request.ifr_addr.sa_len; - if (spaceLeft < size) + size_t size = IF_NAMESIZE + request.ifr_addr.sa_len; + if ((current + size) > bufferEnd) return ENOBUFS; - if (user_memcpy(buffer, &request, size) < B_OK) + if (user_memcpy(current, &request, size) < B_OK) return B_BAD_ADDRESS; - buffer = (void *)((addr_t)buffer + size); - spaceLeft -= size; + current += size; } + *_bufferSize = current - (uint8 *)buffer;; return B_OK; } Modified: haiku/trunk/src/add-ons/kernel/network/stack/interfaces.h =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/interfaces.h 2007-04-01 11:38:37 UTC (rev 20490) +++ haiku/trunk/src/add-ons/kernel/network/stack/interfaces.h 2007-04-01 11:48:07 UTC (rev 20491) @@ -72,7 +72,7 @@ void get_device_interface_address(net_device_interface *interface, sockaddr *address); uint32 count_device_interfaces(); -status_t list_device_interfaces(void *buffer, size_t size); +status_t list_device_interfaces(void *buffer, size_t *_bufferSize); void put_device_interface(struct net_device_interface *interface); struct net_device_interface *get_device_interface(uint32 index); struct net_device_interface *get_device_interface(const char *name); Modified: haiku/trunk/src/add-ons/kernel/network/stack/link.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/link.cpp 2007-04-01 11:38:37 UTC (rev 20490) +++ haiku/trunk/src/add-ons/kernel/network/stack/link.cpp 2007-04-01 11:48:07 UTC (rev 20491) @@ -1,5 +1,5 @@ /* - * Copyright 2006, Haiku, Inc. All Rights Reserved. + * Copyright 2006-2007, Haiku, Inc. All Rights Reserved. * Distributed under the terms of the MIT License. * * Authors: @@ -174,12 +174,17 @@ case SIOCGIFCONF: { - // count number of interfaces + // retrieve available interfaces struct ifconf config; if (user_memcpy(&config, value, sizeof(struct ifconf)) < B_OK) return B_BAD_ADDRESS; - return list_device_interfaces(config.ifc_buf, config.ifc_len); + status_t result = list_device_interfaces(config.ifc_buf, + (size_t *)&config.ifc_len); + if (result != B_OK) + return result; + + return user_memcpy(value, &config, sizeof(struct ifconf)); } case SIOCGIFADDR: From axeld at mail.berlios.de Sun Apr 1 13:51:15 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Sun, 1 Apr 2007 13:51:15 +0200 Subject: [Haiku-commits] r20492 - haiku/trunk/src/bin/network/traceroute Message-ID: <200704011151.l31BpF3C023099@sheep.berlios.de> Author: axeld Date: 2007-04-01 13:51:14 +0200 (Sun, 01 Apr 2007) New Revision: 20492 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20492&view=rev Added: haiku/trunk/src/bin/network/traceroute/findsaddr-generic.c haiku/trunk/src/bin/network/traceroute/findsaddr.h haiku/trunk/src/bin/network/traceroute/gnuc.h haiku/trunk/src/bin/network/traceroute/ifaddrlist.c haiku/trunk/src/bin/network/traceroute/ifaddrlist.h haiku/trunk/src/bin/network/traceroute/traceroute.h haiku/trunk/src/bin/network/traceroute/version.c Modified: haiku/trunk/src/bin/network/traceroute/Jamfile haiku/trunk/src/bin/network/traceroute/arc4random.c haiku/trunk/src/bin/network/traceroute/traceroute.c Log: Ported latest traceroute, courtesy of Hugo Santos. Modified: haiku/trunk/src/bin/network/traceroute/Jamfile =================================================================== --- haiku/trunk/src/bin/network/traceroute/Jamfile 2007-04-01 11:48:07 UTC (rev 20491) +++ haiku/trunk/src/bin/network/traceroute/Jamfile 2007-04-01 11:51:14 UTC (rev 20492) @@ -8,9 +8,19 @@ # Unfortunately we get more than we want, namely all POSIX headers. } +local defines = [ FDefines HAVE_MALLOC_H=1 HAVE_SYS_SELECT=1 HAVE_NET_ROUTE_H=1 + HAVE_STRERROR=1 HAVE_USLEEP=1 HAVE_SETLINEBUF=1 + BYTESWAP_IP_HDR=1 HAVE_MALLOC_H=1 + HAVE_ICMP_NEXTMTU=1 HAVE_SOCKADDR_SA_LEN=1 ] ; + +SubDirCcFlags $(defines) ; +SubDirC++Flags $(defines) ; + BinCommand traceroute : - arc4random.c + findsaddr-generic.c + ifaddrlist.c traceroute.c + version.c : $(NETWORK_LIBS) $(SELECT_UNAME_ETC_LIB) ; # Installation -- in the test directory for the time being Modified: haiku/trunk/src/bin/network/traceroute/arc4random.c =================================================================== --- haiku/trunk/src/bin/network/traceroute/arc4random.c 2007-04-01 11:48:07 UTC (rev 20491) +++ haiku/trunk/src/bin/network/traceroute/arc4random.c 2007-04-01 11:51:14 UTC (rev 20492) @@ -1,149 +0,0 @@ -/* - * Arc4 random number generator for OpenBSD. - * Copyright 1996 David Mazieres . - * - * Modification and redistribution in source and binary forms is - * permitted provided that due credit is given to the author and the - * OpenBSD project by leaving this copyright notice intact. - */ - -/* - * This code is derived from section 17.1 of Applied Cryptography, - * second edition, which describes a stream cipher allegedly - * compatible with RSA Labs "RC4" cipher (the actual description of - * which is a trade secret). The same algorithm is used as a stream - * cipher called "arcfour" in Tatu Ylonen's ssh package. - * - * Here the stream cipher has been modified always to include the time - * when initializing the state. That makes it impossible to - * regenerate the same random sequence twice, so this can't be used - * for encryption, but will generate good random numbers. - * - * RC4 is a registered trademark of RSA Laboratories. - */ - -#include -#include -#include -#include -#include -#include -#include - -#ifdef __GNUC__ -#define inline __inline -#else /* !__GNUC__ */ -#define inline -#endif /* !__GNUC__ */ - -struct arc4_stream { - uint8 i; - uint8 j; - uint8 s[256]; -}; - -int rs_initialized; -static struct arc4_stream rs; - -uint32 arc4random(void); - - -static inline void arc4_init(struct arc4_stream *as) -{ - int n; - - for (n = 0; n < 256; n++) - as->s[n] = n; - as->i = 0; - as->j = 0; -} - - -static inline void arc4_addrandom(struct arc4_stream *as, - u_char *dat, int datlen) -{ - int n; - uint8 si; - - as->i--; - for (n = 0; n < 256; n++) { - as->i = (as->i + 1); - si = as->s[as->i]; - as->j = (as->j + si + dat[n % datlen]); - as->s[as->i] = as->s[as->j]; - as->s[as->j] = si; - } - as->j = as->i; -} - - -static void arc4_stir(struct arc4_stream *as) -{ - int fd; - struct { - struct timeval tv; - u_int rnd[(128 - sizeof(struct timeval)) / sizeof(u_int)]; - } rdat; - - gettimeofday(&rdat.tv, NULL); - fd = open("/dev/arandom", O_RDONLY); - if (fd != -1) { - read(fd, rdat.rnd, sizeof(rdat.rnd)); - close(fd); - } - /* fd < 0 or failed sysctl ? Ah, what the heck. We'll just take - * whatever was on the stack... */ - - arc4_addrandom(as, (void *) &rdat, sizeof(rdat)); -} - - -static inline uint8 arc4_getbyte(struct arc4_stream *as) -{ - uint8 si, sj; - - as->i = (as->i + 1); - si = as->s[as->i]; - as->j = (as->j + si); - sj = as->s[as->j]; - as->s[as->i] = sj; - as->s[as->j] = si; - return (as->s[(si + sj) & 0xff]); -} - - -static inline uint32 arc4_getword(struct arc4_stream *as) -{ - uint32 val; - val = arc4_getbyte(as) << 24; - val |= arc4_getbyte(as) << 16; - val |= arc4_getbyte(as) << 8; - val |= arc4_getbyte(as); - return val; -} - - -static void arc4random_stir(void) -{ - if (!rs_initialized) { - arc4_init(&rs); - rs_initialized = 1; - } - arc4_stir(&rs); -} - -#if 0 -void arc4random_addrandom(u_char *dat, int datlen) -{ - if (!rs_initialized) - arc4random_stir(); - arc4_addrandom(&rs, dat, datlen); -} -#endif - -uint32 arc4random(void) -{ - if (!rs_initialized) - arc4random_stir(); - return arc4_getword(&rs); -} Added: haiku/trunk/src/bin/network/traceroute/findsaddr-generic.c =================================================================== --- haiku/trunk/src/bin/network/traceroute/findsaddr-generic.c 2007-04-01 11:48:07 UTC (rev 20491) +++ haiku/trunk/src/bin/network/traceroute/findsaddr-generic.c 2007-04-01 11:51:14 UTC (rev 20492) @@ -0,0 +1,96 @@ +/* + * Copyright (c) 2000 + * The Regents of the University of California. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. All advertising materials mentioning features or use of this software + * must display the following acknowledgement: + * This product includes software developed by the Computer Systems + * Engineering Group at Lawrence Berkeley Laboratory. + * 4. Neither the name of the University nor of the Laboratory may be used + * to endorse or promote products derived from this software without + * specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + */ + +#ifndef lint +static const char rcsid[] = + "@(#) $Id: findsaddr-generic.c,v 1.1 2000/11/23 20:17:12 leres Exp $ (LBL)"; +#endif + +#include +#include +#include +#ifdef HAVE_SYS_SOCKIO_H +#include +#endif +#include /* concession to AIX */ + +#if __STDC__ +struct mbuf; +struct rtentry; +#endif + +#include +#include + +#include + +#include +#include +#include +#include +#include + +#include "gnuc.h" +#ifdef HAVE_OS_PROTO_H +#include "os-proto.h" +#endif + +#include "findsaddr.h" +#include "ifaddrlist.h" +#include "traceroute.h" + +/* + * Return the source address for the given destination address + */ +const char * +findsaddr(register const struct sockaddr_in *to, + register struct sockaddr_in *from) +{ + register int n; + struct ifaddrlist *al; + static char errbuf[132]; + + /* Get the interface address list */ + if ((n = ifaddrlist(&al, errbuf)) < 0) + return (errbuf); + + if (n == 0) + return ("Can't find any network interfaces"); + + setsin(from, al->addr); + if (n > 1) + fprintf(stderr, + "%s: Warning: Multiple interfaces found; using %s @ %s\n", + prog, inet_ntoa(from->sin_addr), al->device); + return (NULL); +} Added: haiku/trunk/src/bin/network/traceroute/findsaddr.h =================================================================== --- haiku/trunk/src/bin/network/traceroute/findsaddr.h 2007-04-01 11:48:07 UTC (rev 20491) +++ haiku/trunk/src/bin/network/traceroute/findsaddr.h 2007-04-01 11:51:14 UTC (rev 20492) @@ -0,0 +1,23 @@ +/* + * Copyright (c) 2000 + * The Regents of the University of California. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that: (1) source code distributions + * retain the above copyright notice and this paragraph in its entirety, (2) + * distributions including binary code include the above copyright notice and + * this paragraph in its entirety in the documentation or other materials + * provided with the distribution, and (3) all advertising materials mentioning + * features or use of this software display the following acknowledgement: + * ``This product includes software developed by the University of California, + * Lawrence Berkeley Laboratory and its contributors.'' Neither the name of + * the University nor the names of its contributors may be used to endorse + * or promote products derived from this software without specific prior + * written permission. + * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED + * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF + * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. + * + * @(#) $Id: findsaddr.h,v 1.1 2000/11/19 23:13:38 leres Exp $ (LBL) + */ +const char *findsaddr(const struct sockaddr_in *, struct sockaddr_in *); Added: haiku/trunk/src/bin/network/traceroute/gnuc.h =================================================================== --- haiku/trunk/src/bin/network/traceroute/gnuc.h 2007-04-01 11:48:07 UTC (rev 20491) +++ haiku/trunk/src/bin/network/traceroute/gnuc.h 2007-04-01 11:51:14 UTC (rev 20492) @@ -0,0 +1,43 @@ +/* @(#) $Header: gnuc.h,v 1.3 95/10/09 02:47:01 leres Exp $ (LBL) */ + +/* Define __P() macro, if necessary */ +#ifndef __P +#if __STDC__ +#define __P(protos) protos +#else +#define __P(protos) () +#endif +#endif + +/* inline foo */ +#ifdef __GNUC__ +#define inline __inline +#else +#define inline +#endif + +/* + * Handle new and old "dead" routine prototypes + * + * For example: + * + * __dead void foo(void) __attribute__((volatile)); + * + */ +#ifdef __GNUC__ +#ifndef __dead +#define __dead volatile +#endif +#if __GNUC__ < 2 || (__GNUC__ == 2 && __GNUC_MINOR__ < 5) +#ifndef __attribute__ +#define __attribute__(args) +#endif +#endif +#else +#ifndef __dead +#define __dead +#endif +#ifndef __attribute__ +#define __attribute__(args) +#endif +#endif Added: haiku/trunk/src/bin/network/traceroute/ifaddrlist.c =================================================================== --- haiku/trunk/src/bin/network/traceroute/ifaddrlist.c 2007-04-01 11:48:07 UTC (rev 20491) +++ haiku/trunk/src/bin/network/traceroute/ifaddrlist.c 2007-04-01 11:51:14 UTC (rev 20492) @@ -0,0 +1,183 @@ +/* + * Copyright (c) 1997, 1998, 1999, 2000 + * The Regents of the University of California. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. All advertising materials mentioning features or use of this software + * must display the following acknowledgement: + * This product includes software developed by the Computer Systems + * Engineering Group at Lawrence Berkeley Laboratory. + * 4. Neither the name of the University nor of the Laboratory may be used + * to endorse or promote products derived from this software without + * specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + */ + +#ifndef lint +static const char rcsid[] = + "@(#) $Id: ifaddrlist.c,v 1.9 2000/11/23 20:01:55 leres Exp $ (LBL)"; +#endif + +#include +#include +#include +#ifdef HAVE_SYS_SOCKIO_H +#include +#endif +#include /* concession to AIX */ + +#include /* for SIOCGIFCONF */ + +#if __STDC__ +struct mbuf; +struct rtentry; +#endif + +#include +#include + +#include +#include +#include +#include +#include +#include +#include + +#include "gnuc.h" +#ifdef HAVE_OS_PROTO_H +#include "os-proto.h" +#endif + +#include "ifaddrlist.h" + +/* + * Return the interface list + */ +int +ifaddrlist(register struct ifaddrlist **ipaddrp, register char *errbuf) +{ + register int fd, nipaddr; +#ifdef HAVE_SOCKADDR_SA_LEN + register int n; +#endif + register struct ifreq *ifrp, *ifend, *ifnext, *mp; + register struct sockaddr_in *sin; + register struct ifaddrlist *al; + struct ifconf ifc; + struct ifreq ibuf[(32 * 1024) / sizeof(struct ifreq)], ifr; +#define MAX_IPADDR (sizeof(ibuf) / sizeof(ibuf[0])) + static struct ifaddrlist ifaddrlist[MAX_IPADDR]; + char device[sizeof(ifr.ifr_name) + 1]; + + fd = socket(AF_INET, SOCK_DGRAM, 0); + if (fd < 0) { + (void)sprintf(errbuf, "socket: %s", strerror(errno)); + return (-1); + } + ifc.ifc_len = sizeof(ibuf); + ifc.ifc_buf = (caddr_t)ibuf; + + if (ioctl(fd, SIOCGIFCONF, (char *)&ifc) < 0) { + if (errno == EINVAL) + (void)sprintf(errbuf, + "SIOCGIFCONF: ifreq struct too small (%d bytes)", + sizeof(ibuf)); + else + (void)sprintf(errbuf, "SIOCGIFCONF: %s", + strerror(errno)); + (void)close(fd); + return (-1); + } + ifrp = ibuf; + ifend = (struct ifreq *)((char *)ibuf + ifc.ifc_len); + + al = ifaddrlist; + mp = NULL; + nipaddr = 0; + for (; ifrp < ifend; ifrp = ifnext) { +#ifdef HAVE_SOCKADDR_SA_LEN + n = ifrp->ifr_addr.sa_len + sizeof(ifrp->ifr_name); + /* + * our ifreqs from SIOCGIFCONF dumps are very packed + */ + ifnext = (struct ifreq *)((char *)ifrp + n); + if (ifrp->ifr_addr.sa_family != AF_INET) + continue; +#else + ifnext = ifrp + 1; +#endif + /* + * Need a template to preserve address info that is + * used below to locate the next entry. (Otherwise, + * SIOCGIFFLAGS stomps over it because the requests + * are returned in a union.) + */ + strncpy(ifr.ifr_name, ifrp->ifr_name, sizeof(ifr.ifr_name)); + if (ioctl(fd, SIOCGIFFLAGS, (char *)&ifr, sizeof(ifr)) < 0) { + if (errno == ENXIO) + continue; + (void)sprintf(errbuf, "SIOCGIFFLAGS: %.*s: %s", + (int)sizeof(ifr.ifr_name), ifr.ifr_name, + strerror(errno)); + (void)close(fd); + return (-1); + } + + /* Must be up */ + if ((ifr.ifr_flags & IFF_UP) == 0) + continue; + + /* don't use loopback */ + if ((ifr.ifr_flags & IFF_LOOPBACK) != 0) + continue; + + (void)strncpy(device, ifr.ifr_name, sizeof(ifr.ifr_name)); + device[sizeof(device) - 1] = '\0'; +#ifdef sun + /* Ignore sun virtual interfaces */ + if (strchr(device, ':') != NULL) + continue; +#endif + if (ioctl(fd, SIOCGIFADDR, (char *)&ifr, sizeof(ifr)) < 0) { + (void)sprintf(errbuf, "SIOCGIFADDR: %s: %s", + device, strerror(errno)); + (void)close(fd); + return (-1); + } + + if (nipaddr >= MAX_IPADDR) { + (void)sprintf(errbuf, "Too many interfaces (%d)", + MAX_IPADDR); + (void)close(fd); + return (-1); + } + sin = (struct sockaddr_in *)&ifr.ifr_addr; + al->addr = sin->sin_addr.s_addr; + al->device = strdup(device); + ++al; + ++nipaddr; + } + (void)close(fd); + + *ipaddrp = ifaddrlist; + return (nipaddr); +} Added: haiku/trunk/src/bin/network/traceroute/ifaddrlist.h =================================================================== --- haiku/trunk/src/bin/network/traceroute/ifaddrlist.h 2007-04-01 11:48:07 UTC (rev 20491) +++ haiku/trunk/src/bin/network/traceroute/ifaddrlist.h 2007-04-01 11:51:14 UTC (rev 20492) @@ -0,0 +1,29 @@ +/* + * Copyright (c) 1997 + * The Regents of the University of California. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that: (1) source code distributions + * retain the above copyright notice and this paragraph in its entirety, (2) + * distributions including binary code include the above copyright notice and + * this paragraph in its entirety in the documentation or other materials + * provided with the distribution, and (3) all advertising materials mentioning + * features or use of this software display the following acknowledgement: + * ``This product includes software developed by the University of California, + * Lawrence Berkeley Laboratory and its contributors.'' Neither the name of + * the University nor the names of its contributors may be used to endorse + * or promote products derived from this software without specific prior + * written permission. + * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED + * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF + * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. + * + * @(#) $Header: traceroute.h,v 1.1 97/01/04 19:33:33 leres Locked $ (LBL) + */ + +struct ifaddrlist { + u_int32_t addr; + char *device; +}; + +int ifaddrlist(struct ifaddrlist **, char *); Modified: haiku/trunk/src/bin/network/traceroute/traceroute.c =================================================================== --- haiku/trunk/src/bin/network/traceroute/traceroute.c 2007-04-01 11:48:07 UTC (rev 20491) +++ haiku/trunk/src/bin/network/traceroute/traceroute.c 2007-04-01 11:51:14 UTC (rev 20492) @@ -1,39 +1,32 @@ -/*- - * Copyright (c) 1990, 1993 +/* + * Copyright (c) 1988, 1989, 1991, 1994, 1995, 1996, 1997, 1998, 1999, 2000 * The Regents of the University of California. All rights reserved. * - * This code is derived from software contributed to Berkeley by - * Van Jacobson. - * * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions - * are met: - * 1. Redistributions of source code must retain the above copyright - * notice, this list of conditions and the following disclaimer. - * 2. Redistributions in binary form must reproduce the above copyright - * notice, this list of conditions and the following disclaimer in the - * documentation and/or other materials provided with the distribution. - * 3. All advertising materials mentioning features or use of this software - * must display the following acknowledgement: - * This product includes software developed by the University of - * California, Berkeley and its contributors. - * 4. Neither the name of the University nor the names of its contributors - * may be used to endorse or promote products derived from this software - * without specific prior written permission. - * - * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND - * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE - * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE - * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE - * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL - * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS - * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) - * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT - * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY - * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF - * SUCH DAMAGE. + * modification, are permitted provided that: (1) source code distributions + * retain the above copyright notice and this paragraph in its entirety, (2) + * distributions including binary code include the above copyright notice and + * this paragraph in its entirety in the documentation or other materials + * provided with the distribution, and (3) all advertising materials mentioning + * features or use of this software display the following acknowledgement: + * ``This product includes software developed by the University of California, + * Lawrence Berkeley Laboratory and its contributors.'' Neither the name of + * the University nor the names of its contributors may be used to endorse + * or promote products derived from this software without specific prior + * written permission. + * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED + * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF + * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. */ +#ifndef lint +static const char copyright[] = + "@(#) Copyright (c) 1988, 1989, 1991, 1994, 1995, 1996, 1997, 1998, 1999, 2000\n\ +The Regents of the University of California. All rights reserved.\n"; +static const char rcsid[] = + "@(#)$Id$ (LBL)"; +#endif + /* * traceroute host - trace the route ip packets follow going to "host". * @@ -43,7 +36,7 @@ * icmp "time exceeded" reply from a gateway. We start our probes * with a ttl of one and increase by one until we get an icmp "port * unreachable" (which means we got to "host") or hit a max (which - * defaults to 64 hops & can be changed with the -m flag). Three + * defaults to 30 hops & can be changed with the -m flag). Three * probes (change with -q flag) are sent at each ttl setting and a * line is printed showing the ttl, address of the gateway and * round trip time of each probe. If the probe answers come from @@ -60,7 +53,7 @@ * A sample use might be: * * [yak 71]% traceroute nis.nsf.net. - * traceroute to nis.nsf.net (35.1.1.48), 64 hops max, 56 byte packet + * traceroute to nis.nsf.net (35.1.1.48), 30 hops max, 56 byte packet * 1 helios.ee.lbl.gov (128.3.112.1) 19 ms 19 ms 0 ms * 2 lilac-dmc.Berkeley.EDU (128.32.216.1) 39 ms 39 ms 19 ms * 3 lilac-dmc.Berkeley.EDU (128.32.216.1) 39 ms 39 ms 19 ms @@ -80,7 +73,7 @@ * A more interesting example is: * * [yak 72]% traceroute allspice.lcs.mit.edu. - * traceroute to allspice.lcs.mit.edu (18.26.0.115), 64 hops max + * traceroute to allspice.lcs.mit.edu (18.26.0.115), 30 hops max * 1 helios.ee.lbl.gov (128.3.112.1) 0 ms 0 ms 0 ms * 2 lilac-dmc.Berkeley.EDU (128.32.216.1) 19 ms 19 ms 19 ms * 3 lilac-dmc.Berkeley.EDU (128.32.216.1) 39 ms 19 ms 19 ms @@ -201,209 +194,245 @@ * back to yourself. Unfortunately, SO many gateways botch source * routing, the thing is almost worthless. Maybe one day... * - * -- Van Jacobson (van at helios.ee.lbl.gov) + * -- Van Jacobson (van at ee.lbl.gov) * Tue Dec 20 03:50:13 PST 1988 */ #include +#include +#ifdef HAVE_SYS_SELECT_H +#include +#endif +#include #include -#include -#include #include #include +#include #include -#include #include -#include #include #include #include +#include +#ifdef HAVE_MALLOC_H +#include +#endif +#include #include #include #include #include #include +#include "gnuc.h" +#ifdef HAVE_OS_PROTO_H +#include "os-proto.h" +#endif + +/* rfc1716 */ +#ifndef ICMP_UNREACH_FILTER_PROHIB +#define ICMP_UNREACH_FILTER_PROHIB 13 /* admin prohibited filter */ +#endif +#ifndef ICMP_UNREACH_HOST_PRECEDENCE +#define ICMP_UNREACH_HOST_PRECEDENCE 14 /* host precedence violation */ +#endif +#ifndef ICMP_UNREACH_PRECEDENCE_CUTOFF +#define ICMP_UNREACH_PRECEDENCE_CUTOFF 15 /* precedence cutoff */ +#endif + +#include "findsaddr.h" +#include "ifaddrlist.h" +#include "traceroute.h" + +/* Maximum number of gateways (include room for one noop) */ +#define NGATEWAYS ((int)((MAX_IPOPTLEN - IPOPT_MINOFF - 1) / sizeof(u_int32_t))) + +#ifndef MAXHOSTNAMELEN +#define MAXHOSTNAMELEN 64 +#endif + #define Fprintf (void)fprintf #define Printf (void)printf -#define MAX_LSRR ((MAX_IPOPTLEN - 4) / 4) +/* Host name and address list */ +struct hostinfo { + char *name; + int n; + u_int32_t *addrs; +}; -/* - * Format of the data in a (udp) probe packet. - */ -struct packetdata { - u_char seq; /* sequence number of this packet */ - u_char ttl; /* ttl packet left with */ - uint32_t sec; /* time packet left */ - uint32_t usec; +/* Data section of the probe packet */ +struct outdata { + u_char seq; /* sequence number of this packet */ + u_char ttl; /* ttl packet left with */ + struct timeval tv; /* time packet left */ }; -struct in_addr gateway[MAX_LSRR + 1]; -int lsrrlen = 0; -int32_t sec_perturb; -int32_t usec_perturb; +#ifndef HAVE_ICMP_NEXTMTU +/* Path MTU Discovery (RFC1191) */ +struct my_pmtu { + u_short ipm_void; + u_short ipm_nextmtu; +}; +#endif -u_char packet[512], *outpacket; /* last inbound (icmp) packet */ +u_char packet[512]; /* last inbound (icmp) packet */ -int wait_for_reply (int, struct sockaddr_in *, struct timeval *); -void send_probe (int, int, int, struct sockaddr_in *); -int packet_ok (u_char *, int, struct sockaddr_in *, int, int); -void print (u_char *, int, struct sockaddr_in *); -char *inetname (struct in_addr); -u_short compute_in_cksum(uint16_t *, int); -void usage (void); +struct ip *outip; /* last output (udp) packet */ +struct udphdr *outudp; /* last output (udp) packet */ +struct outdata *outdata; /* last output (udp) packet */ +struct icmp *outicmp; /* last output (icmp) packet */ + +/* loose source route gateway list (including room for final destination) */ +u_int32_t gwlist[NGATEWAYS + 1]; + int s; /* receive (icmp) socket file descriptor */ -int sndsock; /* send (udp) socket file descriptor */ -struct timezone tz; /* leftover */ +int sndsock; /* send (udp/icmp) socket file descriptor */ -int datalen; /* How much data */ -int headerlen; /* How long packet's header is */ +struct sockaddr whereto; /* Who to try to reach */ +struct sockaddr wherefrom; /* Who we are */ +int packlen; /* total length of packet */ +int minpacket; /* min ip packet size */ +int maxpacket = 32 * 1024; /* max ip packet size */ +int pmtu; /* Path MTU Discovery (RFC1191) */ +u_int pausemsecs; -char *source = 0; +char *prog; +char *source; char *hostname; +char *device; +static const char devnull[] = "/dev/null"; int nprobes = 3; -int max_ttl = IPDEFTTL; +int max_ttl = 30; int first_ttl = 1; u_short ident; -u_short port = 32768+666; /* start udp dest port # for probe packets */ -u_char proto = IPPROTO_UDP; -u_char icmp_type = ICMP_ECHO; /* default ICMP code/type */ -u_char icmp_code = 0; +u_short port = 32768 + 666; /* start udp dest port # for probe packets */ + int options; /* socket options */ int verbose; int waittime = 5; /* time to wait for response (in seconds) */ int nflag; /* print addresses numerically */ -int dump; +int useicmp; /* use icmp echo instead of udp packets */ +#ifdef CANT_HACK_IPCKSUM +int doipcksum = 0; /* don't calculate ip checksums by default */ +#else +int doipcksum = 1; /* calculate ip checksums by default */ +#endif +int optlen; /* length of ip options */ -/* arc4random is defined in stdlib.h on OpenBSD, so we'll just forward - * declare the prototype here to stop the compiler moaning. - */ -uint32_t arc4random(void); +extern int optind; +extern int opterr; +extern char *optarg; -static void err(int exitval, char *where) -{ - printf("error: %s: error %d [%s]\n", where, errno, strerror(errno)); - exit(exitval); -} +/* Forwards */ +double deltaT(struct timeval *, struct timeval *); +void freehostinfo(struct hostinfo *); +void getaddr(u_int32_t *, char *); +struct hostinfo *gethostinfo(char *); +u_short in_cksum(u_short *, int); +char *inetname(struct in_addr); +int main(int, char **); +int packet_ok(u_char *, int, struct sockaddr_in *, int); +char *pr_type(u_char); +void print(u_char *, int, struct sockaddr_in *); +void send_probe(int, int, struct timeval *); +int str2val(const char *, const char *, int, int); +void tvsub(struct timeval *, struct timeval *); +__dead void usage(void); +int wait_for_reply(int, struct sockaddr_in *, const struct timeval *); +#ifndef HAVE_USLEEP +int usleep(u_int); +#endif -static void errx(int exitval, char *fmt_string, char *value) +int +main(int argc, char **argv) { - printf("error: "); - printf(fmt_string, value); - exit(exitval); -} + register int op, code, n; + register char *cp; + register const char *err; + register u_char *outp; + register u_int32_t *ap; + register struct sockaddr_in *from = (struct sockaddr_in *)&wherefrom; + register struct sockaddr_in *to = (struct sockaddr_in *)&whereto; + register struct hostinfo *hi; + int on = 1; + register struct protoent *pe; + register int ttl, probe, i; + register int seq = 0; + int tos = 0, settos = 0; + register int lsrr = 0; + register u_short off = 0; + struct ifaddrlist *al; + char errbuf[132]; + if (argv[0] == NULL) + prog = "traceroute"; + else if ((cp = strrchr(argv[0], '/')) != NULL) + prog = cp + 1; + else + prog = argv[0]; -int main(int argc, char **argv) -{ - struct hostent *hp; - struct protoent *pe; - struct sockaddr_in from, to; - int ch, i, lsrr, on, probe, seq, tos, ttl, ttl_flag, incflag = 1; - struct ip *ip; - uint32_t tmprnd; - int sump = 0; + opterr = 0; + while ((op = getopt(argc, argv, "dFInrvxf:g:i:m:p:q:s:t:w:z:")) != EOF) + switch (op) { - if ((pe = getprotobyname("icmp")) == NULL) { - Fprintf(stderr, "icmp: unknown protocol\n"); - exit(10); - } - if ((s = socket(AF_INET, SOCK_RAW, pe->p_proto)) < 0) - err(5, "icmp socket"); - if ((sndsock = socket(AF_INET, SOCK_RAW, IPPROTO_RAW)) < 0) - err(5, "raw socket"); + case 'd': + options |= SO_DEBUG; + break; - /* revoke privs */ -// seteuid(getuid()); -// setuid(getuid()); - - ttl_flag = 0; - lsrr = 0; - on = 1; - seq = tos = 0; - while ((ch = getopt(argc, argv, "SDIdg:f:m:np:q:rs:t:w:vlP:c")) != -1) - switch (ch) { - case 'S': - sump = 1; - break; case 'f': - first_ttl = atoi(optarg); - if (first_ttl < 1 || first_ttl > max_ttl) { - printf("min ttl must be 1 to %d.", max_ttl); - exit(1); - } + first_ttl = str2val(optarg, "first ttl", 1, 255); break; - case 'c': - incflag = 0; + + case 'F': + off = IP_DF; break; - case 'd': - options |= SO_DEBUG; - break; - case 'D': - dump = 1; - break; + case 'g': - if (lsrr >= MAX_LSRR) { - printf("too many gateways; max %d", MAX_LSRR); + if (lsrr >= NGATEWAYS) { + Fprintf(stderr, + "%s: No more than %d gateways\n", + prog, NGATEWAYS); exit(1); } - if (inet_aton(optarg, &gateway[lsrr]) == 0) { - hp = gethostbyname(optarg); - if (hp == 0) - errx(1, "unknown host %s", optarg); - memcpy(&gateway[lsrr], hp->h_addr, hp->h_length); - } - if (++lsrr == 1) - lsrrlen = 4; - lsrrlen += 4; + getaddr(gwlist + lsrr, optarg); + ++lsrr; break; + + case 'i': [... truncated: 1345 lines follow ...] From mmu_man at mail.berlios.de Sun Apr 1 13:51:32 2007 From: mmu_man at mail.berlios.de (mmu_man at BerliOS) Date: Sun, 1 Apr 2007 13:51:32 +0200 Subject: [Haiku-commits] r20493 - haiku/trunk/src/add-ons/kernel/drivers/ports/usb_serial Message-ID: <200704011151.l31BpWdE023137@sheep.berlios.de> Author: mmu_man Date: 2007-04-01 13:51:32 +0200 (Sun, 01 Apr 2007) New Revision: 20493 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20493&view=rev Modified: haiku/trunk/src/add-ons/kernel/drivers/ports/usb_serial/driver.h haiku/trunk/src/add-ons/kernel/drivers/ports/usb_serial/prolific.c Log: Fix sending data with prolific devices. Seems they weren't initialised correctly. We now send the same stuff Linux does (without telling why), and it seems to work. Modified: haiku/trunk/src/add-ons/kernel/drivers/ports/usb_serial/driver.h =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/ports/usb_serial/driver.h 2007-04-01 11:51:14 UTC (rev 20492) +++ haiku/trunk/src/add-ons/kernel/drivers/ports/usb_serial/driver.h 2007-04-01 11:51:32 UTC (rev 20493) @@ -133,6 +133,7 @@ struct _spec_acm{ /* ACM-compatible devices */ }acm; struct _spec_prolific{ /* Prolific devices*/ + bool is_HX; /* Linux handles HX type differently */ }prolific; struct _spec_ftdi{ /* FTDI devices*/ uint8 hdrlen; Modified: haiku/trunk/src/add-ons/kernel/drivers/ports/usb_serial/prolific.c =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/ports/usb_serial/prolific.c 2007-04-01 11:51:14 UTC (rev 20492) +++ haiku/trunk/src/add-ons/kernel/drivers/ports/usb_serial/prolific.c 2007-04-01 11:51:32 UTC (rev 20493) @@ -18,18 +18,30 @@ struct usb_endpoint_info *comm_epi = NULL; struct usb_endpoint_info *data_out_epi = NULL; struct usb_endpoint_info *data_in_epi = NULL; + const usb_device_descriptor *ddesc; status_t status = ENODEV; int i = 0; TRACE_FUNCALLS("> add_prolific_device(%08x, %08x)\n", usd, uci); + + /* check for device type. + * Linux checks for type 0, 1 and HX, but handles 0 and 1 the same. + * We'll just check for HX then. + */ + if ((ddesc = (*usb_m->get_device_descriptor)(usd->dev))){ + usd->spec.prolific.is_HX = (ddesc->device_class != 0x02 && + ddesc->max_packet_size_0 == 0x40); + } if(uci->interface_count){ struct usb_interface_info *uii = uci->interface[0].active; for(i = 0; i < uii->endpoint_count; i++){ if(uii->endpoint[i].descr->attributes == USB_EP_ATTR_INTERRUPT){ if((uii->endpoint[i].descr->endpoint_address & USB_EP_ADDR_DIR_IN) - == USB_EP_ADDR_DIR_IN) /*USB_EP_ADDR_DIR_OUT = 0x0*/ + == USB_EP_ADDR_DIR_IN /*USB_EP_ADDR_DIR_OUT = 0x0*/){ + TRACE("add_prolific_device:comm endpoint at %d\n", i); comm_epi = &uii->endpoint[i]; + } } } /*They say that USB-RSAQ1 has 2 interfaces */ @@ -41,10 +53,12 @@ if(uii->endpoint[i].descr->attributes == USB_EP_ATTR_BULK){ if((uii->endpoint[i].descr->endpoint_address & USB_EP_ADDR_DIR_IN) == USB_EP_ADDR_DIR_IN){ + TRACE("add_prolific_device:in endpoint at %d\n", i); data_in_epi = &uii->endpoint[i]; }else{ - if(uii->endpoint[i].descr->endpoint_address - /*USB_EP_ADDR_DIR_OUT = 0x0*/){ + if((uii->endpoint[i].descr->endpoint_address & USB_EP_ADDR_DIR_IN) + == USB_EP_ADDR_DIR_OUT){ + TRACE("add_prolific_device:out endpoint at %d\n", i); data_out_epi = &uii->endpoint[i]; } } @@ -63,13 +77,72 @@ return status; } +struct req_item { + uint8 requestType; + uint8 request; + uint16 value; + uint16 index; +}; + +#define PLRT_O (USB_REQTYPE_VENDOR | USB_REQTYPE_DEVICE_OUT) +#define PLRT_I (USB_REQTYPE_VENDOR | USB_REQTYPE_DEVICE_IN) + +/* Linux sends all those, and it seems to work for me */ +/* see drivers/usb/serial/pl2303.c */ +static struct req_item pl_reset_common_reqs[] = { + {PLRT_I, PROLIFIC_SET_REQUEST, 0x8484, 0}, + {PLRT_O, PROLIFIC_SET_REQUEST, 0x0404, 0}, + {PLRT_I, PROLIFIC_SET_REQUEST, 0x8484, 0}, + {PLRT_I, PROLIFIC_SET_REQUEST, 0x8383, 0}, + {PLRT_I, PROLIFIC_SET_REQUEST, 0x8484, 0}, + {PLRT_O, PROLIFIC_SET_REQUEST, 0x0404, 1}, + {PLRT_I, PROLIFIC_SET_REQUEST, 0x8484, 0}, + {PLRT_I, PROLIFIC_SET_REQUEST, 0x8383, 0}, + {PLRT_O, PROLIFIC_SET_REQUEST, 0x0000, 1}, + {PLRT_O, PROLIFIC_SET_REQUEST, 0x0001, 0} +}; +static struct req_item pl_reset_common_hx[] = { + {PLRT_O, PROLIFIC_SET_REQUEST, 2, 0x44}, + {PLRT_O, PROLIFIC_SET_REQUEST, 8, 0}, + {PLRT_O, PROLIFIC_SET_REQUEST, 0, 0} +}; +static struct req_item pl_reset_common_nhx[] = { + {PLRT_O, PROLIFIC_SET_REQUEST, 2, 0x24} +}; + +static status_t usb_send_requ_list(const usb_device *dev, struct req_item *list, size_t len){ + char buf[10]; + int i; + status_t status; + for (i = 0; i < len; i++){ + bool o = (list[i].requestType == PLRT_O); + size_t len = 1; + status = (*usb_m->send_request)(dev, + list[i].requestType, + list[i].request, + list[i].value, + list[i].index, + 0, o?0:buf, o?0:len, &len); + TRACE("usb_send_requ_list: reqs[%d]: %08lx\n", i, status); + } + return B_OK; +} + status_t reset_prolific_device(usb_serial_device *usd){ status_t status; size_t len = 0; TRACE_FUNCALLS("> reset_prolific_device(%08x)\n", usd); - status = (*usb_m->send_request)(usd->dev, +/* status = (*usb_m->send_request)(usd->dev, USB_REQTYPE_VENDOR | USB_REQTYPE_DEVICE_OUT, PROLIFIC_SET_REQUEST, 0, 0, 0, 0, 0, &len); + */ + + usb_send_requ_list(usd->dev, pl_reset_common_reqs, SIZEOF(pl_reset_common_reqs)); + if (usd->spec.prolific.is_HX) + usb_send_requ_list(usd->dev, pl_reset_common_hx, SIZEOF(pl_reset_common_hx)); + else + usb_send_requ_list(usd->dev, pl_reset_common_nhx, SIZEOF(pl_reset_common_nhx)); + TRACE_FUNCRET("< reset_prolific_device returns:%08x\n", status); return status; } From axeld at mail.berlios.de Sun Apr 1 14:06:17 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Sun, 1 Apr 2007 14:06:17 +0200 Subject: [Haiku-commits] r20494 - in haiku/trunk: headers/posix/net headers/posix/sys src/add-ons/kernel/network/stack Message-ID: <200704011206.l31C6Hpu023995@sheep.berlios.de> Author: axeld Date: 2007-04-01 14:06:16 +0200 (Sun, 01 Apr 2007) New Revision: 20494 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20494&view=rev Modified: haiku/trunk/headers/posix/net/route.h haiku/trunk/headers/posix/sys/sockio.h haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp haiku/trunk/src/add-ons/kernel/network/stack/routes.cpp haiku/trunk/src/add-ons/kernel/network/stack/routes.h Log: Support getting route information for a specific destination using SIOCGETRT. Patch by Hugo Santos. Modified: haiku/trunk/headers/posix/net/route.h =================================================================== --- haiku/trunk/headers/posix/net/route.h 2007-04-01 11:51:32 UTC (rev 20493) +++ haiku/trunk/headers/posix/net/route.h 2007-04-01 12:06:16 UTC (rev 20494) @@ -1,5 +1,5 @@ /* - * Copyright 2006, Haiku, Inc. All Rights Reserved. + * Copyright 2006-2007, Haiku, Inc. All Rights Reserved. * Distributed under the terms of the MIT License. */ #ifndef _NET_ROUTE_H @@ -27,6 +27,7 @@ struct sockaddr *destination; struct sockaddr *mask; struct sockaddr *gateway; + struct sockaddr *source; uint32_t flags; uint32_t mtu; }; Modified: haiku/trunk/headers/posix/sys/sockio.h =================================================================== --- haiku/trunk/headers/posix/sys/sockio.h 2007-04-01 11:51:32 UTC (rev 20493) +++ haiku/trunk/headers/posix/sys/sockio.h 2007-04-01 12:06:16 UTC (rev 20494) @@ -1,5 +1,5 @@ /* - * Copyright 2002-2006, Haiku Inc. All Rights Reserved. + * Copyright 2002-2007, Haiku Inc. All Rights Reserved. * Distributed under the terms of the MIT License. */ #ifndef _SYS_SOCKIO_H @@ -36,6 +36,7 @@ SIOCGRTSIZE, /* get route table size */ SIOCGRTTABLE, /* get route table */ + SIOCGETRT, /* get route information for destination */ SIOCGIFSTATS, /* get interface stats */ SIOCGIFPARAM, /* get interface parameter */ @@ -53,4 +54,4 @@ SIOCGPGRP /* get process group */ }; -#endif /* _SYS_SOCKIO_H */ +#endif /* _SYS_SOCKIO_H */ Modified: haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp 2007-04-01 11:51:32 UTC (rev 20493) +++ haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp 2007-04-01 12:06:16 UTC (rev 20494) @@ -305,6 +305,8 @@ return list_routes(domain, config.ifc_buf, config.ifc_len); } + case SIOCGETRT: + return get_route_information(domain, value, *_length); default: { Modified: haiku/trunk/src/add-ons/kernel/network/stack/routes.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/routes.cpp 2007-04-01 11:51:32 UTC (rev 20493) +++ haiku/trunk/src/add-ons/kernel/network/stack/routes.cpp 2007-04-01 12:06:16 UTC (rev 20494) @@ -1,5 +1,5 @@ /* - * Copyright 2006, Haiku, Inc. All Rights Reserved. + * Copyright 2006-2007, Haiku, Inc. All Rights Reserved. * Distributed under the terms of the MIT License. * * Authors: @@ -35,6 +35,51 @@ #endif +class UserRouteBuffer { + public: + UserRouteBuffer(uint8 *buffer, size_t available) + : + fBuffer(buffer), + fAvailable(available), + fStatus(B_OK) + { + } + + sockaddr * + Copy(sockaddr *source) + { + sockaddr *target = (sockaddr *)fBuffer; + + if (source == NULL || (fStatus = _Copy(source)) != B_OK) + return NULL; + + return target; + } + + status_t Status() const { return fStatus; } + + private: + status_t + _Copy(sockaddr *source) + { + if (fAvailable < source->sa_len) + return ENOBUFS; + + if (user_memcpy(fBuffer, source, source->sa_len) < B_OK) + return B_BAD_ADDRESS; + + fAvailable -= source->sa_len; + fBuffer += source->sa_len; + + return B_OK; + } + + uint8 *fBuffer; + size_t fAvailable; + status_t fStatus; +}; + + net_route_private::net_route_private() { destination = mask = gateway = NULL; @@ -78,6 +123,25 @@ } +static status_t +user_copy_address(const sockaddr *from, sockaddr_storage *to) +{ + if (from == NULL) + return B_BAD_ADDRESS; + + if (user_memcpy(to, from, sizeof(sockaddr)) < B_OK) + return B_BAD_ADDRESS; + + if (to->ss_len > sizeof(sockaddr)) { + if (to->ss_len > sizeof(sockaddr_storage)) + return B_BAD_VALUE; + if (user_memcpy(to, from, to->ss_len) < B_OK) + return B_BAD_ADDRESS; + } + + return B_OK; +} + static net_route_private * find_route(struct net_domain *_domain, const net_route *description) { @@ -415,6 +479,55 @@ } +static status_t +fill_route_entry(route_entry *target, void *_buffer, size_t bufferSize, + net_route *route) +{ + UserRouteBuffer buffer(((uint8 *)_buffer) + sizeof(route_entry), + bufferSize - sizeof(route_entry)); + + target->destination = buffer.Copy(route->destination); + target->mask = buffer.Copy(route->mask); + target->gateway = buffer.Copy(route->gateway); + target->source = buffer.Copy(route->interface->address); + target->flags = route->flags; + target->mtu = route->mtu; + + return buffer.Status(); +} + + +status_t +get_route_information(struct net_domain *_domain, void *value, size_t length) +{ + struct net_domain_private *domain = (net_domain_private *)_domain; + + if (length < sizeof(route_entry)) + return B_BAD_VALUE; + + route_entry entry; + if (user_memcpy(&entry, value, sizeof(route_entry)) < B_OK) + return B_BAD_ADDRESS; + + sockaddr_storage destination; + status_t status = user_copy_address(entry.destination, &destination); + if (status != B_OK) + return status; + + BenaphoreLocker locker(domain->lock); + + net_route_private *route = find_route(domain, (sockaddr *)&destination); + if (route == NULL) + return B_ENTRY_NOT_FOUND; + + status = fill_route_entry(&entry, value, length, route); + if (status != B_OK) + return status; + + return user_memcpy(value, &entry, sizeof(route_entry)); +} + + struct net_route * get_route(struct net_domain *_domain, const struct sockaddr *address) { Modified: haiku/trunk/src/add-ons/kernel/network/stack/routes.h =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/routes.h 2007-04-01 11:51:32 UTC (rev 20493) +++ haiku/trunk/src/add-ons/kernel/network/stack/routes.h 2007-04-01 12:06:16 UTC (rev 20494) @@ -1,5 +1,5 @@ /* - * Copyright 2006, Haiku, Inc. All Rights Reserved. + * Copyright 2006-2007, Haiku, Inc. All Rights Reserved. * Distributed under the terms of the MIT License. * * Authors: @@ -23,11 +23,13 @@ }; typedef DoublyLinkedList RouteList; -typedef DoublyLinkedList > RouteInfoList; +typedef DoublyLinkedList > RouteInfoList; uint32 route_table_size(struct net_domain_private *domain); -status_t list_routes(struct net_domain_private *domain, void *buffer, size_t size); +status_t list_routes(struct net_domain_private *domain, void *buffer, + size_t size); status_t control_routes(struct net_interface *interface, int32 option, void *argument, size_t length); @@ -35,7 +37,10 @@ const struct net_route *route); status_t remove_route(struct net_domain *domain, const struct net_route *route); -struct net_route *get_route(struct net_domain *domain, const struct sockaddr *address); +status_t get_route_information(struct net_domain *domain, void *buffer, + size_t length); +struct net_route *get_route(struct net_domain *domain, + const struct sockaddr *address); void put_route(struct net_domain *domain, struct net_route *route); status_t register_route_info(struct net_domain *domain, From axeld at mail.berlios.de Sun Apr 1 14:10:20 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Sun, 1 Apr 2007 14:10:20 +0200 Subject: [Haiku-commits] r20495 - haiku/trunk/src/bin/network/route Message-ID: <200704011210.l31CAKPZ024175@sheep.berlios.de> Author: axeld Date: 2007-04-01 14:10:20 +0200 (Sun, 01 Apr 2007) New Revision: 20495 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20495&view=rev Modified: haiku/trunk/src/bin/network/route/route.cpp Log: Added 'route get' support to the route command (via SIOCGETRT), patch by Hugo Santos. Modified: haiku/trunk/src/bin/network/route/route.cpp =================================================================== --- haiku/trunk/src/bin/network/route/route.cpp 2007-04-01 12:06:16 UTC (rev 20494) +++ haiku/trunk/src/bin/network/route/route.cpp 2007-04-01 12:10:20 UTC (rev 20495) @@ -1,5 +1,5 @@ /* - * Copyright 2006, Haiku, Inc. All Rights Reserved. + * Copyright 2006-2007, Haiku, Inc. All Rights Reserved. * Distributed under the terms of the MIT License. * * Authors: @@ -32,10 +32,10 @@ RTM_LIST = 0, RTM_DELETE, RTM_ADD, - + RTM_GET, + // TODO: RTM_CHANGE, - RTM_GET, RTM_FLUSH, }; @@ -295,6 +295,45 @@ } +void +get_route(int socket, route_entry &route) +{ + union { + route_entry request; + uint8 buffer[512]; + }; + + request = route; + + if (ioctl(socket, SIOCGETRT, buffer, sizeof(buffer)) < 0) { + fprintf(stderr, "%s: Could not get route: %s\n", + kProgramName, strerror(errno)); + return; + } + + // find family + const address_family *family = NULL; + for (int32 i = 0; kFamilies[i].family >= 0; i++) { + if (route.destination->sa_family == kFamilies[i].family) { + family = &kFamilies[i]; + break; + } + } + + if (family != NULL) { + printf("%s ", family->address_to_string(request.destination)); + printf("mask %s ", family->address_to_string(request.mask)); + + if (request.flags & RTF_GATEWAY) + printf("gateway %s ", family->address_to_string(request.gateway)); + + printf("source %s\n", family->address_to_string(request.source)); + } else { + printf("unknown family "); + } +} + + // #pragma mark - @@ -322,6 +361,12 @@ usage(1); mode = RTM_ADD; + } else if (!strcmp(argv[1], "get")) { + // get route for destination + if (argc < 3) + usage(1); + + mode = RTM_GET; } } @@ -469,6 +514,10 @@ } } break; + + case RTM_GET: + get_route(socket, route); + break; } close(socket); From superstippi at gmx.de Sun Apr 1 14:12:26 2007 From: superstippi at gmx.de (Stephan Assmus) Date: Sun, 01 Apr 2007 14:12:26 +0200 Subject: [Haiku-commits] r20493 - haiku/trunk/src/add-ons/kernel/drivers/ports/usb_serial In-Reply-To: <200704011151.l31BpWdE023137@sheep.berlios.de> References: <200704011151.l31BpWdE023137@sheep.berlios.de> Message-ID: <20070401141226.2213.6@stippis.mshome.net> Hi Francois, pretty cool to see you work on this! Is the driver working under Haiku as well, what is your test environment? Best regards, -Stephan From axeld at mail.berlios.de Sun Apr 1 14:14:20 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Sun, 1 Apr 2007 14:14:20 +0200 Subject: [Haiku-commits] r20496 - haiku/trunk/src/bin/network/traceroute Message-ID: <200704011214.l31CEKbS024411@sheep.berlios.de> Author: axeld Date: 2007-04-01 14:14:20 +0200 (Sun, 01 Apr 2007) New Revision: 20496 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20496&view=rev Added: haiku/trunk/src/bin/network/traceroute/findsaddr-haiku.c Modified: haiku/trunk/src/bin/network/traceroute/Jamfile Log: Traceroute: use new SIOCGETRT to obtain the source address to be used when communicating with the destination, patch by Hugo Santos. Modified: haiku/trunk/src/bin/network/traceroute/Jamfile =================================================================== --- haiku/trunk/src/bin/network/traceroute/Jamfile 2007-04-01 12:10:20 UTC (rev 20495) +++ haiku/trunk/src/bin/network/traceroute/Jamfile 2007-04-01 12:14:20 UTC (rev 20496) @@ -17,7 +17,7 @@ SubDirC++Flags $(defines) ; BinCommand traceroute : - findsaddr-generic.c + findsaddr-haiku.c ifaddrlist.c traceroute.c version.c Added: haiku/trunk/src/bin/network/traceroute/findsaddr-haiku.c =================================================================== --- haiku/trunk/src/bin/network/traceroute/findsaddr-haiku.c 2007-04-01 12:10:20 UTC (rev 20495) +++ haiku/trunk/src/bin/network/traceroute/findsaddr-haiku.c 2007-04-01 12:14:20 UTC (rev 20496) @@ -0,0 +1,49 @@ +/* + * Copyright 2007, Haiku Inc. All rights reserved. + * Distributed under the terms of the MIT License. + * + * Authors: + * Hugo Santos + */ + + +#include +#include +#include +#include +#include +#include +#include + +#include "findsaddr.h" + // is not self containing... + + +const char * +findsaddr(const struct sockaddr_in *to, struct sockaddr_in *from) +{ + uint8_t buffer[256]; + struct route_entry *request = (struct route_entry *)buffer; + + int sock = socket(AF_INET, SOCK_DGRAM, 0); + if (sock < 0) + return "socket() failed"; + + memset(request, 0, sizeof(struct route_entry)); + request->destination = (struct sockaddr *)to; + + if (ioctl(sock, SIOCGETRT, buffer, sizeof(buffer)) < 0) { + close(sock); + return "ioctl(SIOCGETRT) failed"; + } + + if (request->source != NULL && request->source->sa_family == AF_INET) + memcpy(from, request->source, sizeof(struct sockaddr_in)); + + close(sock); + + if (request->source == NULL || request->source->sa_family != AF_INET) + return "No address available"; + + return NULL; +} From axeld at mail.berlios.de Sun Apr 1 14:24:44 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Sun, 1 Apr 2007 14:24:44 +0200 Subject: [Haiku-commits] r20497 - haiku/trunk/src/add-ons/kernel/network/stack Message-ID: <200704011224.l31COiFF024867@sheep.berlios.de> Author: axeld Date: 2007-04-01 14:24:44 +0200 (Sun, 01 Apr 2007) New Revision: 20497 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20497&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/stack/routes.cpp Log: Missed an improvement Hugo sent me a bit later. Modified: haiku/trunk/src/add-ons/kernel/network/stack/routes.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/routes.cpp 2007-04-01 12:14:20 UTC (rev 20496) +++ haiku/trunk/src/add-ons/kernel/network/stack/routes.cpp 2007-04-01 12:24:44 UTC (rev 20497) @@ -50,7 +50,9 @@ { sockaddr *target = (sockaddr *)fBuffer; - if (source == NULL || (fStatus = _Copy(source)) != B_OK) + if (fStatus != B_OK + || source == NULL + || (fStatus = _Copy(source)) != B_OK) return NULL; return target; From bonefish at mail.berlios.de Sun Apr 1 15:41:19 2007 From: bonefish at mail.berlios.de (bonefish at BerliOS) Date: Sun, 1 Apr 2007 15:41:19 +0200 Subject: [Haiku-commits] r20498 - haiku/trunk/src/build/libhaikucompat Message-ID: <200704011341.l31DfJiB029573@sheep.berlios.de> Author: bonefish Date: 2007-04-01 15:41:19 +0200 (Sun, 01 Apr 2007) New Revision: 20498 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20498&view=rev Modified: haiku/trunk/src/build/libhaikucompat/Jamfile Log: Fixed TARGET_PLATFORM r5 build. Modified: haiku/trunk/src/build/libhaikucompat/Jamfile =================================================================== --- haiku/trunk/src/build/libhaikucompat/Jamfile 2007-04-01 12:24:44 UTC (rev 20497) +++ haiku/trunk/src/build/libhaikucompat/Jamfile 2007-04-01 13:41:19 UTC (rev 20498) @@ -4,14 +4,18 @@ UseHeaders [ FDirName $(HAIKU_TOP) headers build private kernel ] : true ; +local libbeTestSources ; +if $(TARGET_PLATFORM) = libbe_test { + libbeTestSources = misc.cpp syscalls.cpp ; +} + StaticLibrary libhaikucompat.a : strcasestr.c strlcat.c strlcpy.c strnlen.c - misc.cpp - syscalls.cpp + $(libbeTestSources) ; SEARCH on [ FGristFiles strcasestr.c strlcat.c strlcpy.c strnlen.c ] From bonefish at cs.tu-berlin.de Sun Apr 1 16:45:08 2007 From: bonefish at cs.tu-berlin.de (Ingo Weinhold) Date: Sun, 01 Apr 2007 16:45:08 +0200 Subject: [Haiku-commits] r20483 - haiku/trunk/src/system/kernel/cache In-Reply-To: <2427272475-BeMail@zon> References: <2427272475-BeMail@zon> Message-ID: <20070401164508.754.2@cs.tu-berlin.de> On 2007-04-01 at 13:34:34 [+0200], Axel D?rfler wrote: > bonefish at BerliOS wrote: > > A few more changes to pages_io(): > > * Added a few comments. > > * Simplified the nested while loops by dropping the special handling > > for the > > first iovec and restructuring the innermost loop. This also rules > > out > > the possibility of a zero-length temporary vec. IMHO the > > readability > > has improved quite a bit (YMMV :-). Hopefully without introducing > > new > > bugs; please review! > > Looks okay, but I'm not sure if I find it easier to read :-) Well, you're cheating -- you wrote the function in the first place. :-) BTW, although l33t, I don't really think a "... += ... = ... = ..." construct is really good to read, especially, if it extends a single line. > After all, the vecOffset is a special case that only affects the first > iovec; True enough, but since it's cheap enough to do it in general, I don't see the need for special casing it, particularly since that special case look completely different than the handling in the loop (code readability-- ;-). > now, you have doubled the number of loops without good reason. Not completely without good reason. The up-front "vecLeft == 0" check is needed to prevent zero-length tempVecs (which aren't fatal, but not nice anyway) and increasing i requires a check against count with a possible termination of the loop (which the loop head delivers). So the only thing really doubled are the two other checks in the loop condition. I suppose one could replace if (vecLeft == 0) { i++; vecOffset = 0; continue; } by if (vecLeft == 0) { vecOffset = 0; if (++i >= count) break; vecLeft = vecs[i].iov_len; } That wouldn't filter out zero-length iovecs anymore. So one could just as well move the check to the end of the loop: if (vecOffset == vecs[i].iov_len) { vecOffset = 0; i++; } > BTW, I've updated the pages_io_test.cpp as well, in case you missed > that one :) Oh, right. :-) > > * Corrected computation of totalSize in case less than size has been > > read/written. > > Thanks, I missed that one :-) > > > * Also set *_numBytes in case all fileVecs have been processed. Only > > relevant in case the request extends beyond the end of file. > > In that case, it would already have dropped out earlier in the loop, so > I don't think this is necessary. I don't see where. If 200 KB shall be read, but the fileVecs provide only 100 KB (ATM that can happen e.g. when the file is heavily fragmented and MAX_FILE_IO_VECS fileVecs don't suffice), all fileVecs will be processed and the outer loop simply terminates. None of the error conditions in the inner loops will have been met. CU, Ingo From bonefish at mail.berlios.de Sun Apr 1 19:05:27 2007 From: bonefish at mail.berlios.de (bonefish at BerliOS) Date: Sun, 1 Apr 2007 19:05:27 +0200 Subject: [Haiku-commits] r20499 - in haiku/trunk/src/system/kernel: . lib Message-ID: <200704011705.l31H5Rst027659@sheep.berlios.de> Author: bonefish Date: 2007-04-01 19:05:26 +0200 (Sun, 01 Apr 2007) New Revision: 20499 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20499&view=rev Added: haiku/trunk/src/system/kernel/lib/kernel_setjmp_save_sigs.c Modified: haiku/trunk/src/system/kernel/Jamfile haiku/trunk/src/system/kernel/lib/Jamfile Log: Enabled setjmp()/longjmp() support in the kernel. Modified: haiku/trunk/src/system/kernel/Jamfile =================================================================== --- haiku/trunk/src/system/kernel/Jamfile 2007-04-01 13:41:19 UTC (rev 20498) +++ haiku/trunk/src/system/kernel/Jamfile 2007-04-01 17:05:26 UTC (rev 20499) @@ -71,6 +71,7 @@ kernel_os_main.o kernel_os_arch_$(TARGET_ARCH).o kernel_posix.o + kernel_posix_arch_$(TARGET_ARCH).o $(HAIKU_STATIC_LIBSUPC++) Modified: haiku/trunk/src/system/kernel/lib/Jamfile =================================================================== --- haiku/trunk/src/system/kernel/lib/Jamfile 2007-04-01 13:41:19 UTC (rev 20498) +++ haiku/trunk/src/system/kernel/lib/Jamfile 2007-04-01 17:05:26 UTC (rev 20499) @@ -118,3 +118,14 @@ : $(TARGET_KERNEL_PIC_CCFLAGS) ; + +SEARCH_SOURCE += [ FDirName $(posixSources) arch $(TARGET_ARCH) ] ; + +KernelMergeObject kernel_posix_arch_$(TARGET_ARCH).o : + setjmp.S + siglongjmp.S + sigsetjmp.S + kernel_setjmp_save_sigs.c + + : $(TARGET_KERNEL_PIC_CCFLAGS) +; Added: haiku/trunk/src/system/kernel/lib/kernel_setjmp_save_sigs.c =================================================================== --- haiku/trunk/src/system/kernel/lib/kernel_setjmp_save_sigs.c 2007-04-01 13:41:19 UTC (rev 20498) +++ haiku/trunk/src/system/kernel/lib/kernel_setjmp_save_sigs.c 2007-04-01 17:05:26 UTC (rev 20499) @@ -0,0 +1,18 @@ +/* +** Copyright 2004, Axel D?rfler, axeld at pinc-software.de. All rights reserved. +** Distributed under the terms of the Haiku License. +*/ + + +#include + + +/** This function is called by sigsetjmp() only */ + +int __setjmp_save_sigs(jmp_buf buffer, int saveMask); + +int +__setjmp_save_sigs(jmp_buf buffer, int saveMask) +{ + return 0; +} From bonefish at mail.berlios.de Sun Apr 1 19:15:38 2007 From: bonefish at mail.berlios.de (bonefish at BerliOS) Date: Sun, 1 Apr 2007 19:15:38 +0200 Subject: [Haiku-commits] r20500 - in haiku/trunk/src/system/kernel: arch/ppc arch/x86 debug Message-ID: <200704011715.l31HFcLk005439@sheep.berlios.de> Author: bonefish Date: 2007-04-01 19:15:37 +0200 (Sun, 01 Apr 2007) New Revision: 20500 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20500&view=rev Modified: haiku/trunk/src/system/kernel/arch/ppc/arch_cpu.cpp haiku/trunk/src/system/kernel/arch/ppc/arch_debug.cpp haiku/trunk/src/system/kernel/arch/x86/arch_cpu.c haiku/trunk/src/system/kernel/arch/x86/arch_debug.c haiku/trunk/src/system/kernel/debug/debug.c Log: Added a wrapper function for the invocation of debugger commands. It sets a fault handler, so that an invalid memory access while executing the command (address typos always do the trick :-) won't result in another KDL session on top of the current one, which wouldn't even be "cont"able. All pieces of code setting a fault handler do now save and reset the previous one, so that e.g. a user_memcpy() in a debugger command doesn't disturb the mechanism. Modified: haiku/trunk/src/system/kernel/arch/ppc/arch_cpu.cpp =================================================================== --- haiku/trunk/src/system/kernel/arch/ppc/arch_cpu.cpp 2007-04-01 17:05:26 UTC (rev 20499) +++ haiku/trunk/src/system/kernel/arch/ppc/arch_cpu.cpp 2007-04-01 17:15:37 UTC (rev 20500) @@ -151,6 +151,7 @@ { char *tmp = (char *)to; char *s = (char *)from; + addr_t oldFaultHandler = *faultHandler; if (ppc_set_fault_handler(faultHandler, (addr_t)&&error)) goto error; @@ -158,11 +159,11 @@ while (size--) *tmp++ = *s++; - *faultHandler = 0; + *faultHandler = oldFaultHandler; return 0; error: - *faultHandler = 0; + *faultHandler = oldFaultHandler; return B_BAD_ADDRESS; } @@ -181,6 +182,7 @@ arch_cpu_user_strlcpy(char *to, const char *from, size_t size, addr_t *faultHandler) { int from_length = 0; + addr_t oldFaultHandler = *faultHandler; if (ppc_set_fault_handler(faultHandler, (addr_t)&&error)) goto error; @@ -197,11 +199,11 @@ while (*from++ != '\0') from_length++; - *faultHandler = 0; + *faultHandler = oldFaultHandler; return from_length; error: - *faultHandler = 0; + *faultHandler = oldFaultHandler; return B_BAD_ADDRESS; } @@ -210,6 +212,7 @@ arch_cpu_user_memset(void *s, char c, size_t count, addr_t *faultHandler) { char *xs = (char *)s; + addr_t oldFaultHandler = *faultHandler; if (ppc_set_fault_handler(faultHandler, (addr_t)&&error)) goto error; @@ -217,11 +220,11 @@ while (count--) *xs++ = c; - *faultHandler = 0; + *faultHandler = oldFaultHandler; return 0; error: - *faultHandler = 0; + *faultHandler = oldFaultHandler; return B_BAD_ADDRESS; } Modified: haiku/trunk/src/system/kernel/arch/ppc/arch_debug.cpp =================================================================== --- haiku/trunk/src/system/kernel/arch/ppc/arch_debug.cpp 2007-04-01 17:05:26 UTC (rev 20499) +++ haiku/trunk/src/system/kernel/arch/ppc/arch_debug.cpp 2007-04-01 17:15:37 UTC (rev 20500) @@ -65,6 +65,7 @@ get_next_frame(addr_t framePointer, addr_t *next, addr_t *ip) { struct thread *thread = thread_get_current_thread(); + addr_t oldFaultHandler = thread->fault_handler; // set fault handler, so that we can safely access user stacks if (thread) { @@ -76,11 +77,11 @@ *next = (addr_t)((struct stack_frame *)framePointer)->previous; if (thread) - thread->fault_handler = NULL; + thread->fault_handler = oldFaultHandler; return B_OK; error: - thread->fault_handler = NULL; + thread->fault_handler = oldFaultHandler; return B_BAD_ADDRESS; } @@ -287,4 +288,3 @@ return B_NO_ERROR; } - Modified: haiku/trunk/src/system/kernel/arch/x86/arch_cpu.c =================================================================== --- haiku/trunk/src/system/kernel/arch/x86/arch_cpu.c 2007-04-01 17:05:26 UTC (rev 20499) +++ haiku/trunk/src/system/kernel/arch/x86/arch_cpu.c 2007-04-01 17:15:37 UTC (rev 20500) @@ -586,6 +586,7 @@ { char *tmp = (char *)to; char *s = (char *)from; + addr_t oldFaultHandler = *faultHandler; // this check is to trick the gcc4 compiler and have it keep the error label if (to == NULL) @@ -596,11 +597,11 @@ while (size--) *tmp++ = *s++; - *faultHandler = 0; + *faultHandler = oldFaultHandler; return 0; error: - *faultHandler = 0; + *faultHandler = oldFaultHandler; return B_BAD_ADDRESS; } @@ -609,6 +610,7 @@ arch_cpu_user_strlcpy(char *to, const char *from, size_t size, addr_t *faultHandler) { int fromLength = 0; + addr_t oldFaultHandler = *faultHandler; // this check is to trick the gcc4 compiler and have it keep the error label if (to == NULL) @@ -629,11 +631,11 @@ fromLength++; } - *faultHandler = 0; + *faultHandler = oldFaultHandler; return fromLength; error: - *faultHandler = 0; + *faultHandler = oldFaultHandler; return B_BAD_ADDRESS; } @@ -642,6 +644,7 @@ arch_cpu_user_memset(void *s, char c, size_t count, addr_t *faultHandler) { char *xs = (char *)s; + addr_t oldFaultHandler = *faultHandler; // this check is to trick the gcc4 compiler and have it keep the error label if (s == NULL) @@ -652,11 +655,11 @@ while (count--) *xs++ = c; - *faultHandler = 0; + *faultHandler = oldFaultHandler; return 0; error: - *faultHandler = 0; + *faultHandler = oldFaultHandler; return B_BAD_ADDRESS; } Modified: haiku/trunk/src/system/kernel/arch/x86/arch_debug.c =================================================================== --- haiku/trunk/src/system/kernel/arch/x86/arch_debug.c 2007-04-01 17:05:26 UTC (rev 20499) +++ haiku/trunk/src/system/kernel/arch/x86/arch_debug.c 2007-04-01 17:15:37 UTC (rev 20500) @@ -56,6 +56,7 @@ get_next_frame(addr_t ebp, addr_t *_next, addr_t *_eip) { // set fault handler, so that we can safely access user stacks + addr_t oldFaultHandler = thread_get_current_thread()->fault_handler; thread_get_current_thread()->fault_handler = (addr_t)&&error; // Fake goto to trick the compiler not to optimize the code at the label // away. @@ -65,11 +66,11 @@ *_eip = ((struct stack_frame *)ebp)->return_address; *_next = (addr_t)((struct stack_frame *)ebp)->previous; - thread_get_current_thread()->fault_handler = NULL; + thread_get_current_thread()->fault_handler = oldFaultHandler; return B_OK; error: - thread_get_current_thread()->fault_handler = NULL; + thread_get_current_thread()->fault_handler = oldFaultHandler; return B_BAD_ADDRESS; } Modified: haiku/trunk/src/system/kernel/debug/debug.c =================================================================== --- haiku/trunk/src/system/kernel/debug/debug.c 2007-04-01 17:05:26 UTC (rev 20499) +++ haiku/trunk/src/system/kernel/debug/debug.c 2007-04-01 17:15:37 UTC (rev 20500) @@ -16,6 +16,7 @@ #include #include #include +#include #include #include @@ -25,6 +26,7 @@ #include #include +#include #include #include #include @@ -59,6 +61,9 @@ static struct debugger_command *sCommands; +static jmp_buf sInvokeCommandEnv; +static bool sInvokeCommandDirectly = false; + #define SYSLOG_BUFFER_SIZE 65536 #define OUTPUT_BUFFER_SIZE 1024 static char sOutputBuffer[OUTPUT_BUFFER_SIZE]; @@ -316,7 +321,47 @@ return *_argc = index; } +/*! This function is a safe gate through which debugger commands are invoked. + It sets a fault handler before invoking the command, so that an invalid + memory access will not result in another KDL session on top of this one + (and "cont" not to work anymore). We use setjmp() + longjmp() to "unwind" + the stack after catching a fault. + */ +static int +invoke_command(int (*command)(int, char **), int argc, char** argv) +{ + struct thread* thread = thread_get_current_thread(); + addr_t oldFaultHandler = thread->fault_handler; + // Invoking the command directly might be useful when debugging debugger + // commands. + if (sInvokeCommandDirectly) + return command(argc, argv); + + if (setjmp(sInvokeCommandEnv) == 0) { + int result; + thread->fault_handler = (addr_t)&&error; + // Fake goto to trick the compiler not to optimize the code at the label + // away. + if (!thread) + goto error; + + result = command(argc, argv); + thread->fault_handler = oldFaultHandler; + return result; + +error: + longjmp(sInvokeCommandEnv, 1); + // jump into the else branch + } else { + kprintf("\n[*** READ/WRITE FAULT ***]\n"); + } + + thread->fault_handler = oldFaultHandler; + return 0; +} + + static void kernel_debugger_loop(void) { @@ -347,7 +392,7 @@ if (cmd == NULL) kprintf("unknown command, enter \"help\" to get a list of all supported commands\n"); else { - int rc = cmd->func(argc, args); + int rc = invoke_command(cmd->func, argc, args); if (rc == B_KDEBUG_QUIT) break; // okay, exit now. From hugosantos at mail.berlios.de Sun Apr 1 19:35:52 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Sun, 1 Apr 2007 19:35:52 +0200 Subject: [Haiku-commits] r20501 - haiku/trunk/src/add-ons/kernel/network/stack Message-ID: <200704011735.l31HZq9M027163@sheep.berlios.de> Author: hugosantos Date: 2007-04-01 19:35:43 +0200 (Sun, 01 Apr 2007) New Revision: 20501 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20501&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/stack/utility.cpp haiku/trunk/src/add-ons/kernel/network/stack/utility.h Log: UserBuffer: generic userspace supplied buffer and copy management Modified: haiku/trunk/src/add-ons/kernel/network/stack/utility.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/utility.cpp 2007-04-01 17:15:37 UTC (rev 20500) +++ haiku/trunk/src/add-ons/kernel/network/stack/utility.cpp 2007-04-01 17:35:43 UTC (rev 20501) @@ -24,6 +24,30 @@ static bigtime_t sTimerTimeout; +void * +UserBuffer::Copy(void *source, size_t length) +{ + if (fStatus != B_OK) + return NULL; + + if (fAvailable < length) { + fStatus = ENOBUFS; + return NULL; + } + + fStatus = user_memcpy(fBuffer, source, length); + if (fStatus < B_OK) + return NULL; + + void *current = fBuffer; + + fAvailable -= length; + fBuffer += length; + + return current; +} + + uint16 compute_checksum(uint8 *_buffer, size_t length) { Modified: haiku/trunk/src/add-ons/kernel/network/stack/utility.h =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/utility.h 2007-04-01 17:15:37 UTC (rev 20500) +++ haiku/trunk/src/add-ons/kernel/network/stack/utility.h 2007-04-01 17:35:43 UTC (rev 20501) @@ -11,7 +11,43 @@ #include +class UserBuffer { +public: + UserBuffer(void *buffer, size_t size); + void *Copy(void *source, size_t size); + status_t Status() const; + size_t ConsumedAmount() const; + +private: + uint8 *fBuffer; + size_t fBufferSize, fAvailable; + status_t fStatus; +}; + + +inline +UserBuffer::UserBuffer(void *buffer, size_t size) + : fBuffer((uint8 *)buffer), fBufferSize(size), + fAvailable(size), fStatus(B_OK) +{ +} + + +inline status_t +UserBuffer::Status() const +{ + return fStatus; +} + + +inline size_t +UserBuffer::ConsumedAmount() const +{ + return fBufferSize - fAvailable; +} + + // checksums uint16 compute_checksum(uint8 *_buffer, size_t length); uint16 checksum(uint8 *buffer, size_t length); From hugosantos at mail.berlios.de Sun Apr 1 19:36:53 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Sun, 1 Apr 2007 19:36:53 +0200 Subject: [Haiku-commits] r20502 - haiku/trunk/src/add-ons/kernel/network/stack Message-ID: <200704011736.l31HarCR027240@sheep.berlios.de> Author: hugosantos Date: 2007-04-01 19:36:41 +0200 (Sun, 01 Apr 2007) New Revision: 20502 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20502&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/stack/routes.cpp Log: use generic UserBuffer in fill_route_entry Modified: haiku/trunk/src/add-ons/kernel/network/stack/routes.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/routes.cpp 2007-04-01 17:35:43 UTC (rev 20501) +++ haiku/trunk/src/add-ons/kernel/network/stack/routes.cpp 2007-04-01 17:36:41 UTC (rev 20502) @@ -10,6 +10,7 @@ #include "domains.h" #include "routes.h" #include "stack_private.h" +#include "utility.h" #include #include @@ -35,53 +36,6 @@ #endif -class UserRouteBuffer { - public: - UserRouteBuffer(uint8 *buffer, size_t available) - : - fBuffer(buffer), - fAvailable(available), - fStatus(B_OK) - { - } - - sockaddr * - Copy(sockaddr *source) - { - sockaddr *target = (sockaddr *)fBuffer; - - if (fStatus != B_OK - || source == NULL - || (fStatus = _Copy(source)) != B_OK) - return NULL; - - return target; - } - - status_t Status() const { return fStatus; } - - private: - status_t - _Copy(sockaddr *source) - { - if (fAvailable < source->sa_len) - return ENOBUFS; - - if (user_memcpy(fBuffer, source, source->sa_len) < B_OK) - return B_BAD_ADDRESS; - - fAvailable -= source->sa_len; - fBuffer += source->sa_len; - - return B_OK; - } - - uint8 *fBuffer; - size_t fAvailable; - status_t fStatus; -}; - - net_route_private::net_route_private() { destination = mask = gateway = NULL; @@ -481,17 +435,26 @@ } +static sockaddr * +copy_address(UserBuffer &buffer, sockaddr *address) +{ + if (address == NULL) + return NULL; + + return (sockaddr *)buffer.Copy(address, address->sa_len); +} + static status_t fill_route_entry(route_entry *target, void *_buffer, size_t bufferSize, net_route *route) { - UserRouteBuffer buffer(((uint8 *)_buffer) + sizeof(route_entry), + UserBuffer buffer(((uint8 *)_buffer) + sizeof(route_entry), bufferSize - sizeof(route_entry)); - target->destination = buffer.Copy(route->destination); - target->mask = buffer.Copy(route->mask); - target->gateway = buffer.Copy(route->gateway); - target->source = buffer.Copy(route->interface->address); + target->destination = copy_address(buffer, route->destination); + target->mask = copy_address(buffer, route->mask); + target->gateway = copy_address(buffer, route->gateway); + target->source = copy_address(buffer, route->interface->address); target->flags = route->flags; target->mtu = route->mtu; From hugosantos at mail.berlios.de Sun Apr 1 19:49:59 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Sun, 1 Apr 2007 19:49:59 +0200 Subject: [Haiku-commits] r20503 - haiku/trunk/src/add-ons/kernel/network/stack Message-ID: <200704011749.l31Hnx8Q028015@sheep.berlios.de> Author: hugosantos Date: 2007-04-01 19:49:41 +0200 (Sun, 01 Apr 2007) New Revision: 20503 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20503&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/stack/domains.cpp haiku/trunk/src/add-ons/kernel/network/stack/interfaces.cpp Log: use UserBuffer in list_{device,domain}_interfaces Modified: haiku/trunk/src/add-ons/kernel/network/stack/domains.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/domains.cpp 2007-04-01 17:36:41 UTC (rev 20502) +++ haiku/trunk/src/add-ons/kernel/network/stack/domains.cpp 2007-04-01 17:49:41 UTC (rev 20503) @@ -9,6 +9,7 @@ #include "domains.h" #include "interfaces.h" +#include "utility.h" #include @@ -99,12 +100,11 @@ returned. */ status_t -list_domain_interfaces(void *buffer, size_t *_bufferSize) +list_domain_interfaces(void *_buffer, size_t *bufferSize) { BenaphoreLocker locker(sDomainLock); - uint8 *current = (uint8 *)buffer; - const uint8 *bufferEnd = current + (*_bufferSize); + UserBuffer buffer(_buffer, *bufferSize); net_domain_private *domain = NULL; while (true) { @@ -119,10 +119,6 @@ if (interface == NULL) break; - size_t size = IF_NAMESIZE + (interface->address ? interface->address->sa_len : 2); - if ((current + size) > bufferEnd) - return ENOBUFS; - ifreq request; strlcpy(request.ifr_name, interface->name, IF_NAMESIZE); if (interface->address != NULL) @@ -133,14 +129,13 @@ request.ifr_addr.sa_family = AF_UNSPEC; } - if (user_memcpy(current, &request, size) < B_OK) - return B_BAD_ADDRESS; - - current += size; + if (buffer.Copy(&request, IF_NAMESIZE + + request.ifr_addr.sa_len) == NULL) + return buffer.Status(); } } - *_bufferSize = current - (uint8 *)buffer; + *bufferSize = buffer.ConsumedAmount(); return B_OK; } Modified: haiku/trunk/src/add-ons/kernel/network/stack/interfaces.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/interfaces.cpp 2007-04-01 17:36:41 UTC (rev 20502) +++ haiku/trunk/src/add-ons/kernel/network/stack/interfaces.cpp 2007-04-01 17:49:41 UTC (rev 20503) @@ -10,6 +10,7 @@ #include "domains.h" #include "interfaces.h" #include "stack_private.h" +#include "utility.h" #include @@ -258,12 +259,11 @@ returned. */ status_t -list_device_interfaces(void *buffer, size_t *_bufferSize) +list_device_interfaces(void *_buffer, size_t *bufferSize) { BenaphoreLocker locker(sInterfaceLock); - uint8 *current = (uint8 *)buffer; - const uint8 *bufferEnd = current + (*_bufferSize); + UserBuffer buffer(_buffer, *bufferSize); net_device_interface *interface = NULL; while (true) { @@ -276,17 +276,12 @@ strlcpy(request.ifr_name, interface->name, IF_NAMESIZE); get_device_interface_address(interface, &request.ifr_addr); - size_t size = IF_NAMESIZE + request.ifr_addr.sa_len; - if ((current + size) > bufferEnd) - return ENOBUFS; - - if (user_memcpy(current, &request, size) < B_OK) - return B_BAD_ADDRESS; - - current += size; + if (buffer.Copy(&request, IF_NAMESIZE + + request.ifr_addr.sa_len) == NULL) + return buffer.Status(); } - *_bufferSize = current - (uint8 *)buffer;; + *bufferSize = buffer.ConsumedAmount(); return B_OK; } From axeld at pinc-software.de Sun Apr 1 22:09:41 2007 From: axeld at pinc-software.de (Axel =?iso-8859-15?q?D=F6rfler?=) Date: Sun, 01 Apr 2007 22:09:41 +0200 CEST Subject: [Haiku-commits] =?iso-8859-15?q?r20502_-_haiku/trunk/src/add-ons/?= =?iso-8859-15?q?kernel/network/stack?= In-Reply-To: <200704011736.l31HarCR027240@sheep.berlios.de> Message-ID: <33334458278-BeMail@zon> Very nice changes, just some style things: hugosantos at mail.berlios.de wrote: > +} > + > static status_t and: > #include > > +class UserBuffer { > +public: 2 blank lines between the contents :-) (we also usually indent the public/private "labels", but since everyone seems to do it differently, I can't force you adopt any style :-)) Bye, Axel. From hugosantos at mail.berlios.de Sun Apr 1 22:25:15 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Sun, 1 Apr 2007 22:25:15 +0200 Subject: [Haiku-commits] r20504 - haiku/trunk/src/add-ons/kernel/network/stack Message-ID: <200704012025.l31KPFUo005257@sheep.berlios.de> Author: hugosantos Date: 2007-04-01 22:23:16 +0200 (Sun, 01 Apr 2007) New Revision: 20504 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20504&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/stack/net_buffer.cpp Log: some cleanups by introducing get_node_at_offset Modified: haiku/trunk/src/add-ons/kernel/network/stack/net_buffer.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/net_buffer.cpp 2007-04-01 17:49:41 UTC (rev 20503) +++ haiku/trunk/src/add-ons/kernel/network/stack/net_buffer.cpp 2007-04-01 20:23:16 UTC (rev 20504) @@ -528,6 +528,19 @@ } +static inline data_node * +get_node_at_offset(net_buffer_private *buffer, size_t offset) +{ + data_node *node = (data_node *)list_get_first_item(&buffer->buffers); + while (node->offset + node->used < offset) { + node = (data_node *)list_get_next_item(&buffer->buffers, node); + if (node == NULL) + return NULL; + } + + return node; +} + /*! Writes into existing allocated memory. \return B_BAD_VALUE if you write outside of the buffers current bounds. @@ -543,14 +556,10 @@ return B_OK; // find first node to write into + data_node *node = get_node_at_offset(buffer, offset); + if (node == NULL) + return B_BAD_VALUE; - data_node *node = (data_node *)list_get_first_item(&buffer->buffers); - while (node->offset + node->used < offset) { - node = (data_node *)list_get_next_item(&buffer->buffers, node); - if (node == NULL) - return B_BAD_VALUE; - } - offset -= node->offset; while (true) { @@ -584,14 +593,10 @@ return B_OK; // find first node to read from + data_node *node = get_node_at_offset(buffer, offset); + if (node == NULL) + return B_BAD_VALUE; - data_node *node = (data_node *)list_get_first_item(&buffer->buffers); - while (node->offset + node->used < offset) { - node = (data_node *)list_get_next_item(&buffer->buffers, node); - if (node == NULL) - return B_BAD_VALUE; - } - offset -= node->offset; while (true) { @@ -917,14 +922,10 @@ return B_BAD_VALUE; // find data_node to start with from the source buffer - - data_node *node = (data_node *)list_get_first_item(&source->buffers); - while (node->offset + node->used < offset) { - node = (data_node *)list_get_next_item(&source->buffers, node); - if (node == NULL) { - // trim size greater than buffer size - return B_BAD_VALUE; - } + data_node *node = get_node_at_offset(source, offset); + if (node == NULL) { + // trim size greater than buffer size + return B_BAD_VALUE; } while (node != NULL && bytes > 0) { @@ -987,14 +988,10 @@ return B_BAD_VALUE; // find node to access + data_node *node = get_node_at_offset(buffer, offset); + if (node == NULL) + return B_BAD_VALUE; - data_node *node = (data_node *)list_get_first_item(&buffer->buffers); - while (node->offset + node->used < offset) { - node = (data_node *)list_get_next_item(&buffer->buffers, node); - if (node == NULL) - return B_BAD_VALUE; - } - offset -= node->offset; if (size > node->used - offset) @@ -1014,14 +1011,10 @@ return B_BAD_VALUE; // find first node to read from + data_node *node = get_node_at_offset(buffer, offset); + if (node == NULL) + return B_ERROR; - data_node *node = (data_node *)list_get_first_item(&buffer->buffers); - while (node->offset + node->used < offset) { - node = (data_node *)list_get_next_item(&buffer->buffers, node); - if (node == NULL) - return B_ERROR; - } - offset -= node->offset; // Since the maximum buffer size is 65536 bytes, it's impossible From axeld at pinc-software.de Sun Apr 1 23:10:10 2007 From: axeld at pinc-software.de (Axel =?iso-8859-15?q?D=F6rfler?=) Date: Sun, 01 Apr 2007 23:10:10 +0200 CEST Subject: [Haiku-commits] r20483 - haiku/trunk/src/system/kernel/cache In-Reply-To: <20070401164508.754.2@cs.tu-berlin.de> Message-ID: <36963933863-BeMail@zon> Ingo Weinhold wrote: > > Looks okay, but I'm not sure if I find it easier to read :-) > Well, you're cheating -- you wrote the function in the first place. : > -) I know, but that was a few years ago - it's not that I like what I did, I'm just not sure you really improved it :-)) > BTW, although l33t, I don't really think a "... += ... = ... = ..." > construct is really good to read, especially, if it extends a single > line. You're definitely right :-) > > After all, the vecOffset is a special case that only affects the > > first > > iovec; > True enough, but since it's cheap enough to do it in general, I don't > see > the need for special casing it, particularly since that special case > look > completely different than the handling in the loop (code readability- > - ;-). Hehe :-) > > now, you have doubled the number of loops without good reason. > Not completely without good reason. The up-front "vecLeft == 0" check > is > needed to prevent zero-length tempVecs (which aren't fatal, but not > nice > anyway) and increasing i requires a check against count with a > possible > termination of the loop (which the loop head delivers). So the only > thing > really doubled are the two other checks in the loop condition. True enough, but the "vecLeft == 0" check could be completely outside the loop, it doesn't give you any bonus. But anyway - the problem is ugly in itself, there probably isn't the perfect and immediately appealing solution (to both of us) - and since it works as is, I wouldn't mind keeping it that way :-) > > > * Also set *_numBytes in case all fileVecs have been processed. > > > Only > > > relevant in case the request extends beyond the end of file. > > In that case, it would already have dropped out earlier in the > > loop, so > > I don't think this is necessary. > I don't see where. If 200 KB shall be read, but the fileVecs provide > only > 100 KB (ATM that can happen e.g. when the file is heavily fragmented > and > MAX_FILE_IO_VECS fileVecs don't suffice), all fileVecs will be > processed > and the outer loop simply terminates. None of the error conditions in > the > inner loops will have been met. How dare you to solve eventual problems that the calling code doesn't care about? :-)) I only considered the "end-of-file" case, not the "heavily-fragmented- file" case - in fact the code completely neglects it as well; maybe read_chunk_into_cache() and write_chunk_to_cache() should take that into account? When I look at that code with that error condition in mind, I see at least two bugs in each of them... I'll look into that tomorrow, thanks for the hint :-) Bye, Axel. From hugosantos at mail.berlios.de Mon Apr 2 00:05:42 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Mon, 2 Apr 2007 00:05:42 +0200 Subject: [Haiku-commits] r20505 - haiku/trunk/src/servers/net Message-ID: <200704012205.l31M5gXv012671@sheep.berlios.de> Author: hugosantos Date: 2007-04-02 00:05:35 +0200 (Mon, 02 Apr 2007) New Revision: 20505 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20505&view=rev Modified: haiku/trunk/src/servers/net/DHCPClient.cpp Log: DHCP: explicitly request the gateway address and domain name servers to the DHCP server. This fixes an issue some people reported regarding obtaining such information. Modified: haiku/trunk/src/servers/net/DHCPClient.cpp =================================================================== --- haiku/trunk/src/servers/net/DHCPClient.cpp 2007-04-01 20:23:16 UTC (rev 20504) +++ haiku/trunk/src/servers/net/DHCPClient.cpp 2007-04-01 22:05:35 UTC (rev 20505) @@ -1,5 +1,5 @@ /* - * Copyright 2006, Haiku, Inc. All Rights Reserved. + * Copyright 2006-2007, Haiku, Inc. All Rights Reserved. * Distributed under the terms of the MIT License. * * Authors: @@ -76,6 +76,18 @@ DHCP_INFORM }; +enum parameter_type { + PARAMETER_SUBNET_MASK = 1, + PARAMETER_TIME_OFFSET = 2, + PARAMETER_ROUTER = 3, + PARAMETER_NAME_SERVER = 6, + PARAMETER_HOST_NAME = 12, + PARAMETER_DOMAIN_NAME = 15, + PARAMETER_BROADCAST_ADDRESS = 28, + PARAMETER_NETBIOS_NAME_SERVER = 44, + PARAMETER_NETBIOS_SCOPE = 47, +}; + struct dhcp_option_cookie { dhcp_option_cookie() : state(0), file_has_options(false), server_name_has_options(false) {} @@ -118,7 +130,7 @@ uint8* PutOption(uint8* options, message_option option, uint8 data); uint8* PutOption(uint8* options, message_option option, uint16 data); uint8* PutOption(uint8* options, message_option option, uint32 data); - uint8* PutOption(uint8* options, message_option option, uint8* data, uint32 size); + uint8* PutOption(uint8* options, message_option option, const uint8* data, uint32 size); } _PACKED; #define DHCP_FLAG_BROADCAST 0x8000 @@ -127,7 +139,12 @@ const uint32 kMsgLeaseTime = 'lstm'; +static const uint8 kRequiredParameters[] = { + PARAMETER_SUBNET_MASK, PARAMETER_ROUTER, + PARAMETER_NAME_SERVER, PARAMETER_BROADCAST_ADDRESS +}; + dhcp_message::dhcp_message(message_type type) { memset(this, 0, sizeof(*this)); @@ -280,7 +297,7 @@ uint8* -dhcp_message::PutOption(uint8* options, message_option option, uint8* data, uint32 size) +dhcp_message::PutOption(uint8* options, message_option option, const uint8* data, uint32 size) { options[0] = option; options[1] = size; @@ -645,9 +662,11 @@ // In RENEWAL or REBINDING state, we must set the client_address field, and not // use OPTION_REQUEST_IP_ADDRESS for DHCP_REQUEST messages - if (type == DHCP_REQUEST && (state == INIT || state == REQUESTING)) + if (type == DHCP_REQUEST && (state == INIT || state == REQUESTING)) { next = message.PutOption(next, OPTION_REQUEST_IP_ADDRESS, fAssignedAddress); - else + next = message.PutOption(next, OPTION_REQUEST_PARAMETERS, + kRequiredParameters, sizeof(kRequiredParameters)); + } else message.client_address = fAssignedAddress; next = message.PutOption(next, OPTION_END); From hugosantos at mail.berlios.de Mon Apr 2 01:46:29 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Mon, 2 Apr 2007 01:46:29 +0200 Subject: [Haiku-commits] r20506 - haiku/trunk/src/servers/net Message-ID: <200704012346.l31NkTTH030462@sheep.berlios.de> Author: hugosantos Date: 2007-04-02 01:46:24 +0200 (Mon, 02 Apr 2007) New Revision: 20506 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20506&view=rev Modified: haiku/trunk/src/servers/net/DHCPClient.cpp Log: DHCP: since we are only installing routes while handling an OFFER, request gateway in DISCOVER. Fixes an issue where the gateway address is not configured. Modified: haiku/trunk/src/servers/net/DHCPClient.cpp =================================================================== --- haiku/trunk/src/servers/net/DHCPClient.cpp 2007-04-01 22:05:35 UTC (rev 20505) +++ haiku/trunk/src/servers/net/DHCPClient.cpp 2007-04-01 23:46:24 UTC (rev 20506) @@ -126,11 +126,13 @@ message_type Type() const; const uint8* LastOption() const; + uint8* PrepareMessage(uint8 type); uint8* PutOption(uint8* options, message_option option); uint8* PutOption(uint8* options, message_option option, uint8 data); uint8* PutOption(uint8* options, message_option option, uint16 data); uint8* PutOption(uint8* options, message_option option, uint32 data); uint8* PutOption(uint8* options, message_option option, const uint8* data, uint32 size); + uint8* FinishOptions(uint8 *); } _PACKED; #define DHCP_FLAG_BROADCAST 0x8000 @@ -150,10 +152,8 @@ memset(this, 0, sizeof(*this)); options_magic = htonl(OPTION_MAGIC); - uint8* next = options; - next = PutOption(next, OPTION_MESSAGE_TYPE, (uint8)type); - next = PutOption(next, OPTION_MESSAGE_SIZE, (uint16)htons(sizeof(dhcp_message))); - next = PutOption(next, OPTION_END); + uint8* next = PrepareMessage(type); + FinishOptions(next); } @@ -268,6 +268,15 @@ uint8* +dhcp_message::PrepareMessage(uint8 type) +{ + uint8 *next = options; + next = PutOption(next, OPTION_MESSAGE_TYPE, type); + next = PutOption(next, OPTION_MESSAGE_SIZE, (uint16)htons(sizeof(dhcp_message))); + return next; +} + +uint8* dhcp_message::PutOption(uint8* options, message_option option) { options[0] = option; @@ -307,6 +316,13 @@ } +uint8* +dhcp_message::FinishOptions(uint8 *next) +{ + return PutOption(next, OPTION_END); +} + + // #pragma mark - @@ -653,10 +669,7 @@ case DHCP_RELEASE: { // add server identifier option - uint8* next = message.options; - next = message.PutOption(next, OPTION_MESSAGE_TYPE, (uint8)DHCP_REQUEST); - next = message.PutOption(next, OPTION_MESSAGE_SIZE, - (uint16)htons(sizeof(dhcp_message))); + uint8* next = message.PrepareMessage(type); next = message.PutOption(next, OPTION_SERVER_ADDRESS, (uint32)fServer.sin_addr.s_addr); @@ -669,10 +682,19 @@ } else message.client_address = fAssignedAddress; - next = message.PutOption(next, OPTION_END); + message.FinishOptions(next); break; } + case DHCP_DISCOVER: + { + uint8 *next = message.PrepareMessage(type); + next = message.PutOption(next, OPTION_REQUEST_PARAMETERS, + kRequiredParameters, sizeof(kRequiredParameters)); + message.FinishOptions(next); + break; + } + default: // the default options are fine break; From revol at free.fr Mon Apr 2 07:08:46 2007 From: revol at free.fr (=?windows-1252?q?Fran=E7ois?= Revol) Date: Mon, 02 Apr 2007 07:08:46 +0200 CEST Subject: [Haiku-commits] r20493 - haiku/trunk/src/add-ons/kernel/drivers/ports/usb_serial In-Reply-To: <20070401141226.2213.6@stippis.mshome.net> Message-ID: <859223244-BeMail@laptop> > Hi Francois, > > pretty cool to see you work on this! Is the driver working under > Haiku as > well, what is your test environment? I'm testing under Zeta for now, someone needs a working driver there... Haiku still lacks a tty module. Fran?ois. From axeld at mail.berlios.de Mon Apr 2 11:09:08 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Mon, 2 Apr 2007 11:09:08 +0200 Subject: [Haiku-commits] r20507 - in haiku/trunk/src: apps/icon-o-matic apps/icon-o-matic/document apps/icon-o-matic/gui apps/icon-o-matic/import_export apps/icon-o-matic/import_export/flat_icon apps/icon-o-matic/import_export/message apps/icon-o-matic/import_export/svg apps/icon-o-matic/shape/commands apps/icon-o-matic/style apps/icon-o-matic/transformable libs/icon libs/icon/flat_icon libs/icon/shape libs/icon/style libs/icon/transformer Message-ID: <200704020909.l32997ux008596@sheep.berlios.de> Author: axeld Date: 2007-04-02 11:08:57 +0200 (Mon, 02 Apr 2007) New Revision: 20507 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20507&view=rev Modified: haiku/trunk/src/apps/icon-o-matic/CanvasView.h haiku/trunk/src/apps/icon-o-matic/MainWindow.h haiku/trunk/src/apps/icon-o-matic/Util.h haiku/trunk/src/apps/icon-o-matic/document/Document.cpp haiku/trunk/src/apps/icon-o-matic/document/Document.h haiku/trunk/src/apps/icon-o-matic/gui/GradientControl.h haiku/trunk/src/apps/icon-o-matic/gui/IconView.h haiku/trunk/src/apps/icon-o-matic/gui/PathListView.h haiku/trunk/src/apps/icon-o-matic/gui/ShapeListView.h haiku/trunk/src/apps/icon-o-matic/gui/StyleListView.h haiku/trunk/src/apps/icon-o-matic/gui/StyleView.h haiku/trunk/src/apps/icon-o-matic/gui/TransformerListView.h haiku/trunk/src/apps/icon-o-matic/import_export/Exporter.h haiku/trunk/src/apps/icon-o-matic/import_export/Importer.h haiku/trunk/src/apps/icon-o-matic/import_export/flat_icon/FlatIconExporter.h haiku/trunk/src/apps/icon-o-matic/import_export/message/MessageExporter.h haiku/trunk/src/apps/icon-o-matic/import_export/message/MessageImporter.h haiku/trunk/src/apps/icon-o-matic/import_export/svg/DocumentBuilder.h haiku/trunk/src/apps/icon-o-matic/import_export/svg/SVGExporter.h haiku/trunk/src/apps/icon-o-matic/import_export/svg/SVGGradients.h haiku/trunk/src/apps/icon-o-matic/shape/commands/AddPathsCommand.h haiku/trunk/src/apps/icon-o-matic/shape/commands/AddPointCommand.h haiku/trunk/src/apps/icon-o-matic/shape/commands/AddShapesCommand.h haiku/trunk/src/apps/icon-o-matic/shape/commands/AddTransformersCommand.h haiku/trunk/src/apps/icon-o-matic/shape/commands/FreezeTransformationCommand.h haiku/trunk/src/apps/icon-o-matic/shape/commands/MovePathsCommand.h haiku/trunk/src/apps/icon-o-matic/shape/commands/MoveShapesCommand.h haiku/trunk/src/apps/icon-o-matic/shape/commands/MoveTransformersCommand.h haiku/trunk/src/apps/icon-o-matic/shape/commands/NudgePointsCommand.h haiku/trunk/src/apps/icon-o-matic/shape/commands/PathCommand.h haiku/trunk/src/apps/icon-o-matic/shape/commands/RemovePathsCommand.h haiku/trunk/src/apps/icon-o-matic/shape/commands/RemoveShapesCommand.h haiku/trunk/src/apps/icon-o-matic/shape/commands/RemoveTransformersCommand.h haiku/trunk/src/apps/icon-o-matic/shape/commands/TransformPointsCommand.h haiku/trunk/src/apps/icon-o-matic/shape/commands/UnassignPathCommand.h haiku/trunk/src/apps/icon-o-matic/style/AddStylesCommand.h haiku/trunk/src/apps/icon-o-matic/style/AssignStyleCommand.h haiku/trunk/src/apps/icon-o-matic/style/MoveStylesCommand.h haiku/trunk/src/apps/icon-o-matic/style/RemoveStylesCommand.h haiku/trunk/src/apps/icon-o-matic/style/SetColorCommand.h haiku/trunk/src/apps/icon-o-matic/style/SetGradientCommand.h haiku/trunk/src/apps/icon-o-matic/transformable/TransformGradientBox.h haiku/trunk/src/apps/icon-o-matic/transformable/TransformObjectsCommand.h haiku/trunk/src/apps/icon-o-matic/transformable/TransformPointsBox.h haiku/trunk/src/apps/icon-o-matic/transformable/TransformShapesBox.h haiku/trunk/src/libs/icon/Icon.h haiku/trunk/src/libs/icon/IconRenderer.h haiku/trunk/src/libs/icon/IconUtils.cpp haiku/trunk/src/libs/icon/flat_icon/FlatIconFormat.cpp haiku/trunk/src/libs/icon/flat_icon/FlatIconFormat.h haiku/trunk/src/libs/icon/flat_icon/FlatIconImporter.h haiku/trunk/src/libs/icon/flat_icon/LittleEndianBuffer.cpp haiku/trunk/src/libs/icon/flat_icon/LittleEndianBuffer.h haiku/trunk/src/libs/icon/flat_icon/PathCommandQueue.h haiku/trunk/src/libs/icon/shape/PathContainer.h haiku/trunk/src/libs/icon/shape/Shape.h haiku/trunk/src/libs/icon/shape/ShapeContainer.h haiku/trunk/src/libs/icon/shape/VectorPath.h haiku/trunk/src/libs/icon/style/Gradient.h haiku/trunk/src/libs/icon/style/Style.h haiku/trunk/src/libs/icon/style/StyleContainer.h haiku/trunk/src/libs/icon/transformer/AffineTransformer.cpp haiku/trunk/src/libs/icon/transformer/AffineTransformer.h haiku/trunk/src/libs/icon/transformer/ContourTransformer.cpp haiku/trunk/src/libs/icon/transformer/ContourTransformer.h haiku/trunk/src/libs/icon/transformer/PathSource.h haiku/trunk/src/libs/icon/transformer/PerspectiveTransformer.cpp haiku/trunk/src/libs/icon/transformer/PerspectiveTransformer.h haiku/trunk/src/libs/icon/transformer/StrokeTransformer.cpp haiku/trunk/src/libs/icon/transformer/StrokeTransformer.h haiku/trunk/src/libs/icon/transformer/Transformer.cpp haiku/trunk/src/libs/icon/transformer/Transformer.h haiku/trunk/src/libs/icon/transformer/TransformerFactory.cpp haiku/trunk/src/libs/icon/transformer/TransformerFactory.h Log: * Put the remaining libicon.a classes into the BPrivate::Icon namespace. * Minor cleanup (like removing the extra blank line between the copyright and the header guard). Modified: haiku/trunk/src/apps/icon-o-matic/CanvasView.h =================================================================== --- haiku/trunk/src/apps/icon-o-matic/CanvasView.h 2007-04-01 23:46:24 UTC (rev 20506) +++ haiku/trunk/src/apps/icon-o-matic/CanvasView.h 2007-04-02 09:08:57 UTC (rev 20507) @@ -1,21 +1,28 @@ /* - * Copyright 2006, Haiku. + * Copyright 2006-2007, Haiku. * Distributed under the terms of the MIT License. * * Authors: * Stephan A?mus */ - #ifndef CANVAS_VIEW_H #define CANVAS_VIEW_H + #include "Icon.h" #include "Scrollable.h" #include "StateView.h" + class BBitmap; -class IconRenderer; +namespace BPrivate { +namespace Icon { + class IconRenderer; +} +} +using namespace BPrivate::Icon; + enum { SNAPPING_OFF = 0, SNAPPING_64, Modified: haiku/trunk/src/apps/icon-o-matic/MainWindow.h =================================================================== --- haiku/trunk/src/apps/icon-o-matic/MainWindow.h 2007-04-01 23:46:24 UTC (rev 20506) +++ haiku/trunk/src/apps/icon-o-matic/MainWindow.h 2007-04-02 09:08:57 UTC (rev 20507) @@ -19,7 +19,6 @@ class BMenuItem; class CanvasView; class Document; -class Icon; class IconObjectListView; class IconEditorApp; class IconView; @@ -30,6 +29,13 @@ class SwatchGroup; class TransformerListView; +namespace BPrivate { +namespace Icon { + class Icon; +} +} +using namespace BPrivate::Icon; + class MultipleManipulatorState; enum { Modified: haiku/trunk/src/apps/icon-o-matic/Util.h =================================================================== --- haiku/trunk/src/apps/icon-o-matic/Util.h 2007-04-01 23:46:24 UTC (rev 20506) +++ haiku/trunk/src/apps/icon-o-matic/Util.h 2007-04-02 09:08:57 UTC (rev 20507) @@ -1,28 +1,35 @@ /* - * Copyright 2006, Haiku. All rights reserved. + * Copyright 2006-2007, Haiku. All rights reserved. * Distributed under the terms of the MIT License. * * Authors: * Stephan A?mus */ - #ifndef UTIL_H #define UTIL_H + #include + class AddPathsCommand; class AddStylesCommand; -class PathContainer; -class Style; -class StyleContainer; -class VectorPath; +namespace BPrivate { +namespace Icon { + class PathContainer; + class Style; + class StyleContainer; + class VectorPath; +} +} +using namespace BPrivate::Icon; + + void new_style(rgb_color color, StyleContainer* container, Style** style, AddStylesCommand** command); void new_path(PathContainer* container, VectorPath** path, AddPathsCommand** command, VectorPath* other = NULL); - -#endif // UTIL_H +#endif // UTIL_H Modified: haiku/trunk/src/apps/icon-o-matic/document/Document.cpp =================================================================== --- haiku/trunk/src/apps/icon-o-matic/document/Document.cpp 2007-04-01 23:46:24 UTC (rev 20506) +++ haiku/trunk/src/apps/icon-o-matic/document/Document.cpp 2007-04-02 09:08:57 UTC (rev 20507) @@ -1,29 +1,33 @@ /* - * Copyright 2006, Haiku. + * Copyright 2006-2007, Haiku. * Distributed under the terms of the MIT License. * * Authors: * Stephan A?mus */ + #include "Document.h" -#include -#include - -#include - #include "CommandStack.h" #include "DocumentSaver.h" #include "Icon.h" #include "Selection.h" +#include + +#include +#include + + using std::nothrow; +using namespace BPrivate::Icon; + // constructor Document::Document(const char* name) : RWLocker("document rw lock"), - fIcon(new (nothrow) ::Icon()), + fIcon(new (nothrow) BPrivate::Icon::Icon()), fCommandStack(new (nothrow) ::CommandStack()), fSelection(new (nothrow) ::Selection()), @@ -80,7 +84,7 @@ // SetIcon void -Document::SetIcon(::Icon* icon) +Document::SetIcon(BPrivate::Icon::Icon* icon) { if (fIcon == icon) return; Modified: haiku/trunk/src/apps/icon-o-matic/document/Document.h =================================================================== --- haiku/trunk/src/apps/icon-o-matic/document/Document.h 2007-04-01 23:46:24 UTC (rev 20506) +++ haiku/trunk/src/apps/icon-o-matic/document/Document.h 2007-04-02 09:08:57 UTC (rev 20507) @@ -1,24 +1,31 @@ /* - * Copyright 2006, Haiku. + * Copyright 2006-2007, Haiku. * Distributed under the terms of the MIT License. * * Authors: * Stephan A?mus */ - #ifndef DOCUMENT_H #define DOCUMENT_H -#include #include "Observable.h" #include "RWLocker.h" +#include + struct entry_ref; +namespace BPrivate { +namespace Icon { + +class Icon; + +} // namespace Icon +} // namespace BPrivate + class CommandStack; class DocumentSaver; -class Icon; class Selection; class Document : public RWLocker, @@ -44,14 +51,14 @@ inline ::DocumentSaver* ExportSaver() const { return fExportSaver; } - void SetIcon(::Icon* icon); - inline ::Icon* Icon() const + void SetIcon(BPrivate::Icon::Icon* icon); + inline BPrivate::Icon::Icon* Icon() const { return fIcon; } void MakeEmpty(bool includingSavers = true); private: - ::Icon* fIcon; + BPrivate::Icon::Icon* fIcon; ::CommandStack* fCommandStack; ::Selection* fSelection; Modified: haiku/trunk/src/apps/icon-o-matic/gui/GradientControl.h =================================================================== --- haiku/trunk/src/apps/icon-o-matic/gui/GradientControl.h 2007-04-01 23:46:24 UTC (rev 20506) +++ haiku/trunk/src/apps/icon-o-matic/gui/GradientControl.h 2007-04-02 09:08:57 UTC (rev 20507) @@ -1,22 +1,29 @@ /* - * Copyright 2006, Haiku. + * Copyright 2006-2007, Haiku. * Distributed under the terms of the MIT License. * * Authors: * Stephan A?mus */ - #ifndef GRADIENT_CONTROL_H #define GRADIENT_CONTROL_H + #include + #if LIB_LAYOUT -#include +# include #endif +namespace BPrivate { +namespace Icon { + class Gradient; +} // namespace Icon +} // namespace BPrivate + enum { MSG_GRADIENT_CONTROL_FOCUS_CHANGED = 'gcfc', }; @@ -54,8 +61,9 @@ virtual void FrameResized(float width, float height); // GradientControl - void SetGradient(const ::Gradient* gradient); - ::Gradient* Gradient() const + void SetGradient(const BPrivate::Icon::Gradient* + gradient); + BPrivate::Icon::Gradient* Gradient() const { return fGradient; } void SetCurrentStop(const rgb_color& color); @@ -73,7 +81,7 @@ float _OffsetFor(BPoint where) const; void _UpdateCurrentColor() const; - ::Gradient* fGradient; + BPrivate::Icon::Gradient* fGradient; BBitmap* fGradientBitmap; int32 fDraggingStepIndex; int32 fCurrentStepIndex; Modified: haiku/trunk/src/apps/icon-o-matic/gui/IconView.h =================================================================== --- haiku/trunk/src/apps/icon-o-matic/gui/IconView.h 2007-04-01 23:46:24 UTC (rev 20506) +++ haiku/trunk/src/apps/icon-o-matic/gui/IconView.h 2007-04-02 09:08:57 UTC (rev 20507) @@ -1,21 +1,28 @@ /* - * Copyright 2006, Haiku. + * Copyright 2006-2007, Haiku. * Distributed under the terms of the MIT License. * * Authors: * Stephan A?mus */ - #ifndef ICON_VIEW_H #define ICON_VIEW_H -#include #include "Icon.h" +#include + + class BBitmap; -class IconRenderer; +namespace BPrivate { +namespace Icon { + class IconRenderer; +} +} +using namespace BPrivate::Icon; + class IconView : public BView, public IconListener { public: Modified: haiku/trunk/src/apps/icon-o-matic/gui/PathListView.h =================================================================== --- haiku/trunk/src/apps/icon-o-matic/gui/PathListView.h 2007-04-01 23:46:24 UTC (rev 20506) +++ haiku/trunk/src/apps/icon-o-matic/gui/PathListView.h 2007-04-02 09:08:57 UTC (rev 20507) @@ -1,5 +1,5 @@ /* - * Copyright 2006, Haiku. + * Copyright 2006-2007, Haiku. * Distributed under the terms of the MIT License. * * Authors: @@ -8,20 +8,28 @@ #ifndef PATH_LIST_VIEW_H #define PATH_LIST_VIEW_H + #include "ListViews.h" #include "PathContainer.h" class BMenu; class BMenuItem; +namespace BPrivate { +namespace Icon { + class VectorPath; + class Shape; + class ShapeContainer; +} +} + class CommandStack; -class VectorPath; class PathListItem; class Selection; -class Shape; -class ShapeContainer; class ShapePathListener; +using namespace BPrivate::Icon; + class PathListView : public SimpleListView, public PathContainerListener { public: Modified: haiku/trunk/src/apps/icon-o-matic/gui/ShapeListView.h =================================================================== --- haiku/trunk/src/apps/icon-o-matic/gui/ShapeListView.h 2007-04-01 23:46:24 UTC (rev 20506) +++ haiku/trunk/src/apps/icon-o-matic/gui/ShapeListView.h 2007-04-02 09:08:57 UTC (rev 20507) @@ -1,24 +1,31 @@ /* - * Copyright 2006, Haiku. + * Copyright 2006-2007, Haiku. * Distributed under the terms of the MIT License. * * Authors: * Stephan A?mus */ - #ifndef SHAPE_LIST_VIEW_H #define SHAPE_LIST_VIEW_H + #include "ListViews.h" #include "ShapeContainer.h" + class BMenu; class BMenuItem; class CommandStack; -class Shape; class ShapeListItem; class Selection; +namespace BPrivate { +namespace Icon { + class Shape; +} +} +using namespace BPrivate::Icon; + enum { MSG_ADD_SHAPE = 'adsh', }; Modified: haiku/trunk/src/apps/icon-o-matic/gui/StyleListView.h =================================================================== --- haiku/trunk/src/apps/icon-o-matic/gui/StyleListView.h 2007-04-01 23:46:24 UTC (rev 20506) +++ haiku/trunk/src/apps/icon-o-matic/gui/StyleListView.h 2007-04-02 09:08:57 UTC (rev 20507) @@ -1,28 +1,35 @@ /* - * Copyright 2006, Haiku. + * Copyright 2006-2007, Haiku. * Distributed under the terms of the MIT License. * * Authors: * Stephan A?mus */ - #ifndef STYLE_LIST_VIEW_H #define STYLE_LIST_VIEW_H + #include "ListViews.h" #include "StyleContainer.h" + class BMenu; class BMenuItem; class CommandStack; class Selection; -class Shape; -class ShapeContainer; -class ShapeListener; class ShapeStyleListener; -class Style; class StyleListItem; +namespace BPrivate { +namespace Icon { + class Shape; + class ShapeContainer; + class ShapeListener; + class Style; +} +} +using namespace BPrivate::Icon; + class StyleListView : public SimpleListView, public StyleContainerListener { public: Modified: haiku/trunk/src/apps/icon-o-matic/gui/StyleView.h =================================================================== --- haiku/trunk/src/apps/icon-o-matic/gui/StyleView.h 2007-04-01 23:46:24 UTC (rev 20506) +++ haiku/trunk/src/apps/icon-o-matic/gui/StyleView.h 2007-04-02 09:08:57 UTC (rev 20507) @@ -1,26 +1,33 @@ /* - * Copyright 2006, Haiku. + * Copyright 2006-2007, Haiku. * Distributed under the terms of the MIT License. * * Authors: * Stephan A?mus */ - #ifndef STYLE_VIEW_H #define STYLE_VIEW_H -#include #include "Observer.h" +#include + + class BMenu; class BMenuField; class CommandStack; class CurrentColor; -class Gradient; class GradientControl; -class Style; +namespace BPrivate { +namespace Icon { + class Gradient; + class Style; +} +} +using namespace BPrivate::Icon; + // TODO: write lock the document when changing something... enum { Modified: haiku/trunk/src/apps/icon-o-matic/gui/TransformerListView.h =================================================================== --- haiku/trunk/src/apps/icon-o-matic/gui/TransformerListView.h 2007-04-01 23:46:24 UTC (rev 20506) +++ haiku/trunk/src/apps/icon-o-matic/gui/TransformerListView.h 2007-04-02 09:08:57 UTC (rev 20507) @@ -1,23 +1,29 @@ /* - * Copyright 2006, Haiku. + * Copyright 2006-2007, Haiku. * Distributed under the terms of the MIT License. * * Authors: * Stephan A?mus */ - #ifndef TRANSFORMER_LIST_VIEW_H #define TRANSFORMER_LIST_VIEW_H + #include "ListViews.h" #include "Shape.h" + class BMenu; class CommandStack; -class Transformer; class TransformerItem; class Selection; +namespace BPrivate { +namespace Icon { + class Transformer; +} +} + class TransformerListView : public SimpleListView, public ShapeListener { public: Modified: haiku/trunk/src/apps/icon-o-matic/import_export/Exporter.h =================================================================== --- haiku/trunk/src/apps/icon-o-matic/import_export/Exporter.h 2007-04-01 23:46:24 UTC (rev 20506) +++ haiku/trunk/src/apps/icon-o-matic/import_export/Exporter.h 2007-04-02 09:08:57 UTC (rev 20507) @@ -1,21 +1,30 @@ /* - * Copyright 2006, Haiku. All rights reserved. + * Copyright 2006-2007, Haiku. All rights reserved. * Distributed under the terms of the MIT License. * * Authors: * Stephan A?mus */ - #ifndef EXPORTER_H #define EXPORTER_H + #include #include class BPositionIO; class Document; + +namespace BPrivate { +namespace Icon { + class Icon; +} // namespace Icon +} // namespace BPrivate + +using namespace BPrivate::Icon; + class Exporter { public: Exporter(); Modified: haiku/trunk/src/apps/icon-o-matic/import_export/Importer.h =================================================================== --- haiku/trunk/src/apps/icon-o-matic/import_export/Importer.h 2007-04-01 23:46:24 UTC (rev 20506) +++ haiku/trunk/src/apps/icon-o-matic/import_export/Importer.h 2007-04-02 09:08:57 UTC (rev 20507) @@ -5,14 +5,23 @@ * Authors: * Stephan A?mus */ - #ifndef IMPORTER_H #define IMPORTER_H + #include + +namespace BPrivate { +namespace Icon { + class Icon; +} // namespace Icon +} // namespace BPrivate + +using namespace BPrivate::Icon; + class Importer { public: Importer(); Modified: haiku/trunk/src/apps/icon-o-matic/import_export/flat_icon/FlatIconExporter.h =================================================================== --- haiku/trunk/src/apps/icon-o-matic/import_export/flat_icon/FlatIconExporter.h 2007-04-01 23:46:24 UTC (rev 20506) +++ haiku/trunk/src/apps/icon-o-matic/import_export/flat_icon/FlatIconExporter.h 2007-04-02 09:08:57 UTC (rev 20507) @@ -1,27 +1,34 @@ /* - * Copyright 2006, Haiku. All rights reserved. + * Copyright 2006-2007, Haiku. All rights reserved. * Distributed under the terms of the MIT License. * * Authors: * Stephan A?mus */ - #ifndef FLAT_ICON_EXPORTER_H #define FLAT_ICON_EXPORTER_H + #include "Exporter.h" + class BMessage; class BNode; class BPositionIO; + +namespace BPrivate { +namespace Icon { + class Gradient; -class Icon; class LittleEndianBuffer; class PathContainer; class ShapeContainer; class StyleContainer; class VectorPath; +} // namespace Icon +} // namespace BPrivate + #define PRINT_STATISTICS 1 #if PRINT_STATISTICS Modified: haiku/trunk/src/apps/icon-o-matic/import_export/message/MessageExporter.h =================================================================== --- haiku/trunk/src/apps/icon-o-matic/import_export/message/MessageExporter.h 2007-04-01 23:46:24 UTC (rev 20506) +++ haiku/trunk/src/apps/icon-o-matic/import_export/message/MessageExporter.h 2007-04-02 09:08:57 UTC (rev 20507) @@ -1,26 +1,31 @@ /* - * Copyright 2006, Haiku. All rights reserved. + * Copyright 2006-2007, Haiku. All rights reserved. * Distributed under the terms of the MIT License. * * Authors: * Stephan A?mus */ - #ifndef MESSAGE_EXPORTER_H #define MESSAGE_EXPORTER_H + #include "Exporter.h" class BMessage; class BPositionIO; -class Icon; -class PathContainer; -class Shape; -class Style; -class StyleContainer; -class Transformer; -class VectorPath; +namespace BPrivate { +namespace Icon { + class Icon; + class PathContainer; + class Shape; + class Style; + class StyleContainer; + class Transformer; + class VectorPath; +} +} + class MessageExporter : public Exporter { public: MessageExporter(); Modified: haiku/trunk/src/apps/icon-o-matic/import_export/message/MessageImporter.h =================================================================== --- haiku/trunk/src/apps/icon-o-matic/import_export/message/MessageImporter.h 2007-04-01 23:46:24 UTC (rev 20506) +++ haiku/trunk/src/apps/icon-o-matic/import_export/message/MessageImporter.h 2007-04-02 09:08:57 UTC (rev 20507) @@ -1,23 +1,28 @@ /* - * Copyright 2006, Haiku. All rights reserved. + * Copyright 2006-2007, Haiku. All rights reserved. * Distributed under the terms of the MIT License. * * Authors: * Stephan A?mus */ - #ifndef MESSAGE_IMPORTER_H #define MESSAGE_IMPORTER_H + #include "Importer.h" class BMessage; class BPositionIO; -class Icon; -class PathContainer; -class ShapeContainer; -class StyleContainer; +namespace BPrivate { +namespace Icon { + class Icon; + class PathContainer; + class ShapeContainer; + class StyleContainer; +} +} + class MessageImporter : public Importer { public: MessageImporter(); Modified: haiku/trunk/src/apps/icon-o-matic/import_export/svg/DocumentBuilder.h =================================================================== --- haiku/trunk/src/apps/icon-o-matic/import_export/svg/DocumentBuilder.h 2007-04-01 23:46:24 UTC (rev 20506) +++ haiku/trunk/src/apps/icon-o-matic/import_export/svg/DocumentBuilder.h 2007-04-02 09:08:57 UTC (rev 20507) @@ -41,15 +41,15 @@ #include "PathTokenizer.h" -class Icon; class SVGImporter; namespace BPrivate { namespace Icon { + class Icon; class Transformable; } } -using BPrivate::Icon::Transformable; +using namespace BPrivate::Icon; namespace agg { namespace svg { Modified: haiku/trunk/src/apps/icon-o-matic/import_export/svg/SVGExporter.h =================================================================== --- haiku/trunk/src/apps/icon-o-matic/import_export/svg/SVGExporter.h 2007-04-01 23:46:24 UTC (rev 20506) +++ haiku/trunk/src/apps/icon-o-matic/import_export/svg/SVGExporter.h 2007-04-02 09:08:57 UTC (rev 20507) @@ -1,28 +1,28 @@ /* - * Copyright 2006, Haiku. All rights reserved. + * Copyright 2006-2007, Haiku. All rights reserved. * Distributed under the terms of the MIT License. * * Authors: * Stephan A?mus */ - #ifndef SVG_EXPORTER_H #define SVG_EXPORTER_H -#include #include "Exporter.h" -class Gradient; -class Shape; -class Style; +#include + namespace BPrivate { namespace Icon { + class Gradient; + class Shape; + class Style; class Transformable; } } -using BPrivate::Icon::Transformable; +using namespace BPrivate::Icon; class SVGExporter : public Exporter { public: Modified: haiku/trunk/src/apps/icon-o-matic/import_export/svg/SVGGradients.h =================================================================== --- haiku/trunk/src/apps/icon-o-matic/import_export/svg/SVGGradients.h 2007-04-01 23:46:24 UTC (rev 20506) +++ haiku/trunk/src/apps/icon-o-matic/import_export/svg/SVGGradients.h 2007-04-02 09:08:57 UTC (rev 20507) @@ -1,23 +1,26 @@ /* - * Copyright 2006, Haiku. All rights reserved. + * Copyright 2006-2007, Haiku. All rights reserved. * Distributed under the terms of the MIT License. * * Authors: * Stephan A?mus */ - - #ifndef SVG_GRADIENTS_H #define SVG_GRADIENTS_H -#include -#include #include #include -class Gradient; +#include +#include +namespace BPrivate { +namespace Icon { + class Gradient; +} +} + namespace agg { namespace svg { Modified: haiku/trunk/src/apps/icon-o-matic/shape/commands/AddPathsCommand.h =================================================================== --- haiku/trunk/src/apps/icon-o-matic/shape/commands/AddPathsCommand.h 2007-04-01 23:46:24 UTC (rev 20506) +++ haiku/trunk/src/apps/icon-o-matic/shape/commands/AddPathsCommand.h 2007-04-02 09:08:57 UTC (rev 20507) @@ -1,19 +1,25 @@ /* - * Copyright 2006, Haiku. + * Copyright 2006-2007, Haiku. * Distributed under the terms of the MIT License. * * Authors: * Stephan A?mus */ - #ifndef ADD_PATHS_COMMAND_H #define ADD_PATHS_COMMAND_H + #include "Command.h" -class VectorPath; -class PathContainer; +namespace BPrivate { +namespace Icon { + class VectorPath; + class PathContainer; +} +} +using namespace BPrivate::Icon; + class AddPathsCommand : public Command { public: AddPathsCommand( Modified: haiku/trunk/src/apps/icon-o-matic/shape/commands/AddPointCommand.h =================================================================== --- haiku/trunk/src/apps/icon-o-matic/shape/commands/AddPointCommand.h 2007-04-01 23:46:24 UTC (rev 20506) +++ haiku/trunk/src/apps/icon-o-matic/shape/commands/AddPointCommand.h 2007-04-02 09:08:57 UTC (rev 20507) @@ -1,18 +1,19 @@ /* - * Copyright 2006, Haiku. + * Copyright 2006-2007, Haiku. * Distributed under the terms of the MIT License. * * Authors: * Stephan A?mus */ - #ifndef ADD_POINT_COMMAND_H #define ADD_POINT_COMMAND_H -#include #include "PathCommand.h" +#include + + class AddPointCommand : public PathCommand { public: AddPointCommand(VectorPath* path, Modified: haiku/trunk/src/apps/icon-o-matic/shape/commands/AddShapesCommand.h =================================================================== --- haiku/trunk/src/apps/icon-o-matic/shape/commands/AddShapesCommand.h 2007-04-01 23:46:24 UTC (rev 20506) +++ haiku/trunk/src/apps/icon-o-matic/shape/commands/AddShapesCommand.h 2007-04-02 09:08:57 UTC (rev 20507) @@ -1,20 +1,27 @@ /* - * Copyright 2006, Haiku. + * Copyright 2006-2007, Haiku. * Distributed under the terms of the MIT License. * * Authors: * Stephan A?mus */ - #ifndef ADD_SHAPES_COMMAND_H #define ADD_SHAPES_COMMAND_H + #include "Command.h" -class Shape; -class ShapeContainer; + class Selection; +namespace BPrivate { +namespace Icon { + class Shape; + class ShapeContainer; +} +} +using namespace BPrivate::Icon; + class AddShapesCommand : public Command { public: AddShapesCommand( Modified: haiku/trunk/src/apps/icon-o-matic/shape/commands/AddTransformersCommand.h =================================================================== --- haiku/trunk/src/apps/icon-o-matic/shape/commands/AddTransformersCommand.h 2007-04-01 23:46:24 UTC (rev 20506) +++ haiku/trunk/src/apps/icon-o-matic/shape/commands/AddTransformersCommand.h 2007-04-02 09:08:57 UTC (rev 20507) @@ -1,19 +1,25 @@ /* - * Copyright 2006, Haiku. + * Copyright 2006-2007, Haiku. * Distributed under the terms of the MIT License. * * Authors: * Stephan A?mus */ - #ifndef ADD_TRANSFORMERS_COMMAND_H #define ADD_TRANSFORMERS_COMMAND_H + #include "Command.h" -class Shape; -class Transformer; +namespace BPrivate { +namespace Icon { + class Shape; + class Transformer; +} +} +using namespace BPrivate::Icon; + // TODO: make a templated "add items" command? class AddTransformersCommand : public Command { Modified: haiku/trunk/src/apps/icon-o-matic/shape/commands/FreezeTransformationCommand.h =================================================================== --- haiku/trunk/src/apps/icon-o-matic/shape/commands/FreezeTransformationCommand.h 2007-04-01 23:46:24 UTC (rev 20506) +++ haiku/trunk/src/apps/icon-o-matic/shape/commands/FreezeTransformationCommand.h 2007-04-02 09:08:57 UTC (rev 20507) @@ -1,24 +1,24 @@ /* - * Copyright 2006, Haiku. + * Copyright 2006-2007, Haiku. * Distributed under the terms of the MIT License. * * Authors: * Stephan A?mus */ - #ifndef FREEZE_TRANSFORMATION_COMMAND_H #define FREEZE_TRANSFORMATION_COMMAND_H + #include "Command.h" -class Shape; namespace BPrivate { namespace Icon { + class Shape; class Transformable; } } -using BPrivate::Icon::Transformable; [... truncated: 1919 lines follow ...] From axeld at mail.berlios.de Mon Apr 2 11:22:23 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Mon, 2 Apr 2007 11:22:23 +0200 Subject: [Haiku-commits] r20508 - haiku/trunk/src/servers/net Message-ID: <200704020922.l329MNhl010473@sheep.berlios.de> Author: axeld Date: 2007-04-02 11:22:22 +0200 (Mon, 02 Apr 2007) New Revision: 20508 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20508&view=rev Modified: haiku/trunk/src/servers/net/DHCPClient.cpp Log: Removed duplicated information (the PARAMETER_* constants were already expressed in form of the OPTION_* constants). Modified: haiku/trunk/src/servers/net/DHCPClient.cpp =================================================================== --- haiku/trunk/src/servers/net/DHCPClient.cpp 2007-04-02 09:08:57 UTC (rev 20507) +++ haiku/trunk/src/servers/net/DHCPClient.cpp 2007-04-02 09:22:22 UTC (rev 20508) @@ -40,6 +40,7 @@ OPTION_PAD = 0, OPTION_END = 255, OPTION_SUBNET_MASK = 1, + OPTION_TIME_OFFSET = 2, OPTION_ROUTER_ADDRESS = 3, OPTION_DOMAIN_NAME_SERVER = 6, OPTION_HOST_NAME = 12, @@ -48,6 +49,8 @@ OPTION_MTU = 26, OPTION_BROADCAST_ADDRESS = 28, OPTION_NETWORK_TIME_SERVERS = 42, + OPTION_NETBIOS_NAME_SERVER = 44, + OPTION_NETBIOS_SCOPE = 47, // DHCP specific options OPTION_REQUEST_IP_ADDRESS = 50, @@ -76,18 +79,6 @@ DHCP_INFORM }; -enum parameter_type { - PARAMETER_SUBNET_MASK = 1, - PARAMETER_TIME_OFFSET = 2, - PARAMETER_ROUTER = 3, - PARAMETER_NAME_SERVER = 6, - PARAMETER_HOST_NAME = 12, - PARAMETER_DOMAIN_NAME = 15, - PARAMETER_BROADCAST_ADDRESS = 28, - PARAMETER_NETBIOS_NAME_SERVER = 44, - PARAMETER_NETBIOS_SCOPE = 47, -}; - struct dhcp_option_cookie { dhcp_option_cookie() : state(0), file_has_options(false), server_name_has_options(false) {} @@ -142,8 +133,8 @@ const uint32 kMsgLeaseTime = 'lstm'; static const uint8 kRequiredParameters[] = { - PARAMETER_SUBNET_MASK, PARAMETER_ROUTER, - PARAMETER_NAME_SERVER, PARAMETER_BROADCAST_ADDRESS + OPTION_SUBNET_MASK, OPTION_ROUTER_ADDRESS, + OPTION_DOMAIN_NAME_SERVER, OPTION_BROADCAST_ADDRESS }; @@ -276,6 +267,7 @@ return next; } + uint8* dhcp_message::PutOption(uint8* options, message_option option) { From axeld at mail.berlios.de Mon Apr 2 13:13:03 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Mon, 2 Apr 2007 13:13:03 +0200 Subject: [Haiku-commits] r20509 - in haiku/trunk/src: system/kernel/cache tests/system/kernel/cache Message-ID: <200704021113.l32BD3g8009036@sheep.berlios.de> Author: axeld Date: 2007-04-02 13:13:03 +0200 (Mon, 02 Apr 2007) New Revision: 20509 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20509&view=rev Modified: haiku/trunk/src/system/kernel/cache/file_cache.cpp haiku/trunk/src/tests/system/kernel/cache/pages_io_test.cpp Log: * pages_io() now handles it gracefully in case the fileVec array is too small to hold the information for the requested I/O size. * get_file_map() returned B_BUFFER_OVERFLOW already in case the array was exactly as large as needed. * read_chunk_into_cache() and write_chunk_to_cache() will no longer override their local "size" variable. Modified: haiku/trunk/src/system/kernel/cache/file_cache.cpp =================================================================== --- haiku/trunk/src/system/kernel/cache/file_cache.cpp 2007-04-02 09:22:22 UTC (rev 20508) +++ haiku/trunk/src/system/kernel/cache/file_cache.cpp 2007-04-02 11:13:03 UTC (rev 20509) @@ -288,14 +288,14 @@ vecs[index] = fileExtent->disk; index++; + if (size <= fileExtent->disk.length) + break; + if (index >= maxVecs) { *_count = index; return B_BUFFER_OVERFLOW; } - if (size <= fileExtent->disk.length) - break; - size -= fileExtent->disk.length; } @@ -312,8 +312,8 @@ pages_io(file_cache_ref *ref, off_t offset, const iovec *vecs, size_t count, size_t *_numBytes, bool doWrite) { - TRACE(("pages_io: ref = %p, offset = %Ld, size = %lu, vecCount = %lu, %s\n", ref, offset, - *_numBytes, count, doWrite ? "write" : "read")); + TRACE(("pages_io: ref = %p, offset = %Ld, size = %lu, vecCount = %lu, %s\n", + ref, offset, *_numBytes, count, doWrite ? "write" : "read")); // translate the iovecs into direct device accesses file_io_vec fileVecs[MAX_FILE_IO_VECS]; @@ -322,16 +322,17 @@ status_t status = get_file_map(ref, offset, numBytes, fileVecs, &fileVecCount); - if (status < B_OK) { - TRACE(("get_file_map(offset = %Ld, numBytes = %lu) failed\n", offset, - numBytes)); + if (status < B_OK && status != B_BUFFER_OVERFLOW) { + TRACE(("get_file_map(offset = %Ld, numBytes = %lu) failed: %s\n", + offset, numBytes, strerror(status))); return status; } - // TODO: handle array overflow gracefully! + bool bufferOverflow = status == B_BUFFER_OVERFLOW; #ifdef TRACE_FILE_CACHE - dprintf("got %lu file vecs for %Ld:%lu:\n", fileVecCount, offset, numBytes); + dprintf("got %lu file vecs for %Ld:%lu%s:\n", fileVecCount, offset, + numBytes, bufferOverflow ? " (array too small)" : ""); for (size_t i = 0; i < fileVecCount; i++) { dprintf(" [%lu] offset = %Ld, size = %Ld\n", i, fileVecs[i].offset, fileVecs[i].length); @@ -357,8 +358,8 @@ if (size > numBytes) size = numBytes; - status = vfs_read_pages(ref->device, ref->cookie, fileVecs[0].offset, vecs, - count, &size, false); + status = vfs_read_pages(ref->device, ref->cookie, fileVecs[0].offset, + vecs, count, &size, false); if (status < B_OK) return status; @@ -406,75 +407,100 @@ size_t vecOffset = size; size_t bytesLeft = numBytes - size; - for (; fileVecIndex < fileVecCount; fileVecIndex++) { - file_io_vec &fileVec = fileVecs[fileVecIndex]; - off_t fileOffset = fileVec.offset; - off_t fileLeft = fileVec.length; + while (true) { + for (; fileVecIndex < fileVecCount; fileVecIndex++) { + file_io_vec &fileVec = fileVecs[fileVecIndex]; + off_t fileOffset = fileVec.offset; + off_t fileLeft = min_c(fileVec.length, bytesLeft); - fileLeft = min_c(fileVec.length, bytesLeft); + TRACE(("FILE VEC [%lu] length %Ld\n", fileVecIndex, fileLeft)); - TRACE(("FILE VEC [%lu] length %Ld\n", fileVecIndex, fileLeft)); + // process the complete fileVec + while (fileLeft > 0) { + iovec tempVecs[MAX_TEMP_IO_VECS]; + uint32 tempCount = 0; - // process the complete fileVec - while (fileLeft > 0) { - iovec tempVecs[MAX_TEMP_IO_VECS]; - uint32 tempCount = 0; + // size tracks how much of what is left of the current fileVec + // (fileLeft) has been assigned to tempVecs + size = 0; - // size tracks how much of what is left of the current fileVec - // (fileLeft) has been assigned to tempVecs - size = 0; + // assign what is left of the current fileVec to the tempVecs + for (size = 0; size < fileLeft && i < count + && tempCount < MAX_TEMP_IO_VECS;) { + // try to satisfy one iovec per iteration (or as much as + // possible) - // assign what is left of the current fileVec to the tempVecs - while (size < fileLeft && i < count - && tempCount < MAX_TEMP_IO_VECS) { - // try to satisfy one iovec per iteration (or as much as - // possible) - TRACE(("fill vec %ld, offset = %lu, size = %lu\n", - i, vecOffset, size)); + // bytes left of the current iovec + size_t vecLeft = vecs[i].iov_len - vecOffset; + if (vecLeft == 0) { + vecOffset = 0; + i++; + continue; + } - // bytes left of the current iovec - size_t vecLeft = vecs[i].iov_len - vecOffset; - if (vecLeft == 0) { - i++; - vecOffset = 0; - continue; + TRACE(("fill vec %ld, offset = %lu, size = %lu\n", + i, vecOffset, size)); + + // actually available bytes + size_t tempVecSize = min_c(vecLeft, fileLeft - size); + + tempVecs[tempCount].iov_base + = (void *)((addr_t)vecs[i].iov_base + vecOffset); + tempVecs[tempCount].iov_len = tempVecSize; + tempCount++; + + size += tempVecSize; + vecOffset += tempVecSize; } - // actually available bytes - size_t tempVecSize = min_c(vecLeft, fileLeft - size); + size_t bytes = size; + if (doWrite) { + status = vfs_write_pages(ref->device, ref->cookie, + fileOffset, tempVecs, tempCount, &bytes, false); + } else { + status = vfs_read_pages(ref->device, ref->cookie, + fileOffset, tempVecs, tempCount, &bytes, false); + } + if (status < B_OK) + return status; - tempVecs[tempCount].iov_base - = (void *)((addr_t)vecs[i].iov_base + vecOffset); - tempVecs[tempCount].iov_len = tempVecSize; - tempCount++; + totalSize += bytes; + bytesLeft -= size; + fileOffset += size; + fileLeft -= size; + //dprintf("-> file left = %Lu\n", fileLeft); - size += tempVecSize; - vecOffset += tempVecSize; + if (size != bytes || i >= count) { + // there are no more bytes or iovecs, let's bail out + *_numBytes = totalSize; + return B_OK; + } } + } - size_t bytes = size; - if (doWrite) { - status = vfs_write_pages(ref->device, ref->cookie, fileOffset, - tempVecs, tempCount, &bytes, false); - } else { - status = vfs_read_pages(ref->device, ref->cookie, fileOffset, - tempVecs, tempCount, &bytes, false); + if (bufferOverflow) { + status = get_file_map(ref, offset + totalSize, bytesLeft, fileVecs, + &fileVecCount); + if (status < B_OK && status != B_BUFFER_OVERFLOW) { + TRACE(("get_file_map(offset = %Ld, numBytes = %lu) failed: %s\n", + offset, numBytes, strerror(status))); + return status; } - if (status < B_OK) - return status; - totalSize += bytes; - bytesLeft -= size; - fileOffset += size; - fileLeft -= size; - //dprintf("-> file left = %Lu\n", fileLeft); + bufferOverflow = status == B_BUFFER_OVERFLOW; + fileVecIndex = 0; - if (size != bytes || i >= count) { - // there are no more bytes or iovecs, let's bail out - *_numBytes = totalSize; - return B_OK; +#ifdef TRACE_FILE_CACHE + dprintf("got %lu file vecs for %Ld:%lu%s:\n", fileVecCount, + offset + totalSize, numBytes, + bufferOverflow ? " (array too small)" : ""); + for (size_t i = 0; i < fileVecCount; i++) { + dprintf(" [%lu] offset = %Ld, size = %Ld\n", + i, fileVecs[i].offset, fileVecs[i].length); } - } +#endif + } else + break; } *_numBytes = totalSize; @@ -488,7 +514,7 @@ sure that it matches that criterion. */ static inline status_t -read_chunk_into_cache(file_cache_ref *ref, off_t offset, size_t size, +read_chunk_into_cache(file_cache_ref *ref, off_t offset, size_t numBytes, int32 pageOffset, addr_t buffer, size_t bufferSize) { TRACE(("read_chunk(offset = %Ld, size = %lu, pageOffset = %ld, buffer = %#lx, bufferSize = %lu\n", @@ -503,7 +529,7 @@ int32 pageIndex = 0; // allocate pages for the cache and mark them busy - for (size_t pos = 0; pos < size; pos += B_PAGE_SIZE) { + for (size_t pos = 0; pos < numBytes; pos += B_PAGE_SIZE) { vm_page *page = pages[pageIndex++] = vm_page_allocate_page(PAGE_STATE_FREE); if (page == NULL) panic("no more pages!"); @@ -524,7 +550,7 @@ mutex_unlock(&cache->lock); // read file into reserved pages - status_t status = pages_io(ref, offset, vecs, vecCount, &size, false); + status_t status = pages_io(ref, offset, vecs, vecCount, &numBytes, false); if (status < B_OK) { // reading failed, free allocated pages @@ -635,7 +661,7 @@ /** Like read_chunk_into_cache() but writes data into the cache */ static inline status_t -write_chunk_to_cache(file_cache_ref *ref, off_t offset, size_t size, +write_chunk_to_cache(file_cache_ref *ref, off_t offset, size_t numBytes, int32 pageOffset, addr_t buffer, size_t bufferSize) { iovec vecs[MAX_IO_VECS]; @@ -648,7 +674,7 @@ bool writeThrough = false; // allocate pages for the cache and mark them busy - for (size_t pos = 0; pos < size; pos += B_PAGE_SIZE) { + for (size_t pos = 0; pos < numBytes; pos += B_PAGE_SIZE) { // ToDo: if space is becoming tight, and this cache is already grown // big - shouldn't we better steal the pages directly in that case? // (a working set like approach for the file cache) @@ -696,7 +722,7 @@ iovec readVec = { (void *)last, B_PAGE_SIZE }; size_t bytesRead = B_PAGE_SIZE; - status = pages_io(ref, offset + size - B_PAGE_SIZE, &readVec, 1, + status = pages_io(ref, offset + numBytes - B_PAGE_SIZE, &readVec, 1, &bytesRead, false); // ToDo: handle errors for real! if (status < B_OK) @@ -721,7 +747,7 @@ if (writeThrough) { // write cached pages back to the file if we were asked to do that - status_t status = pages_io(ref, offset, vecs, vecCount, &size, true); + status_t status = pages_io(ref, offset, vecs, vecCount, &numBytes, true); if (status < B_OK) { // ToDo: remove allocated pages, ...? panic("file_cache: remove allocated pages! write pages failed: %s\n", Modified: haiku/trunk/src/tests/system/kernel/cache/pages_io_test.cpp =================================================================== --- haiku/trunk/src/tests/system/kernel/cache/pages_io_test.cpp 2007-04-02 09:22:22 UTC (rev 20508) +++ haiku/trunk/src/tests/system/kernel/cache/pages_io_test.cpp 2007-04-02 11:13:03 UTC (rev 20509) @@ -10,6 +10,7 @@ #include #include #include +#include #include #define TRACE_FILE_CACHE @@ -22,7 +23,7 @@ // maximum number of iovecs per request #define MAX_IO_VECS 64 // 256 kB -#define MAX_FILE_IO_VECS 32 +#define MAX_FILE_IO_VECS 4 #define MAX_TEMP_IO_VECS 8 #define CACHED_FILE_EXTENTS 2 @@ -61,7 +62,9 @@ }; -file_io_vec gFileVecs[MAX_FILE_IO_VECS]; +const uint32 kMaxFileVecs = 1024; + +file_io_vec gFileVecs[kMaxFileVecs]; size_t gFileVecCount; off_t gFileSize; @@ -202,7 +205,7 @@ va_list args; va_start(args, length); - while (gFileVecCount < MAX_FILE_IO_VECS) { + while (gFileVecCount < kMaxFileVecs) { off_t offset = va_arg(args, int32); if (offset < 0) break; @@ -252,6 +255,9 @@ size_t max = *_count; uint32 index = 0; + printf("vfs_get_file_map(offset = %Ld, size = %lu, count = %lu)\n", + offset, size, *_count); + while (true) { status_t status = find_map_base(offset, diskOffset, diskLength, fileOffset); //status_t status = inode->FindBlockRun(offset, run, fileOffset); @@ -415,14 +421,14 @@ vecs[index] = fileExtent->disk; index++; + if (size <= fileExtent->disk.length) + break; + if (index >= maxVecs) { *_count = index; return B_BUFFER_OVERFLOW; } - if (size <= fileExtent->disk.length) - break; - size -= fileExtent->disk.length; } @@ -449,16 +455,17 @@ status_t status = get_file_map(ref, offset, numBytes, fileVecs, &fileVecCount); - if (status < B_OK) { - TRACE(("get_file_map(offset = %Ld, numBytes = %lu) failed\n", offset, - numBytes)); + if (status < B_OK && status != B_BUFFER_OVERFLOW) { + TRACE(("get_file_map(offset = %Ld, numBytes = %lu) failed: %s\n", offset, + numBytes, strerror(status))); return status; } - // TODO: handle array overflow gracefully! + bool bufferOverflow = status == B_BUFFER_OVERFLOW; #ifdef TRACE_FILE_CACHE - dprintf("got %lu file vecs for %Ld:%lu:\n", fileVecCount, offset, numBytes); + dprintf("got %lu file vecs for %Ld:%lu%s:\n", fileVecCount, offset, numBytes, + bufferOverflow ? " (array too small)" : ""); for (size_t i = 0; i < fileVecCount; i++) { dprintf(" [%lu] offset = %Ld, size = %Ld\n", i, fileVecs[i].offset, fileVecs[i].length); @@ -533,75 +540,100 @@ size_t vecOffset = size; size_t bytesLeft = numBytes - size; - for (; fileVecIndex < fileVecCount; fileVecIndex++) { - file_io_vec &fileVec = fileVecs[fileVecIndex]; - off_t fileOffset = fileVec.offset; - off_t fileLeft = fileVec.length; + while (true) { + for (; fileVecIndex < fileVecCount; fileVecIndex++) { + file_io_vec &fileVec = fileVecs[fileVecIndex]; + off_t fileOffset = fileVec.offset; + off_t fileLeft = min_c(fileVec.length, bytesLeft); - fileLeft = min_c(fileVec.length, bytesLeft); + TRACE(("FILE VEC [%lu] length %Ld\n", fileVecIndex, fileLeft)); - TRACE(("FILE VEC [%lu] length %Ld\n", fileVecIndex, fileLeft)); + // process the complete fileVec + while (fileLeft > 0) { + iovec tempVecs[MAX_TEMP_IO_VECS]; + uint32 tempCount = 0; - // process the complete fileVec - while (fileLeft > 0) { - iovec tempVecs[MAX_TEMP_IO_VECS]; - uint32 tempCount = 0; + // size tracks how much of what is left of the current fileVec + // (fileLeft) has been assigned to tempVecs + size = 0; - // size tracks how much of what is left of the current fileVec - // (fileLeft) has been assigned to tempVecs - size = 0; + // assign what is left of the current fileVec to the tempVecs + for (size = 0; size < fileLeft && i < count + && tempCount < MAX_TEMP_IO_VECS;) { + // try to satisfy one iovec per iteration (or as much as + // possible) - // assign what is left of the current fileVec to the tempVecs - for (size = 0; size < fileLeft && i < count - && tempCount < MAX_TEMP_IO_VECS;) { - // try to satisfy one iovec per iteration (or as much as - // possible) - TRACE(("fill vec %ld, offset = %lu, size = %lu\n", - i, vecOffset, size)); + // bytes left of the current iovec + size_t vecLeft = vecs[i].iov_len - vecOffset; + if (vecLeft == 0) { + vecOffset = 0; + i++; + continue; + } - // bytes left of the current iovec - size_t vecLeft = vecs[i].iov_len - vecOffset; - if (vecLeft == 0) { - vecOffset = 0; - i++; - continue; + TRACE(("fill vec %ld, offset = %lu, size = %lu\n", + i, vecOffset, size)); + + // actually available bytes + size_t tempVecSize = min_c(vecLeft, fileLeft - size); + + tempVecs[tempCount].iov_base + = (void *)((addr_t)vecs[i].iov_base + vecOffset); + tempVecs[tempCount].iov_len = tempVecSize; + tempCount++; + + size += tempVecSize; + vecOffset += tempVecSize; } - // actually available bytes - size_t tempVecSize = min_c(vecLeft, fileLeft - size); + size_t bytes = size; + if (doWrite) { + status = vfs_write_pages(ref->device, ref->cookie, + fileOffset, tempVecs, tempCount, &bytes, false); + } else { + status = vfs_read_pages(ref->device, ref->cookie, + fileOffset, tempVecs, tempCount, &bytes, false); + } + if (status < B_OK) + return status; - tempVecs[tempCount].iov_base - = (void *)((addr_t)vecs[i].iov_base + vecOffset); - tempVecs[tempCount].iov_len = tempVecSize; - tempCount++; + totalSize += bytes; + bytesLeft -= size; + fileOffset += size; + fileLeft -= size; + //dprintf("-> file left = %Lu\n", fileLeft); - size += tempVecSize; - vecOffset += tempVecSize; + if (size != bytes || i >= count) { + // there are no more bytes or iovecs, let's bail out + *_numBytes = totalSize; + return B_OK; + } } + } - size_t bytes = size; - if (doWrite) { - status = vfs_write_pages(ref->device, ref->cookie, fileOffset, - tempVecs, tempCount, &bytes, false); - } else { - status = vfs_read_pages(ref->device, ref->cookie, fileOffset, - tempVecs, tempCount, &bytes, false); + if (bufferOverflow) { + status = get_file_map(ref, offset + totalSize, bytesLeft, fileVecs, + &fileVecCount); + if (status < B_OK && status != B_BUFFER_OVERFLOW) { + TRACE(("get_file_map(offset = %Ld, numBytes = %lu) failed: %s\n", + offset, numBytes, strerror(status))); + return status; } - if (status < B_OK) - return status; - totalSize += bytes; - bytesLeft -= size; - fileOffset += size; - fileLeft -= size; - //dprintf("-> file left = %Lu\n", fileLeft); + bufferOverflow = status == B_BUFFER_OVERFLOW; + fileVecIndex = 0; - if (size != bytes || i >= count) { - // there are no more bytes or iovecs, let's bail out - *_numBytes = totalSize; - return B_OK; +#ifdef TRACE_FILE_CACHE + dprintf("got %lu file vecs for %Ld:%lu%s:\n", fileVecCount, + offset + totalSize, numBytes, + bufferOverflow ? " (array too small)" : ""); + for (size_t i = 0; i < fileVecCount; i++) { + dprintf(" [%lu] offset = %Ld, size = %Ld\n", + i, fileVecs[i].offset, fileVecs[i].length); } - } +#endif + } else + break; } *_numBytes = totalSize; @@ -621,10 +653,14 @@ size_t numBytes = 10000; off_t offset = 4999; - set_vecs(vecs, &count, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 4096, 8192, 16384, 4096, 4096, -1); - set_file_map(0, 2000, 5000, 3000, 10000, 800, 11000, 20, 12000, 30, 13000, 70, 14000, 100, 15000, 30000, -1); + set_vecs(vecs, &count, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, + 16, 4096, 8192, 16384, 4096, 4096, -1); + set_file_map(0, 2000, 5000, 3000, 10000, 800, 11000, 20, 12000, 30, + 13000, 70, 14000, 100, 15000, 900, 20000, 30000, -1); - pages_io(&ref, offset, vecs, count, &numBytes, false); + status_t status = pages_io(&ref, offset, vecs, count, &numBytes, false); + if (status < B_OK) + fprintf(stderr, "pages_io() returned: %s\n", strerror(status)); return 0; } From nielx at mail.berlios.de Mon Apr 2 13:25:44 2007 From: nielx at mail.berlios.de (nielx at BerliOS) Date: Mon, 2 Apr 2007 13:25:44 +0200 Subject: [Haiku-commits] r20510 - haiku/trunk/src/kits/support Message-ID: <200704021125.l32BPiax000176@sheep.berlios.de> Author: nielx Date: 2007-04-02 13:25:43 +0200 (Mon, 02 Apr 2007) New Revision: 20510 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20510&view=rev Modified: haiku/trunk/src/kits/support/BufferIO.cpp haiku/trunk/src/kits/support/DataIO.cpp Log: Strip API documentation from these files: they are in separate dox files now. Modified: haiku/trunk/src/kits/support/BufferIO.cpp =================================================================== --- haiku/trunk/src/kits/support/BufferIO.cpp 2007-04-02 11:13:03 UTC (rev 20509) +++ haiku/trunk/src/kits/support/BufferIO.cpp 2007-04-02 11:25:43 UTC (rev 20510) @@ -6,9 +6,7 @@ * Stefano Ceccherini (burton666 at libero.it) */ -//! A buffered adapter for BPositionIO objects. - #include #include @@ -16,21 +14,6 @@ #include -/*! \class BBufferIO - \brief A buffered adapter for BPositionIO objects. - \author #include From nielx at mail.berlios.de Mon Apr 2 13:39:12 2007 From: nielx at mail.berlios.de (nielx at BerliOS) Date: Mon, 2 Apr 2007 13:39:12 +0200 Subject: [Haiku-commits] r20511 - in haiku/trunk/docs/user: . support Message-ID: <200704021139.l32BdC3t000931@sheep.berlios.de> Author: nielx Date: 2007-04-02 13:39:10 +0200 (Mon, 02 Apr 2007) New Revision: 20511 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20511&view=rev Added: haiku/trunk/docs/user/support/Flattenable.dox Modified: haiku/trunk/docs/user/book.dox haiku/trunk/docs/user/support/BufferIO.dox haiku/trunk/docs/user/support/DataIO.dox haiku/trunk/docs/user/support/Locker.dox haiku/trunk/docs/user/support/SupportDefs.dox Log: * book.dox Reformat according to the guidelines * BufferIO.dox Reformat according to the guidelines * DataIO.dox Reformat according to the guidelines * Flattenable.dox New documentation. * Locker.dox Finished documentation. * SupportDefs.dox Reformat according to the guidelines Modified: haiku/trunk/docs/user/book.dox =================================================================== --- haiku/trunk/docs/user/book.dox 2007-04-02 11:25:43 UTC (rev 20510) +++ haiku/trunk/docs/user/book.dox 2007-04-02 11:39:10 UTC (rev 20511) @@ -1,31 +1,32 @@ /*! -\mainpage The Haiku Book + \mainpage The Haiku Book -\section kits Kits and Servers + \section kits Kits and Servers -- \ref midi1 -- \ref midi2 | \link midi2_intro \em Introduction \endlink -- \ref support | \link support_intro \em Introduction \endlink + - \ref midi1 + - \ref midi2 | \link midi2_intro \em Introduction \endlink + - \ref support | \link support_intro \em Introduction \endlink -\section notes General Notes and Information -- \ref compatibility + \section notes General Notes and Information + - \ref compatibility + - \ref apidoc */ -// Define main kits +///// Define main kits ///// /*! -\defgroup midi2 MIDI 2 Kit -\brief API for producing and consuming MIDI events. -\defgroup libmidi2 (libmidi2.so) -\defgroup support Support Kit -\brief Collection of utility classes that are used throughout the API. -\defgroup libbe (libbe.so) -\defgroup libroot (libroot.so) + \defgroup midi2 MIDI 2 Kit + \brief API for producing and consuming MIDI events. + \defgroup libmidi2 (libmidi2.so) + \defgroup support Support Kit + \brief Collection of utility classes that are used throughout the API. + \defgroup libbe (libbe.so) + \defgroup libroot (libroot.so) */ -// Subgroups +///// Subgroups ///// /*! -\defgroup support_globals Global functions in the support kit -\ingroup support + \defgroup support_globals Global functions in the support kit + \ingroup support */ \ No newline at end of file Modified: haiku/trunk/docs/user/support/BufferIO.dox =================================================================== --- haiku/trunk/docs/user/support/BufferIO.dox 2007-04-02 11:25:43 UTC (rev 20510) +++ haiku/trunk/docs/user/support/BufferIO.dox 2007-04-02 11:39:10 UTC (rev 20511) @@ -1,3 +1,15 @@ +/* + * Copyright 2007, Haiku, Inc. All Rights Reserved. + * Distributed under the terms of the MIT License. + * + * Documentation by: + * Niels Sascha Reedijk + * Stefano Ceccherini (burton666 at libero.it) + * Corresponds to: + * /trunk/headers/os/support/BufferIO.h rev 19972 + * /trunk/src/kits/support/BufferIO.cpp rev 20510 + */ + /*! \file BufferIO.h \brief Provides the BBufferIO class. @@ -38,126 +50,135 @@ */ /*! -\fn BBufferIO::BBufferIO(BPositionIO *stream, size_t bufferSize, bool ownsStream) -\brief Initialize a BBufferIO object. - -The constructor will create a buffer of the given size -and associate the object with the given BPositionIO stream. + \fn BBufferIO::BBufferIO(BPositionIO *stream, size_t bufferSize, bool ownsStream) + \brief Initialize a BBufferIO object. + + The constructor will create a buffer of the given size + and associate the object with the given BPositionIO stream. -\param stream A pointer to a BPositionIO object. -\param bufferSize The size of the buffer that the object will allocate and use. -\param ownsStream Specifies if the object will delete the stream on destruction. + \param stream A pointer to a BPositionIO object. + \param bufferSize The size of the buffer that the object will allocate and + use. + \param ownsStream Specifies if the object will delete the stream on + destruction. */ /*! -\fn BBufferIO::~BBufferIO() -\brief Free the resources allocated by the object + \fn BBufferIO::~BBufferIO() + \brief Free the resources allocated by the object -Flush pending changes to the stream and free the allocated memory. -If the \c owns_stream property is \c true, the destructor also -deletes the stream associated with the BBufferIO object. + Flush pending changes to the stream and free the allocated memory. + If the \c owns_stream property is \c true, the destructor also + deletes the stream associated with the BBufferIO object. */ /*! -\fn ssize_t BBufferIO::ReadAt(off_t pos, void *buffer, size_t size) -\brief Read the specified amount of bytes at the given position. -\param pos The offset into the stream where to read. -\param buffer A pointer to a buffer where to copy the read data. -\param size The amount of bytes to read. -\return The amount of bytes actually read, or an error code. -\retval B_NO_INIT The object is not associated with a valid BPositionIO stream. -\retval B_BAD_VALUE The \c buffer parameter is not valid. + \fn ssize_t BBufferIO::ReadAt(off_t pos, void *buffer, size_t size) + \brief Read the specified amount of bytes at the given position. + \param pos The offset into the stream where to read. + \param buffer A pointer to a buffer where to copy the read data. + \param size The amount of bytes to read. + \return The amount of bytes actually read, or an error code. + \retval B_NO_INIT The object is not associated with a valid BPositionIO + stream. + \retval B_BAD_VALUE The \c buffer parameter is not valid. */ /*! -\fn ssize_t BBufferIO::WriteAt(off_t pos, const void *buffer, size_t size) -\brief Write the specified amount of bytes at the given position. -\param pos The offset into the stream where to write. -\param buffer A pointer to a buffer which contains the data to write. -\param size The amount of bytes to write. -\return The amount of bytes actually written, or an error code. -\retval B_NO_INIT The object is not associated with a valid BPositionIO stream. -\retval B_BAD_VALUE The \c buffer parameter is not valid. + \fn ssize_t BBufferIO::WriteAt(off_t pos, const void *buffer, size_t size) + \brief Write the specified amount of bytes at the given position. + \param pos The offset into the stream where to write. + \param buffer A pointer to a buffer which contains the data to write. + \param size The amount of bytes to write. + \return The amount of bytes actually written, or an error code. + \retval B_NO_INIT The object is not associated with a valid BPositionIO + stream. + \retval B_BAD_VALUE The \c buffer parameter is not valid. */ /*! -\fn off_t BBufferIO::Seek(off_t position, uint32 seekMode) -\brief Set the position in the stream. - - Set the position in the stream where the Read() and Write() functions - (inherited from BPositionIO) begin reading and writing. - How the position argument is understood depends on the seek_mode flag. - - \param position The position where you want to seek. - \param seekMode Can have three values: - - \c SEEK_SET. The position passed is an offset from the beginning of the stream; - in other words, the current position is set to position. - For this mode, position should be a positive value. - - \c SEEK_CUR. The position argument is an offset from the current position; - the value of the argument is added to the current position. - - \c SEEK_END. The position argument is an offset from the end of the stream. - In this mode the position argument should be negative (or zero). + \fn off_t BBufferIO::Seek(off_t position, uint32 seekMode) + \brief Set the position in the stream. + + Set the position in the stream where the Read() and Write() functions + (inherited from BPositionIO) begin reading and writing. + How the position argument is understood depends on the seek_mode flag. + + \param position The position where you want to seek. + \param seekMode Can have three values: + - \c SEEK_SET. The position passed is an offset from the beginning of the + stream; in other words, the current position is set to position. + For this mode, position should be a positive value. + - \c SEEK_CUR. The position argument is an offset from the current position; + the value of the argument is added to the current position. + - \c SEEK_END. The position argument is an offset from the end of the + stream. In this mode the position argument should be negative (or zero). - \return The current position as an offset in bytes - from the beginning of the stream. - - \retval B_NO_INIT The object is not associated with a valid BPositionIO stream. + \return The current position as an offset in bytes from the beginning of + the stream. + + \retval B_NO_INIT The object is not associated with a valid BPositionIO + stream. */ /*! -\fn off_t BBufferIO::Position() const -\brief Return the current position in the stream. -\return The current position as an offset in bytes - from the beginning of the stream. -\retval B_NO_INIT The object is not associated with a valid BPositionIO stream. + \fn off_t BBufferIO::Position() const + \brief Return the current position in the stream. + \return The current position as an offset in bytes + from the beginning of the stream. + \retval B_NO_INIT The object is not associated with a valid BPositionIO + stream. */ /*! -\fn status_t BBufferIO::SetSize(off_t size) -\brief Call the SetSize() function of the assigned BPositionIO stream. -\param size The new size of the BPositionIO object. -\retval B_OK The stream is resized. -\retval B_NO_INIT The object is not associated with a valid BPositionIO stream. + \fn status_t BBufferIO::SetSize(off_t size) + \brief Call the SetSize() function of the assigned BPositionIO stream. + \param size The new size of the BPositionIO object. + \retval B_OK The stream is resized. + \retval B_NO_INIT The object is not associated with a valid BPositionIO + stream. */ /*! -\fn status_t BBufferIO::Flush() -\brief Write pending modifications to the stream. -\return The amount of bytes written, or if it failed it will return an error code. + \fn status_t BBufferIO::Flush() + \brief Write pending modifications to the stream. + \return The amount of bytes written, or if it failed it will return an error + code. */ /*! -\fn BPositionIO *BBufferIO::Stream() const -\brief Return a pointer to the stream specified on construction. -\return A pointer to the BPositionIO stream specified on construction. + \fn BPositionIO *BBufferIO::Stream() const + \brief Return a pointer to the stream specified on construction. + \return A pointer to the BPositionIO stream specified on construction. */ /*! -\fn size_t BBufferIO::BufferSize() const -\brief Return the size of the internal buffer. -\return The size of the buffer allocated by the object. + \fn size_t BBufferIO::BufferSize() const + \brief Return the size of the internal buffer. + \return The size of the buffer allocated by the object. */ /*! -\fn bool BBufferIO::OwnsStream() const -\brief Tell if the BBufferIO object "owns" the specified stream. -\retval true The object "owns" the stream and will destroy it upon destruction. -\retval false The object does not own the stream. -\sa SetOwnsStream() + \fn bool BBufferIO::OwnsStream() const + \brief Tell if the BBufferIO object "owns" the specified stream. + \retval true The object "owns" the stream and will destroy it upon + destruction. + \retval false The object does not own the stream. + \see SetOwnsStream() */ /*! -\fn void BBufferIO::SetOwnsStream(bool owns_stream) -\brief Set the \c owns_stream property of the object. -\param owns_stream If you pass \c true, the object will delete the stream - upon destruction, if you pass \c false it will not. + \fn void BBufferIO::SetOwnsStream(bool owns_stream) + \brief Set the \c owns_stream property of the object. + \param owns_stream If you pass \c true, the object will delete the stream + upon destruction, if you pass \c false it will not. */ /*! -\fn void BBufferIO::PrintToStream() const -\brief Print the object to stdout. + \fn void BBufferIO::PrintToStream() const + \brief Print the object to stdout. */ Modified: haiku/trunk/docs/user/support/DataIO.dox =================================================================== --- haiku/trunk/docs/user/support/DataIO.dox 2007-04-02 11:25:43 UTC (rev 20510) +++ haiku/trunk/docs/user/support/DataIO.dox 2007-04-02 11:39:10 UTC (rev 20511) @@ -1,16 +1,14 @@ -// -// Copyright 2007, Haiku Inc. All Rights Reserved. -// -// Distributed under the terms of the MIT License. -// -// -// Documentation by: -// Niels Sascha Reedijk -// Stefano Ceccherini (burton666 at libero.it) -// Corresponds to: -// /trunk/headers/os/support/DataIO.h rev 17981 -// /trunk/src/kits/support/DataIO.cpp rev 17981 -// +/* + * Copyright 2007, Haiku, Inc. All Rights Reserved. + * Distributed under the terms of the MIT License. + * + * Documentation by: + * Niels Sascha Reedijk + * Stefano Ceccherini (burton666 at libero.it) + * Corresponds to: + * /trunk/headers/os/support/DataIO.h rev 17981 + * /trunk/src/kits/support/DataIO.cpp rev 20510 + */ /*! \file DataIO.h Added: haiku/trunk/docs/user/support/Flattenable.dox =================================================================== --- haiku/trunk/docs/user/support/Flattenable.dox 2007-04-02 11:25:43 UTC (rev 20510) +++ haiku/trunk/docs/user/support/Flattenable.dox 2007-04-02 11:39:10 UTC (rev 20511) @@ -0,0 +1,171 @@ +/* + * Copyright 2007, Haiku, Inc. All Rights Reserved. + * Distributed under the terms of the MIT License. + * + * Documentation written by: + * Niels Sascha Reedijk + * Corresponds to: + * /trunk/headers/os/support/Flattenable.h rev 19972 + * /trunk/src/kits/support/Flattenable.cpp rev 12963 + */ + +/*! + \file Flattenable.h + \brief Provides the BFlattenable interface +*/ + +/*! + \class BFlattenable + \ingroup support + \ingroup libbe + \brief Interface for classes that can flatten and unflatten themselves to + a stream of bytes. + + It is convenient that objects can be stored as a flat stream of bytes. In + this way, they can be written to disk, exchanged between applications or send + over networks. This ability, which is known in many other programming + languages as marshalling, is not native in C++. The Haiku API has created a + universal interface that classes have if they are able to be flattened. This + class defines the interface. This class does nothing on its own, and + therefore contains pure virtuals. By inheriting this class and inmplementing + the methods in your own class, you will be able to use your objects as + flattenable objects throughout the Haiku API. + + Flattened objects can be used for example when sending messages within an + application or between applications. The BMessage class uses the interface + to store and transmit custom classes. + + If you want to be able to flatten your objects, you will need to implement + various methods. Flatten() and Unflatten() are where the magic happen. These + methods handle the actual flattening and unflattening. To identify flattened + data in for example BMessage, the object has a type_code. Type codes are + four byte long integers. You can choose to flatten to one of the existing + types, if you are certain that you are compatible to those, but you'll + usually define your own type. Your best option is by using a multicharacter + constant, such as 'STRI'. Implement TypeCode() to return the type you + support. Implement FlattenedSize() to make sure that other objects can + provide the right buffers. Implement IsFixedSize() to return whether your + objects always store to a fixed size. + + See the following example: + \code +type_code CUSTOM_STRING_TYPE = 'CUST'; + +class CustomString : public BFlattenable +{ +public: + char data[100]; + + // From BFlattenable + bool IsFixedSize() const { return false; }; + type_code TypeCode() const { return CUSTOM_STRING_TYPE; }; + ssize_t FlattenedSize() const { return strlen(data); }; + + status_t Flatten(void* buffer, ssize_t size) const + { + if ((strlen(data) + 1) < size) + return B_BAD_VALUE; + memcpy(buffer, data, size); + return B_OK; + }; + + status_t Unflatten(type_code code, const void* buffer, ssize_t size) + { + if (code != CUSTOM_STRING_TYPE) + return B_BAD_TYPE; + if (size > 100) + return B_NO_MEMORY; + memcpy(data, buffer, size); + return B_OK; + }; +}; + \endcode + + Have a look at TypeConstants.h for a list of all the types that the Haiku + API defines. + + The Haiku API has a second interface for storing objects, which is with + BArchivable. BArchivable is for more complex cases. Instead of one flat + datastream, it stores an object in a BMessage. In that way you can reflect + internals of a class better. It also provides an interface for instantiating + objects, that is, for objects to restore themselves from a BMessage. In + essence, BArchivable is more suitable for objects that are alive. In short + BFlattenable is for data objects, BArchivable is for 'live' objects. + + Other classes in the API that support flattening and unflattening are for + example BMessage, which enables you to conveniently write flattened data + to disk. Another example is BPath. Because of that you can store paths and + send them over via messages. Throughout the Haiku API you will find classes + that provide the flattening interface. +*/ + +/*! + \fn virtual bool BFlattenable::IsFixedSize() const = 0 + \brief Pure virtual that should return whether or not flattened objects of + this type always have a fixed size. +*/ + +/*! + \fn virtual type_code BFlattenable::TypeCode() const = 0 + \brief Pure virtual that should return which type_code this class flattens + to. + + \return Either one of the existing typecodes, found in TypeConstants.h, + if your class actually is compatible to those formats, or a custom + four byte integer constant. +*/ + +/*! + \fn virtual ssize_t BFlattenable::FlattenedSize() const = 0 + \brief Pure virtual that should return the size of the flattened object in + bytes. +*/ + +/*! + \fn virtual status_t BFlattenable::Flatten(void* buffer, ssize_t size) const = 0 + \brief Pure virtual that should flatten the object into the supplied + \a buffer. + + Please make sure that you check that the supplied buffer is not a \c NULL + pointer. Also make sure that the size of the flattened object does isn't + larger than the size of the buffer. + + \param buffer The buffer to flatten in. + \param size The size of the buffer. + \retval B_OK The object was flattened. + \retval B_NO_MEMORY The buffer was smaller than required. + \retval B_BAD_VALUE The buffer was a \c NULL pointer. +*/ + +/*! + \fn bool BFlattenable::AllowsTypeCode(type_code code) const + \brief Return whether or not the supplied type_code is supported. + + This default implementation checks the \a code argument against the type_code + returned by TypeCode(). + + \param code The type_code constant you want to check for. + \retval true The type_code is supported. + \retval false The type_code is not supported. +*/ + +/*! + \fn virtual status_t BFlattenable::Unflatten(type_code code, const void* buffer, ssize_t size) = 0 + \brief Pure virtual that should unflatten the buffer and put the contents + into the current object. + + Make sure that the supplied buffer is not \c NULL and that you actually + support the typecode. + + \param code The type_code this data is. + \param buffer The buffer to unflatten the data from. + \param size The size of the data. + \retval B_OK The object is unflattened. + \retval B_BAD_VALUE The \a buffer pointer is \c NULL or the data is invalid. + \retval B_BAD_TYPE You don't support data with this \a code. +*/ + +/*! + \fn virtual BFlattenable::~BFlattenable() + \brief Destructor. Does nothing. +*/ Modified: haiku/trunk/docs/user/support/Locker.dox =================================================================== --- haiku/trunk/docs/user/support/Locker.dox 2007-04-02 11:25:43 UTC (rev 20510) +++ haiku/trunk/docs/user/support/Locker.dox 2007-04-02 11:39:10 UTC (rev 20511) @@ -1,127 +1,204 @@ +/* + * Copyright 2007, Haiku, Inc. All Rights Reserved. + * Distributed under the terms of the MIT License. + * + * Documentation by: + * Niels Sascha Reedijk + * Corresponds to: + * /trunk/headers/os/support/Locker.h rev 19972 + * /trunk/src/kits/support/Locker.cpp rev 13826 + */ + /*! -\file Locker.h -\brief Provides locking class BLocker. + \file Locker.h + \brief Provides locking class BLocker. */ /*! -\class BLocker -\ingroup support -\ingroup libbe -\brief Semaphore-type class for thread safety. + \class BLocker + \ingroup support + \ingroup libbe + \brief Semaphore-type class for thread safety. -The BLocker interface is not merely a wrapper around a semaphore, but it -also has two advantages. First of all, it implements a benaphore. -A benaphore is in some ways more speed efficient, -because before it uses the internal semaphore, it first checks against a -variable that is only operated on with atomic operations. Setting a variable -is a lot more efficient than acquiring a semaphore, thus this type of locking -is much prefered. + The BLocker interface is not merely a wrapper around a semaphore, but it + also has two advantages. First of all, it implements a benaphore. + A benaphore is in some ways more speed efficient, + because before it uses the internal semaphore, it first checks against a + variable that is only operated on with atomic operations. Setting a variable + is a lot more efficient than acquiring a semaphore, thus this type of locking + is much prefered. -It basically works as follows. Whenever you newly created BLocker object -recieves a locking request, it atomically sets the benaphore variable to -\c 1. Then only additional calls from different threads will utilize the -semaphore. You can imagine that in many cases where you protect -of data that \em might be accessed by two or more concurrent threads, but -the chances of it happening being very small, the benaphore benefits the -most from it's speed. + It basically works as follows. Whenever you newly created BLocker object + recieves a locking request, it atomically sets the benaphore variable to + \c 1. Then only additional calls from different threads will utilize the + semaphore. You can imagine that in many cases where you protect + of data that \em might be accessed by two or more concurrent threads, but + the chances of it happening being very small, the benaphore benefits the + most from it's speed. -The other feature of BLocker that improves basic semaphore handling is that -it allows for recursive locks. The following piece of code works with a -BLocker, but block inevitably with a semaphore. Let's pretend I call \c Water(): + The other feature of BLocker that improves basic semaphore handling is that + it allows for recursive locks. The following piece of code works with a + BLocker, but block inevitably with a semaphore. Let's pretend I call + \c Water(): -\code -status_t -Flower::Grow(int length) -{ - if (fLock->Lock()) { - fLength += lenght; - fLock->Unlock(); - return B_OK; - } else { - return B_ERROR; + \code + status_t + Flower::Grow(int length) + { + if (fLock->Lock()) { + fLength += lenght; + fLock->Unlock(); + return B_OK; + } else { + return B_ERROR; + } } -} -status_t -Flower::Water(int amount) -{ - if (fLock->Lock()) { - status_t status = Grow(amount * 2); - fLock->Unlock(); - return status; - } else { - return B_ERROR; + status_t + Flower::Water(int amount) + { + if (fLock->Lock()) { + status_t status = Grow(amount * 2); + fLock->Unlock(); + return status; + } else { + return B_ERROR; + } } -} -\endcode + \endcode -This code would work because BLocker keeps track of the amount of lock -requests from the same thread. A normal semaphore would block in \c Grow() -because the semaphore would be acquired already. Please do make sure you -pair every Lock() with an Unlock() though, or you'll create a deadlock. + This code would work because BLocker keeps track of the amount of lock + requests from the same thread. A normal semaphore would block in \c Grow() + because the semaphore would be acquired already. Please do make sure you + pair every Lock() with an Unlock() though, or you'll create a deadlock. */ /*! -\fn BLocker::BLocker() -\brief Constructor. + \fn BLocker::BLocker() + \brief Constructor. + + Create a new BLocker with the default name of some BLocker. This + BLocker will use the benaphore-style locking. + + \note For debugging purposes, it's extremely convenient to actually give a + name to the object. In case of a deadlock, it's easier to track down which + BLocker object might have caused the problems. + + \see BLocker(const char* name, bool benaphoreStyle) for all the options. */ /*! -\fn BLocker::BLocker(const char* name) -\brief Constructor. + \fn BLocker::BLocker(const char* name) + \brief Constructor. + + Create a new BLocker with benaphore-style locking. + + \param name A NULL-terminated string that contains the name of the semaphore. + Note that the length of the names are limited to B_OS_NAME_LENGTH constant, + which includes the \c \\0 character. + + \see BLocker(const char* name, bool benaphoreStyle) for all the options. */ /*! -\fn BLocker::BLocker(bool benaphoreStyle) -\brief Constructor. + \fn BLocker::BLocker(bool benaphoreStyle) + \brief Constructor. + + Creates a BLocker with the default name of some BLocker. + + \note For debugging purposes, it's extremely convenient to actually give a + name to the object. In case of a deadlock, it's easier to track down which + BLocker object might have caused the problems. + + \param benaphoreStyle If you pass \c true, the locker will be in benaphore + style (which is the default option for other constructors). If you pass + \c false, the object will completely rely on semaphores for it's + functioning. + + \see BLocker(const char* name, bool benaphoreStyle) if you also want to set a + name. */ /*! -\fn BLocker::BLocker(const char* name, bool benaphoreStyle) -\brief Constructor. + \fn BLocker::BLocker(const char* name, bool benaphoreStyle) + \brief Constructor. + + \param name A NULL-terminated string that contains the name of the semaphore. + Note that the length of the names are limited to B_OS_NAME_LENGTH constant, + which includes the \c \\0 character. + \param benaphoreStyle If you pass \c true, the locker will be in benaphore + style (which is the default option for other constructors). If you pass + \c false, the object will completely rely on semaphores for it's + functioning. */ /*! -\fn virtual BLocker::~BLocker() -\brief Destructor. + \fn virtual BLocker::~BLocker() + \brief Destructor. + + Release the internal semaphore. Because of this, any pending Lock() calls + from other threads be cancelled. The return code will be \c false for + those calls. */ /*! -\fn bool BLocker::Lock(void) -\brief Add a lock request and block on it until we get it. + \fn bool BLocker::Lock() + \brief Add a lock request and block on it until we get it. + + \retval true Lock acquired succesfully. + \retval false Failed to acquire the lock. Most probable cause is that the + object is deleted. This frees the semaphore and releases the pending Lock() + requests. + + \see LockWithTimeout(bigtime_t timeout), Unlock() */ /*! -\fn status_t BLocker::LockWithTimeout(bigtime_t timeout) -\brief Add a lock request and block until we get it with a maximum time. + \fn status_t BLocker::LockWithTimeout(bigtime_t timeout) + \brief Add a lock request and block until we get it or until it times out. + + \param timeout This is a timeout in microseconds (one millionth of a second), + \e relative from now. + + \see Lock(), Unlock() */ /*! -\fn void BLocker::Unlock(void) -\brief Give up the lock count. + \fn void BLocker::Unlock(void) + \brief Release the lock that's currently held. */ /*! -\fn thread_id BLocker::LockingThread(void) const -\brief Return the \c thread_id of the thread that's currently holding the lock. + \fn thread_id BLocker::LockingThread(void) const + \brief Return the \c thread_id of the thread that's currently holding the + lock. */ /*! -\fn bool BLocker::IsLocked(void) const -\brief Check if your lock succeeded. + \fn bool BLocker::IsLocked(void) const + \brief Check if the calling thread is actually holding the lock. + + \retval true The thread from which this method is called from is currently + holding the lock. + \retval false The object is unlocked or the lock is held by another thread. */ /*! -\fn int32 BLocker::CountLocks(void) const -\brief Return the number of recursive locks that are currently held. + \fn int32 BLocker::CountLocks(void) const + \brief Return the number of recursive locks that are currently held. */ /*! -\fn nt32 BLocker::CountLockRequests(void) const -\brief Return the number of pending lock requests. + \fn nt32 BLocker::CountLockRequests(void) const + \brief Return the number of threads with a pending lock request. */ /*! -\fn sem_id BLocker::Sem(void) const -\brief Return the sem_id of the semaphore this object holds. + \fn sem_id BLocker::Sem(void) const + \brief Return the sem_id of the semaphore this object holds. + + \warning Like any other internal objects that the Haiku API might expose, + this semaphore id should in general be left alone. You should not use any + of the public low-level semaphore functions on this semaphore, because it + will harm the internal consistency of the object. */ Modified: haiku/trunk/docs/user/support/SupportDefs.dox =================================================================== --- haiku/trunk/docs/user/support/SupportDefs.dox 2007-04-02 11:25:43 UTC (rev 20510) +++ haiku/trunk/docs/user/support/SupportDefs.dox 2007-04-02 11:39:10 UTC (rev 20511) @@ -1,186 +1,187 @@ /*! -\file SupportDefs.h -\ingroup support -\brief Defines basic types and definitions for the Haiku API. + \file SupportDefs.h + \ingroup support + \brief Defines basic types and definitions for the Haiku API. */ /*! -\name Short byte long Type Formats + \name Short byte long Type Formats */ //! @{ /*! -\typedef typedef signed char int8 + \typedef typedef signed char int8 */ /*! -\typedef typedef unsigned char uint8 + \typedef typedef unsigned char uint8 */ /*! -\typedef typedef volatile signed char vint8 + \typedef typedef volatile signed char vint8 */ /*! -\typedef typedef volatile unsigned char vuint8 + \typedef typedef volatile unsigned char vuint8 */ //! @} /*! -\name Short 2-byte long Type Formats + \name Short 2-byte long Type Formats */ //! @{ /*! -\typedef typedef short int16 + \typedef typedef short int16 */ /*! -\typedef typedef unsigned short uint16 + \typedef typedef unsigned short uint16 */ /*! -\typedef typedef volatile short vint16 + \typedef typedef volatile short vint16 */ /*! -\typedef typedef volatile unsigned short vuint16 + \typedef typedef volatile unsigned short vuint16 */ //! @} /*! -\name Short 4-byte long Type Formats + \name Short 4-byte long Type Formats */ //! @{ /*! -\typedef typedef long int32 + \typedef typedef long int32 */ /*! -\typedef typedef unsigned long uint32 + \typedef typedef unsigned long uint32 */ /*! -\typedef typedef volatile long vint32 + \typedef typedef volatile long vint32 */ /*! -\typedef typedef volatile unsigned long vuint32 + \typedef typedef volatile unsigned long vuint32 */ //! @} /*! -\name Short 8-byte long Type Formats + \name Short 8-byte long Type Formats */ //! @{ /*! -\typedef typedef long long int64 + \typedef typedef long long int64 */ /*! -\typedef typedef unsigned long long uint64 + \typedef typedef unsigned long long uint64 */ /*! -\typedef typedef volatile long long vint64 + \typedef typedef volatile long long vint64 */ /*! -\typedef typedef volatile unsigned long long vuint64 + \typedef typedef volatile unsigned long long vuint64 */ //! @} /*! -\name Short volatile Type Formats + \name Short volatile Type Formats */ //! @{ /*! -\typedef typedef volatile long vlong + \typedef typedef volatile long vlong */ /*! -\typedef typedef volatile int vint + \typedef typedef volatile int vint */ /*! -\typedef typedef volatile short vshort + \typedef typedef volatile short vshort */ /*! -\typedef typedef volatile char vchar + \typedef typedef volatile char vchar */ /*! -\typedef typedef volatile unsigned long vulong + \typedef typedef volatile unsigned long vulong */ /*! -\typedef typedef volatile unsigned int vuint + \typedef typedef volatile unsigned int vuint */ /*! -\typedef typedef volatile unsigned short vushort + \typedef typedef volatile unsigned short vushort */ /*! -\typedef typedef volatile unsigned char vuchar + \typedef typedef volatile unsigned char vuchar */ //! @} /*! -\name Character Type Formats + \name Character Type Formats */ //! @{ /*! -\typedef typedef unsigned char uchar + \typedef typedef unsigned char uchar */ /*! -\typedef typedef unsigned short unichar + \typedef typedef unsigned short unichar */ //! @} /*! -\name Descriptive Type Formats + \name Descriptive Type Formats */ //! @{ /*! -\typedef typedef int32 status_t -\brief Represents one of the status codes defined in Error.h + \typedef typedef int32 status_t + \brief Represents one of the status codes defined in Error.h */ [... truncated: 259 lines follow ...] From mmu_man at mail.berlios.de Mon Apr 2 14:07:12 2007 From: mmu_man at mail.berlios.de (mmu_man at BerliOS) Date: Mon, 2 Apr 2007 14:07:12 +0200 Subject: [Haiku-commits] r20512 - haiku/trunk/src/add-ons/kernel/drivers/ports/usb_serial Message-ID: <200704021207.l32C7CHv003710@sheep.berlios.de> Author: mmu_man Date: 2007-04-02 14:07:12 +0200 (Mon, 02 Apr 2007) New Revision: 20512 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20512&view=rev Modified: haiku/trunk/src/add-ons/kernel/drivers/ports/usb_serial/driver.c Log: Remove hardcoded support list as it's dynamically generated from the device list. Modified: haiku/trunk/src/add-ons/kernel/drivers/ports/usb_serial/driver.c =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/ports/usb_serial/driver.c 2007-04-02 11:39:10 UTC (rev 20511) +++ haiku/trunk/src/add-ons/kernel/drivers/ports/usb_serial/driver.c 2007-04-02 12:07:12 UTC (rev 20512) @@ -135,21 +135,6 @@ }; /* supported devices*/ usb_support_descriptor *supported_devices; -#if 0 -usb_support_descriptor supported_devices[] = { - {USB_DEV_CLASS_COMM, 0, 0, 0, 0}, - {0, 0, 0, VND_PROLIFIC, PROD_PROLIFIC_RSAQ2 }, - {0, 0, 0, VND_IODATA, PROD_IODATA_USBRSAQ }, - {0, 0, 0, VND_ATEN, PROD_ATEN_UC232A }, - {0, 0, 0, VND_TDK, PROD_TDK_UHA6400 }, - {0, 0, 0, VND_RATOC, PROD_RATOC_REXUSB60 }, - {0, 0, 0, VND_PROLIFIC, PROD_PROLIFIC_PL2303 }, - {0, 0, 0, VND_ELECOM, PROD_ELECOM_UCSGT }, - - {0, 0, 0, VND_FTDI, PROD_8U100AX }, - {0, 0, 0, VND_FTDI, PROD_8U232AM }, -}; -#endif /* main devices table locking semaphore */ sem_id usb_serial_lock = -1; /* array of pointers to device objects */ From mmu_man at mail.berlios.de Mon Apr 2 14:13:16 2007 From: mmu_man at mail.berlios.de (mmu_man at BerliOS) Date: Mon, 2 Apr 2007 14:13:16 +0200 Subject: [Haiku-commits] r20513 - haiku/trunk/src/add-ons/kernel/drivers/ports/usb_serial Message-ID: <200704021213.l32CDGkn004568@sheep.berlios.de> Author: mmu_man Date: 2007-04-02 14:13:16 +0200 (Mon, 02 Apr 2007) New Revision: 20513 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20513&view=rev Modified: haiku/trunk/src/add-ons/kernel/drivers/ports/usb_serial/driver.h Log: Avoid redefining stuff. Modified: haiku/trunk/src/add-ons/kernel/drivers/ports/usb_serial/driver.h =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/ports/usb_serial/driver.h 2007-04-02 12:07:12 UTC (rev 20512) +++ haiku/trunk/src/add-ons/kernel/drivers/ports/usb_serial/driver.h 2007-04-02 12:13:16 UTC (rev 20513) @@ -45,13 +45,17 @@ #define CLS_LINE_RTS 0x0002 /* "forgotten" attributes etc ...*/ +#ifndef USB_EP_ADDR_DIR_IN #define USB_EP_ADDR_DIR_IN 0x80 #define USB_EP_ADDR_DIR_OUT 0x00 +#endif +#ifndef USB_EP_ATTR_CONTROL #define USB_EP_ATTR_CONTROL 0x00 #define USB_EP_ATTR_ISOCHRONOUS 0x01 #define USB_EP_ATTR_BULK 0x02 #define USB_EP_ATTR_INTERRUPT 0x03 +#endif /* USB class - communication devices */ #define USB_DEV_CLASS_COMM 0x02 From mmu_man at mail.berlios.de Mon Apr 2 14:17:20 2007 From: mmu_man at mail.berlios.de (mmu_man at BerliOS) Date: Mon, 2 Apr 2007 14:17:20 +0200 Subject: [Haiku-commits] r20514 - haiku/trunk/src/add-ons/kernel/drivers/ports/usb_serial Message-ID: <200704021217.l32CHKXm004911@sheep.berlios.de> Author: mmu_man Date: 2007-04-02 14:17:18 +0200 (Mon, 02 Apr 2007) New Revision: 20514 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20514&view=rev Modified: haiku/trunk/src/add-ons/kernel/drivers/ports/usb_serial/prolific.c Log: Remove commented out code & warnings. Modified: haiku/trunk/src/add-ons/kernel/drivers/ports/usb_serial/prolific.c =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/ports/usb_serial/prolific.c 2007-04-02 12:13:16 UTC (rev 20513) +++ haiku/trunk/src/add-ons/kernel/drivers/ports/usb_serial/prolific.c 2007-04-02 12:17:18 UTC (rev 20514) @@ -20,7 +20,7 @@ struct usb_endpoint_info *data_in_epi = NULL; const usb_device_descriptor *ddesc; status_t status = ENODEV; - int i = 0; + uint32 i = 0; TRACE_FUNCALLS("> add_prolific_device(%08x, %08x)\n", usd, uci); @@ -130,19 +130,15 @@ status_t reset_prolific_device(usb_serial_device *usd){ status_t status; - size_t len = 0; TRACE_FUNCALLS("> reset_prolific_device(%08x)\n", usd); -/* status = (*usb_m->send_request)(usd->dev, - USB_REQTYPE_VENDOR | USB_REQTYPE_DEVICE_OUT, - PROLIFIC_SET_REQUEST, 0, 0, 0, 0, 0, &len); - */ - usb_send_requ_list(usd->dev, pl_reset_common_reqs, SIZEOF(pl_reset_common_reqs)); + status = usb_send_requ_list(usd->dev, pl_reset_common_reqs, SIZEOF(pl_reset_common_reqs)); if (usd->spec.prolific.is_HX) - usb_send_requ_list(usd->dev, pl_reset_common_hx, SIZEOF(pl_reset_common_hx)); + status = usb_send_requ_list(usd->dev, pl_reset_common_hx, SIZEOF(pl_reset_common_hx)); else - usb_send_requ_list(usd->dev, pl_reset_common_nhx, SIZEOF(pl_reset_common_nhx)); - + status = usb_send_requ_list(usd->dev, pl_reset_common_nhx, SIZEOF(pl_reset_common_nhx)); + + status = B_OK; /* discard */ TRACE_FUNCRET("< reset_prolific_device returns:%08x\n", status); return status; } From mmu_man at mail.berlios.de Mon Apr 2 14:21:21 2007 From: mmu_man at mail.berlios.de (mmu_man at BerliOS) Date: Mon, 2 Apr 2007 14:21:21 +0200 Subject: [Haiku-commits] r20515 - haiku/trunk/src/add-ons/kernel/drivers/ports/usb_serial Message-ID: <200704021221.l32CLLta005947@sheep.berlios.de> Author: mmu_man Date: 2007-04-02 14:21:20 +0200 (Mon, 02 Apr 2007) New Revision: 20515 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20515&view=rev Modified: haiku/trunk/src/add-ons/kernel/drivers/ports/usb_serial/prolific.c Log: Fix some warnings. Modified: haiku/trunk/src/add-ons/kernel/drivers/ports/usb_serial/prolific.c =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/ports/usb_serial/prolific.c 2007-04-02 12:17:18 UTC (rev 20514) +++ haiku/trunk/src/add-ons/kernel/drivers/ports/usb_serial/prolific.c 2007-04-02 12:21:20 UTC (rev 20515) @@ -111,18 +111,18 @@ }; static status_t usb_send_requ_list(const usb_device *dev, struct req_item *list, size_t len){ - char buf[10]; - int i; + uint32 i; status_t status; for (i = 0; i < len; i++){ + char buf[10]; bool o = (list[i].requestType == PLRT_O); - size_t len = 1; + size_t buflen = 1; status = (*usb_m->send_request)(dev, list[i].requestType, list[i].request, list[i].value, list[i].index, - 0, o?0:buf, o?0:len, &len); + 0, o?0:buf, o?0:buflen, &buflen); TRACE("usb_send_requ_list: reqs[%d]: %08lx\n", i, status); } return B_OK; From korli at users.berlios.de Mon Apr 2 14:48:07 2007 From: korli at users.berlios.de (=?ISO-8859-1?Q?J=E9r=F4me_Duval?=) Date: Mon, 2 Apr 2007 14:48:07 +0200 Subject: [Haiku-commits] r20484 - haiku/trunk/src/add-ons/kernel/drivers/ports/usb_serial In-Reply-To: <200703312253.l2VMrhcQ013547@sheep.berlios.de> References: <200703312253.l2VMrhcQ013547@sheep.berlios.de> Message-ID: Hi Fran?ois, 2007/4/1, mmu_man at BerliOS : > + // other devices > + for (i = 1; i < SIZEOF(usb_serial_hw_devices); i++){ > + supported_devices[i].dev_class = 0; Could you explain the use of the uppercase sizeof() ? Also the select() and deselect() implementations you added seem to have a non compliant code style (space after if, before else). Thanks, J?r?me From revol at free.fr Mon Apr 2 16:15:19 2007 From: revol at free.fr (=?windows-1252?q?Fran=E7ois?= Revol) Date: Mon, 02 Apr 2007 16:15:19 +0200 CEST Subject: [Haiku-commits] =?windows-1252?q?r20484_-_haiku/trunk/src/add-ons?= =?windows-1252?q?/kernel/drivers/ports/usb=5Fserial?= In-Reply-To: Message-ID: <949267936-BeMail@laptop> > Hi Fran?ois, > > 2007/4/1, mmu_man at BerliOS : > > + // other devices > > + for (i = 1; i < SIZEOF(usb_serial_hw_devices); i++){ > > + supported_devices[i].dev_class = 0; > > Could you explain the use of the uppercase sizeof() ? I just reused that macro, it's private to the driver, just defined as (sizeof(array)/sizeof(array[0])). A better name could be countof or something if we want to make it public. > Also the select() and deselect() implementations you added seem to > have a non compliant code style (space after if, before else). I just did a copy-paste from the surrounding code, I didn't try to change the coding style cause I didn't want to rewrite the whole stuff :) I suppose a M-x indent-region in XEmacs would pretty it up, but I still don't have a fully working haiku-c++-mode yet (works mostly though, including automatic indent and tabs). Fran?ois. From superstippi at gmx.de Mon Apr 2 16:27:35 2007 From: superstippi at gmx.de (Stephan Assmus) Date: Mon, 02 Apr 2007 16:27:35 +0200 Subject: [Haiku-commits] r20507 - in haiku/trunk/src: apps/icon-o-matic apps/icon-o-matic/document apps/icon-o-matic/gui apps/icon-o-matic/import_export apps/icon-o-matic/import_export/flat_icon apps/icon-o-matic/import_export/message apps/icon-o-matic/import_export/svg apps/icon-o-matic/shape/commands apps/icon-o-matic/style apps/icon-o-matic/transformable libs/icon libs/icon/flat_icon libs/icon/shape libs/icon/style libs/icon/transformer In-Reply-To: <200704020909.l32997ux008596@sheep.berlios.de> References: <200704020909.l32997ux008596@sheep.berlios.de> Message-ID: <20070402162735.11009.6@stippis.mshome.net> Hi Axel, > Log: > * Put the remaining libicon.a classes into the BPrivate::Icon namespace. > * Minor cleanup (like removing the extra blank line between the > copyright and the header guard). thanks for doing this! Great, now I don't have to do it. It was on my list.... :-) Best regards, -Stephan From korli at mail.berlios.de Mon Apr 2 23:03:56 2007 From: korli at mail.berlios.de (korli at BerliOS) Date: Mon, 2 Apr 2007 23:03:56 +0200 Subject: [Haiku-commits] r20516 - haiku/trunk/src/kits/interface Message-ID: <200704022103.l32L3uar027830@sheep.berlios.de> Author: korli Date: 2007-04-02 23:03:56 +0200 (Mon, 02 Apr 2007) New Revision: 20516 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20516&view=rev Modified: haiku/trunk/src/kits/interface/Font.cpp Log: attach missing args for AS_GET_EDGES Modified: haiku/trunk/src/kits/interface/Font.cpp =================================================================== --- haiku/trunk/src/kits/interface/Font.cpp 2007-04-02 12:21:20 UTC (rev 20515) +++ haiku/trunk/src/kits/interface/Font.cpp 2007-04-02 21:03:56 UTC (rev 20516) @@ -1146,6 +1146,8 @@ BPrivate::AppServerLink link; link.StartMessage(AS_GET_EDGES); + link.Attach(fFamilyID); + link.Attach(fStyleID); link.Attach(numChars); uint32 bytesInBuffer = UTF8CountBytes(charArray, numChars); From korli at mail.berlios.de Tue Apr 3 00:53:07 2007 From: korli at mail.berlios.de (korli at BerliOS) Date: Tue, 3 Apr 2007 00:53:07 +0200 Subject: [Haiku-commits] r20517 - haiku/trunk/src/kits/app Message-ID: <200704022253.l32Mr7TX006847@sheep.berlios.de> Author: korli Date: 2007-04-03 00:53:01 +0200 (Tue, 03 Apr 2007) New Revision: 20517 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20517&view=rev Modified: haiku/trunk/src/kits/app/ServerLink.cpp Log: fix ServerLink::ReadShape and ServerLink::AttachShape for empty shapes Modified: haiku/trunk/src/kits/app/ServerLink.cpp =================================================================== --- haiku/trunk/src/kits/app/ServerLink.cpp 2007-04-02 21:03:56 UTC (rev 20516) +++ haiku/trunk/src/kits/app/ServerLink.cpp 2007-04-02 22:53:01 UTC (rev 20517) @@ -58,10 +58,12 @@ fReceiver->Read(&ptCount, sizeof(int32)); uint32 opList[opCount]; - fReceiver->Read(opList, opCount * sizeof(uint32)); + if (opCount > 0) + fReceiver->Read(opList, opCount * sizeof(uint32)); BPoint ptList[ptCount]; - fReceiver->Read(ptList, ptCount * sizeof(BPoint)); + if (ptCount > 0) + fReceiver->Read(ptList, ptCount * sizeof(BPoint)); shape->SetData(opCount, ptCount, opList, ptList); return B_OK; @@ -79,8 +81,11 @@ fSender->Attach(&opCount, sizeof(int32)); fSender->Attach(&ptCount, sizeof(int32)); - fSender->Attach(opList, opCount * sizeof(uint32)); - return fSender->Attach(ptList, ptCount * sizeof(BPoint)); + if (opCount > 0) + fSender->Attach(opList, opCount * sizeof(uint32)); + if (ptCount > 0) + fSender->Attach(ptList, ptCount * sizeof(BPoint)); + return B_OK; } From bonefish at mail.berlios.de Tue Apr 3 01:44:25 2007 From: bonefish at mail.berlios.de (bonefish at BerliOS) Date: Tue, 3 Apr 2007 01:44:25 +0200 Subject: [Haiku-commits] r20518 - haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/server Message-ID: <200704022344.l32NiPW9021552@sheep.berlios.de> Author: bonefish Date: 2007-04-03 01:44:24 +0200 (Tue, 03 Apr 2007) New Revision: 20518 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20518&view=rev Modified: haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/server/haiku_file_cache.cpp Log: Synchronized with kernel file cache changes in r20509. Modified: haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/server/haiku_file_cache.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/server/haiku_file_cache.cpp 2007-04-02 22:53:01 UTC (rev 20517) +++ haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/server/haiku_file_cache.cpp 2007-04-02 23:44:24 UTC (rev 20518) @@ -1161,14 +1161,14 @@ vecs[index] = fileExtent->disk; index++; + if (size <= fileExtent->disk.length) + break; + if (index >= maxVecs) { *_count = index; return B_BUFFER_OVERFLOW; } - if (size <= fileExtent->disk.length) - break; - size -= fileExtent->disk.length; } @@ -1185,8 +1185,8 @@ pages_io(file_cache_ref *ref, off_t offset, const iovec *vecs, size_t count, size_t *_numBytes, bool doWrite) { - TRACE(("pages_io: ref = %p, offset = %Ld, size = %lu, vecCount = %lu, %s\n", ref, offset, - *_numBytes, count, doWrite ? "write" : "read")); + TRACE(("pages_io: ref = %p, offset = %Ld, size = %lu, vecCount = %lu, %s\n", + ref, offset, *_numBytes, count, doWrite ? "write" : "read")); // translate the iovecs into direct device accesses file_io_vec fileVecs[MAX_FILE_IO_VECS]; @@ -1195,16 +1195,17 @@ status_t status = get_file_map(ref, offset, numBytes, fileVecs, &fileVecCount); - if (status < B_OK) { - TRACE(("get_file_map(offset = %Ld, numBytes = %lu) failed\n", offset, - numBytes)); + if (status < B_OK && status != B_BUFFER_OVERFLOW) { + TRACE(("get_file_map(offset = %Ld, numBytes = %lu) failed: %s\n", + offset, numBytes, strerror(status))); return status; } - // TODO: handle array overflow gracefully! + bool bufferOverflow = status == B_BUFFER_OVERFLOW; #ifdef TRACE_FILE_CACHE - dprintf("got %lu file vecs for %Ld:%lu:\n", fileVecCount, offset, numBytes); + dprintf("got %lu file vecs for %Ld:%lu%s:\n", fileVecCount, offset, + numBytes, bufferOverflow ? " (array too small)" : ""); for (size_t i = 0; i < fileVecCount; i++) { dprintf(" [%lu] offset = %Ld, size = %Ld\n", i, fileVecs[i].offset, fileVecs[i].length); @@ -1279,75 +1280,100 @@ size_t vecOffset = size; size_t bytesLeft = numBytes - size; - for (; fileVecIndex < fileVecCount; fileVecIndex++) { - file_io_vec &fileVec = fileVecs[fileVecIndex]; - off_t fileOffset = fileVec.offset; - off_t fileLeft = fileVec.length; + while (true) { + for (; fileVecIndex < fileVecCount; fileVecIndex++) { + file_io_vec &fileVec = fileVecs[fileVecIndex]; + off_t fileOffset = fileVec.offset; + off_t fileLeft = min_c(fileVec.length, bytesLeft); - fileLeft = min_c(fileVec.length, bytesLeft); + TRACE(("FILE VEC [%lu] length %Ld\n", fileVecIndex, fileLeft)); - TRACE(("FILE VEC [%lu] length %Ld\n", fileVecIndex, fileLeft)); + // process the complete fileVec + while (fileLeft > 0) { + iovec tempVecs[MAX_TEMP_IO_VECS]; + uint32 tempCount = 0; - // process the complete fileVec - while (fileLeft > 0) { - iovec tempVecs[MAX_TEMP_IO_VECS]; - uint32 tempCount = 0; + // size tracks how much of what is left of the current fileVec + // (fileLeft) has been assigned to tempVecs + size = 0; - // size tracks how much of what is left of the current fileVec - // (fileLeft) has been assigned to tempVecs - size = 0; + // assign what is left of the current fileVec to the tempVecs + for (size = 0; size < fileLeft && i < count + && tempCount < MAX_TEMP_IO_VECS;) { + // try to satisfy one iovec per iteration (or as much as + // possible) - // assign what is left of the current fileVec to the tempVecs - while (size < fileLeft && i < count - && tempCount < MAX_TEMP_IO_VECS) { - // try to satisfy one iovec per iteration (or as much as - // possible) - TRACE(("fill vec %ld, offset = %lu, size = %lu\n", - i, vecOffset, size)); + // bytes left of the current iovec + size_t vecLeft = vecs[i].iov_len - vecOffset; + if (vecLeft == 0) { + vecOffset = 0; + i++; + continue; + } - // bytes left of the current iovec - size_t vecLeft = vecs[i].iov_len - vecOffset; - if (vecLeft == 0) { - i++; - vecOffset = 0; - continue; + TRACE(("fill vec %ld, offset = %lu, size = %lu\n", + i, vecOffset, size)); + + // actually available bytes + size_t tempVecSize = min_c(vecLeft, fileLeft - size); + + tempVecs[tempCount].iov_base + = (void *)((addr_t)vecs[i].iov_base + vecOffset); + tempVecs[tempCount].iov_len = tempVecSize; + tempCount++; + + size += tempVecSize; + vecOffset += tempVecSize; } - // actually available bytes - size_t tempVecSize = min_c(vecLeft, fileLeft - size); + size_t bytes = size; + if (doWrite) { + status = vfs_write_pages(ref->deviceFD, fileOffset, + tempVecs, tempCount, &bytes, false); + } else { + status = vfs_read_pages(ref->deviceFD, fileOffset, + tempVecs, tempCount, &bytes, false); + } + if (status < B_OK) + return status; - tempVecs[tempCount].iov_base - = (void *)((addr_t)vecs[i].iov_base + vecOffset); - tempVecs[tempCount].iov_len = tempVecSize; - tempCount++; + totalSize += bytes; + bytesLeft -= size; + fileOffset += size; + fileLeft -= size; + //dprintf("-> file left = %Lu\n", fileLeft); - size += tempVecSize; - vecOffset += tempVecSize; + if (size != bytes || i >= count) { + // there are no more bytes or iovecs, let's bail out + *_numBytes = totalSize; + return B_OK; + } } + } - size_t bytes = size; - if (doWrite) { - status = vfs_write_pages(ref->deviceFD, fileOffset, - tempVecs, tempCount, &bytes, false); - } else { - status = vfs_read_pages(ref->deviceFD, fileOffset, - tempVecs, tempCount, &bytes, false); + if (bufferOverflow) { + status = get_file_map(ref, offset + totalSize, bytesLeft, fileVecs, + &fileVecCount); + if (status < B_OK && status != B_BUFFER_OVERFLOW) { + TRACE(("get_file_map(offset = %Ld, numBytes = %lu) failed: %s\n", + offset, numBytes, strerror(status))); + return status; } - if (status < B_OK) - return status; - totalSize += bytes; - bytesLeft -= size; - fileOffset += size; - fileLeft -= size; - //dprintf("-> file left = %Lu\n", fileLeft); + bufferOverflow = status == B_BUFFER_OVERFLOW; + fileVecIndex = 0; - if (size != bytes || i >= count) { - // there are no more bytes or iovecs, let's bail out - *_numBytes = totalSize; - return B_OK; +#ifdef TRACE_FILE_CACHE + dprintf("got %lu file vecs for %Ld:%lu%s:\n", fileVecCount, + offset + totalSize, numBytes, + bufferOverflow ? " (array too small)" : ""); + for (size_t i = 0; i < fileVecCount; i++) { + dprintf(" [%lu] offset = %Ld, size = %Ld\n", + i, fileVecs[i].offset, fileVecs[i].length); } - } +#endif + } else + break; } *_numBytes = totalSize; @@ -1361,7 +1387,7 @@ sure that it matches that criterion. */ static inline status_t -read_chunk_into_cache(file_cache_ref *ref, off_t offset, size_t size, +read_chunk_into_cache(file_cache_ref *ref, off_t offset, size_t numBytes, int32 pageOffset, addr_t buffer, size_t bufferSize) { TRACE(("read_chunk(offset = %Ld, size = %lu, pageOffset = %ld, buffer = %#lx, bufferSize = %lu\n", @@ -1374,7 +1400,7 @@ int32 pageIndex = 0; // allocate pages for the cache and mark them busy - for (size_t pos = 0; pos < size; pos += B_PAGE_SIZE) { + for (size_t pos = 0; pos < numBytes; pos += B_PAGE_SIZE) { vm_page *page = pages[pageIndex++] = vm_page_allocate_page(PAGE_STATE_FREE); if (page == NULL) panic("no more pages!"); @@ -1392,7 +1418,7 @@ mutex_unlock(&ref->lock); // read file into reserved pages - status_t status = pages_io(ref, offset, vecs, vecCount, &size, false); + status_t status = pages_io(ref, offset, vecs, vecCount, &numBytes, false); if (status < B_OK) { // reading failed, free allocated pages @@ -1493,7 +1519,7 @@ /** Like read_chunk_into_cache() but writes data into the cache */ static inline status_t -write_chunk_to_cache(file_cache_ref *ref, off_t offset, size_t size, +write_chunk_to_cache(file_cache_ref *ref, off_t offset, size_t numBytes, int32 pageOffset, addr_t buffer, size_t bufferSize) { iovec vecs[MAX_IO_VECS]; @@ -1506,7 +1532,7 @@ bool writeThrough = false; // allocate pages for the cache and mark them busy - for (size_t pos = 0; pos < size; pos += B_PAGE_SIZE) { + for (size_t pos = 0; pos < numBytes; pos += B_PAGE_SIZE) { // ToDo: if space is becoming tight, and this cache is already grown // big - shouldn't we better steal the pages directly in that case? // (a working set like approach for the file cache) @@ -1552,7 +1578,7 @@ iovec readVec = { (void *)last, B_PAGE_SIZE }; size_t bytesRead = B_PAGE_SIZE; - status = pages_io(ref, offset + size - B_PAGE_SIZE, &readVec, 1, + status = pages_io(ref, offset + numBytes - B_PAGE_SIZE, &readVec, 1, &bytesRead, false); // ToDo: handle errors for real! if (status < B_OK) @@ -1577,7 +1603,7 @@ if (writeThrough) { // write cached pages back to the file if we were asked to do that - status_t status = pages_io(ref, offset, vecs, vecCount, &size, true); + status_t status = pages_io(ref, offset, vecs, vecCount, &numBytes, true); if (status < B_OK) { // ToDo: remove allocated pages, ...? panic("file_cache: remove allocated pages! write pages failed: %s\n", From axeld at pinc-software.de Tue Apr 3 02:28:05 2007 From: axeld at pinc-software.de (Axel =?iso-8859-15?q?D=F6rfler?=) Date: Tue, 03 Apr 2007 02:28:05 +0200 CEST Subject: [Haiku-commits] =?iso-8859-15?q?r20518_-_haiku/trunk/src/add-ons/?= =?iso-8859-15?q?kernel/file=5Fsystems/userlandfs/server?= In-Reply-To: <200704022344.l32NiPW9021552@sheep.berlios.de> Message-ID: <54998127915-BeMail@zon> bonefish at BerliOS wrote: > Log: > Synchronized with kernel file cache changes in r20509. On the next next change I will probably remember to do that myself, thanks :-) Bye, Axel. From bonefish at mail.berlios.de Tue Apr 3 06:29:25 2007 From: bonefish at mail.berlios.de (bonefish at BerliOS) Date: Tue, 3 Apr 2007 06:29:25 +0200 Subject: [Haiku-commits] r20519 - haiku/trunk/src/system/kernel/fs Message-ID: <200704030429.l334TPUC003497@sheep.berlios.de> Author: bonefish Date: 2007-04-03 06:29:24 +0200 (Tue, 03 Apr 2007) New Revision: 20519 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20519&view=rev Modified: haiku/trunk/src/system/kernel/fs/vfs.cpp Log: get_vnode_name(): * read_dir() is supposed to return B_OK and and a count of 0 when reaching the end of the directory. In case the node in question could not be found, we were looping infinitely. * free_dir_cookie() was not invoked. Modified: haiku/trunk/src/system/kernel/fs/vfs.cpp =================================================================== --- haiku/trunk/src/system/kernel/fs/vfs.cpp 2007-04-02 23:44:24 UTC (rev 20518) +++ haiku/trunk/src/system/kernel/fs/vfs.cpp 2007-04-03 04:29:24 UTC (rev 20519) @@ -1852,13 +1852,21 @@ status = dir_read(parent, cookie, buffer, bufferSize, &num); if (status < B_OK) break; + if (num == 0) { + status = B_ENTRY_NOT_FOUND; + break; + } if (vnode->id == buffer->d_ino) { // found correct entry! break; } } - FS_CALL(vnode, close_dir)(vnode->mount->cookie, vnode->private_node, cookie); + + FS_CALL(vnode, close_dir)(vnode->mount->cookie, vnode->private_node, + cookie); + FS_CALL(vnode, free_dir_cookie)(vnode->mount->cookie, + vnode->private_node, cookie); } return status; } From bonefish at mail.berlios.de Tue Apr 3 06:30:23 2007 From: bonefish at mail.berlios.de (bonefish at BerliOS) Date: Tue, 3 Apr 2007 06:30:23 +0200 Subject: [Haiku-commits] r20520 - in haiku/trunk/src/add-ons/kernel/file_systems: ramfs reiserfs Message-ID: <200704030430.l334UNfF004382@sheep.berlios.de> Author: bonefish Date: 2007-04-03 06:30:22 +0200 (Tue, 03 Apr 2007) New Revision: 20520 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20520&view=rev Modified: haiku/trunk/src/add-ons/kernel/file_systems/ramfs/Jamfile haiku/trunk/src/add-ons/kernel/file_systems/reiserfs/Jamfile Log: Define debug output prefixes. Modified: haiku/trunk/src/add-ons/kernel/file_systems/ramfs/Jamfile =================================================================== --- haiku/trunk/src/add-ons/kernel/file_systems/ramfs/Jamfile 2007-04-03 04:29:24 UTC (rev 20519) +++ haiku/trunk/src/add-ons/kernel/file_systems/ramfs/Jamfile 2007-04-03 04:30:22 UTC (rev 20520) @@ -8,6 +8,8 @@ SEARCH_SOURCE += [ FDirName $(userlandFSTop) shared ] ; +DEFINES += DEBUG_APP="\\\"ramfs\\\"" ; + KernelAddon ramfs : Debug.cpp Locker.cpp Modified: haiku/trunk/src/add-ons/kernel/file_systems/reiserfs/Jamfile =================================================================== --- haiku/trunk/src/add-ons/kernel/file_systems/reiserfs/Jamfile 2007-04-03 04:29:24 UTC (rev 20519) +++ haiku/trunk/src/add-ons/kernel/file_systems/reiserfs/Jamfile 2007-04-03 04:30:22 UTC (rev 20520) @@ -8,6 +8,8 @@ SEARCH_SOURCE += [ FDirName $(userlandFSTop) shared ] ; +DEFINES += DEBUG_APP="\\\"reiserfs\\\"" ; + KernelAddon reiserfs : Debug.cpp From bonefish at mail.berlios.de Tue Apr 3 06:31:31 2007 From: bonefish at mail.berlios.de (bonefish at BerliOS) Date: Tue, 3 Apr 2007 06:31:31 +0200 Subject: [Haiku-commits] r20521 - haiku/trunk/src/add-ons/kernel/file_systems/ramfs Message-ID: <200704030431.l334VVFJ006512@sheep.berlios.de> Author: bonefish Date: 2007-04-03 06:31:30 +0200 (Tue, 03 Apr 2007) New Revision: 20521 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20521&view=rev Removed: haiku/trunk/src/add-ons/kernel/file_systems/ramfs/makefile Log: Utterly obsolete. Deleted: haiku/trunk/src/add-ons/kernel/file_systems/ramfs/makefile From bonefish at mail.berlios.de Tue Apr 3 06:41:01 2007 From: bonefish at mail.berlios.de (bonefish at BerliOS) Date: Tue, 3 Apr 2007 06:41:01 +0200 Subject: [Haiku-commits] r20522 - in haiku/trunk: headers/private/userlandfs/private src/add-ons/kernel/file_systems/userlandfs/kernel_add_on src/add-ons/kernel/file_systems/userlandfs/private src/add-ons/kernel/file_systems/userlandfs/server Message-ID: <200704030441.l334f1gr026106@sheep.berlios.de> Author: bonefish Date: 2007-04-03 06:40:54 +0200 (Tue, 03 Apr 2007) New Revision: 20522 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20522&view=rev Modified: haiku/trunk/headers/private/userlandfs/private/Requests.h haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/kernel_add_on/Volume.cpp haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/kernel_add_on/Volume.h haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/kernel_add_on/kernel_interface.cpp haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/private/Requests.cpp haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/private/SingleReplyRequestHandler.cpp haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/server/BeOSKernelVolume.cpp haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/server/BeOSKernelVolume.h haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/server/HaikuKernelVolume.cpp haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/server/HaikuKernelVolume.h haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/server/UserlandRequestHandler.cpp haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/server/UserlandRequestHandler.h haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/server/Volume.cpp haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/server/Volume.h Log: The last missing hooks -- get_vnode_name(), write_attr_stat() and rewind_query() -- are passed to the userland. get_vnode_name() has an emulation in userland, in case the client FS doesn't implement it. Modified: haiku/trunk/headers/private/userlandfs/private/Requests.h =================================================================== --- haiku/trunk/headers/private/userlandfs/private/Requests.h 2007-04-03 04:31:30 UTC (rev 20521) +++ haiku/trunk/headers/private/userlandfs/private/Requests.h 2007-04-03 04:40:54 UTC (rev 20522) @@ -43,6 +43,8 @@ // vnodes LOOKUP_REQUEST, LOOKUP_REPLY, + GET_VNODE_NAME_REQUEST, + GET_VNODE_NAME_REPLY, READ_VNODE_REQUEST, READ_VNODE_REPLY, WRITE_VNODE_REQUEST, @@ -137,6 +139,8 @@ WRITE_ATTR_REPLY, READ_ATTR_STAT_REQUEST, READ_ATTR_STAT_REPLY, + WRITE_ATTR_STAT_REQUEST, + WRITE_ATTR_STAT_REPLY, RENAME_ATTR_REQUEST, RENAME_ATTR_REPLY, REMOVE_ATTR_REQUEST, @@ -169,6 +173,8 @@ FREE_QUERY_COOKIE_REPLY, READ_QUERY_REQUEST, READ_QUERY_REPLY, + REWIND_QUERY_REQUEST, + REWIND_QUERY_REPLY, // userland -> kernel requests // notifications @@ -428,6 +434,23 @@ int type; }; +// GetVNodeNameRequest +class GetVNodeNameRequest : public NodeRequest { +public: + GetVNodeNameRequest() : NodeRequest(GET_VNODE_NAME_REQUEST) {} + + size_t size; +}; + +// GetVNodeNameReply +class GetVNodeNameReply : public ReplyRequest { +public: + GetVNodeNameReply() : ReplyRequest(GET_VNODE_NAME_REPLY) {} + status_t GetAddressInfos(AddressInfo* infos, int32* count); + + Address buffer; +}; + // ReadVNodeRequest class ReadVNodeRequest : public VolumeRequest { public: @@ -1085,6 +1108,21 @@ struct stat st; }; +// WriteAttrStatRequest +class WriteAttrStatRequest : public AttributeRequest { +public: + WriteAttrStatRequest() : AttributeRequest(WRITE_ATTR_STAT_REQUEST) {} + + struct stat st; + uint32 mask; +}; + +// WriteAttrStatReply +class WriteAttrStatReply : public ReplyRequest { +public: + WriteAttrStatReply() : ReplyRequest(WRITE_ATTR_STAT_REPLY) {} +}; + // RenameAttrRequest class RenameAttrRequest : public VolumeRequest { public: @@ -1308,7 +1346,19 @@ Address buffer; }; +// RewindQueryRequest +class RewindQueryRequest : public QueryRequest { +public: + RewindQueryRequest() : QueryRequest(REWIND_QUERY_REQUEST) {} +}; +// RewindQueryReply +class RewindQueryReply : public ReplyRequest { +public: + RewindQueryReply() : ReplyRequest(REWIND_QUERY_REPLY) {} +}; + + // #pragma mark - // #pragma mark ----- userland requests ----- @@ -1552,6 +1602,10 @@ return task((LookupRequest*)request); case LOOKUP_REPLY: return task((LookupReply*)request); + case GET_VNODE_NAME_REQUEST: + return task((GetVNodeNameRequest*)request); + case GET_VNODE_NAME_REPLY: + return task((GetVNodeNameReply*)request); case READ_VNODE_REQUEST: return task((ReadVNodeRequest*)request); case READ_VNODE_REPLY: @@ -1721,6 +1775,10 @@ return task((ReadAttrStatRequest*)request); case READ_ATTR_STAT_REPLY: return task((ReadAttrStatReply*)request); + case WRITE_ATTR_STAT_REQUEST: + return task((WriteAttrStatRequest*)request); + case WRITE_ATTR_STAT_REPLY: + return task((WriteAttrStatReply*)request); case RENAME_ATTR_REQUEST: return task((RenameAttrRequest*)request); case RENAME_ATTR_REPLY: @@ -1779,6 +1837,10 @@ return task((ReadQueryRequest*)request); case READ_QUERY_REPLY: return task((ReadQueryReply*)request); + case REWIND_QUERY_REQUEST: + return task((RewindQueryRequest*)request); + case REWIND_QUERY_REPLY: + return task((RewindQueryReply*)request); // userland -> kernel requests // notifications @@ -1869,6 +1931,8 @@ // vnodes using UserlandFSUtil::LookupRequest; using UserlandFSUtil::LookupReply; +using UserlandFSUtil::GetVNodeNameRequest; +using UserlandFSUtil::GetVNodeNameReply; using UserlandFSUtil::ReadVNodeRequest; using UserlandFSUtil::ReadVNodeReply; using UserlandFSUtil::WriteVNodeRequest; @@ -1956,6 +2020,8 @@ using UserlandFSUtil::WriteAttrReply; using UserlandFSUtil::ReadAttrStatRequest; using UserlandFSUtil::ReadAttrStatReply; +using UserlandFSUtil::WriteAttrStatRequest; +using UserlandFSUtil::WriteAttrStatReply; using UserlandFSUtil::RenameAttrRequest; using UserlandFSUtil::RenameAttrReply; using UserlandFSUtil::RemoveAttrRequest; @@ -1986,6 +2052,8 @@ using UserlandFSUtil::FreeQueryCookieReply; using UserlandFSUtil::ReadQueryRequest; using UserlandFSUtil::ReadQueryReply; +using UserlandFSUtil::RewindQueryRequest; +using UserlandFSUtil::RewindQueryReply; // userland -> kernel requests // notifications Modified: haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/kernel_add_on/Volume.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/kernel_add_on/Volume.cpp 2007-04-03 04:31:30 UTC (rev 20521) +++ haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/kernel_add_on/Volume.cpp 2007-04-03 04:40:54 UTC (rev 20522) @@ -1,6 +1,9 @@ // Volume.cpp +#include "Volume.h" + #include +#include #include #include @@ -16,7 +19,6 @@ #include "RequestPort.h" #include "Requests.h" #include "userlandfs_ioctl.h" -#include "Volume.h" // missing ioctl()s // TODO: Place somewhere else. @@ -402,6 +404,55 @@ return error; } +// GetVNodeName +status_t +Volume::GetVNodeName(fs_vnode node, char* buffer, size_t bufferSize) +{ + // We don't check the capability -- if not implemented by the client FS, + // the functionality is emulated in userland. + + // get a free port + RequestPort* port = fFileSystem->GetPortPool()->AcquirePort(); + if (!port) + return B_ERROR; + PortReleaser _(fFileSystem->GetPortPool(), port); + + // prepare the request + RequestAllocator allocator(port->GetPort()); + GetVNodeNameRequest* request; + status_t error = AllocateRequest(allocator, &request); + if (error != B_OK) + return error; + + request->volume = fUserlandVolume; + request->node = node; + request->size = bufferSize; + + // send the request + KernelRequestHandler handler(this, GET_VNODE_NAME_REPLY); + GetVNodeNameReply* reply; + error = _SendRequest(port, &allocator, &handler, (Request**)&reply); + if (error != B_OK) + return error; + RequestReleaser requestReleaser(port, reply); + + // process the reply + if (reply->error != B_OK) + return reply->error; + + char* readBuffer = (char*)reply->buffer.GetData(); + size_t nameLen = reply->buffer.GetSize(); + nameLen = strnlen(readBuffer, nameLen); + if (nameLen <= 1 || nameLen >= bufferSize) + RETURN_ERROR(B_BAD_DATA); + + memcpy(buffer, readBuffer, nameLen); + buffer[nameLen] = '\0'; + + _SendReceiptAck(port); + return error; +} + // ReadVNode status_t Volume::ReadVNode(vnode_id vnid, bool reenter, fs_vnode* node) @@ -2099,6 +2150,48 @@ return error; } +// WriteAttrStat +status_t +Volume::WriteAttrStat(fs_vnode node, fs_cookie cookie, const struct stat *st, + int statMask) +{ + // check capability + if (!fFileSystem->HasCapability(FS_CAPABILITY_WRITE_ATTR_STAT)) + return B_BAD_VALUE; + + // get a free port + RequestPort* port = fFileSystem->GetPortPool()->AcquirePort(); + if (!port) + return B_ERROR; + PortReleaser _(fFileSystem->GetPortPool(), port); + + // prepare the request + RequestAllocator allocator(port->GetPort()); + WriteAttrStatRequest* request; + status_t error = AllocateRequest(allocator, &request); + if (error != B_OK) + return error; + + request->volume = fUserlandVolume; + request->node = node; + request->attrCookie = cookie; + request->st = *st; + request->mask = statMask; + + // send the request + KernelRequestHandler handler(this, WRITE_ATTR_STAT_REPLY); + WriteAttrStatReply* reply; + error = _SendRequest(port, &allocator, &handler, (Request**)&reply); + if (error != B_OK) + return error; + RequestReleaser requestReleaser(port, reply); + + // process the reply + if (reply->error != B_OK) + return reply->error; + return error; +} + // RenameAttr status_t Volume::RenameAttr(fs_vnode oldNode, const char* oldName, fs_vnode newNode, @@ -2632,6 +2725,44 @@ return error; } +// RewindQuery +status_t +Volume::RewindQuery(fs_cookie cookie) +{ + // check capability + if (!fFileSystem->HasCapability(FS_CAPABILITY_REWIND_QUERY)) + return B_BAD_VALUE; + + // get a free port + RequestPort* port = fFileSystem->GetPortPool()->AcquirePort(); + if (!port) + return B_ERROR; + PortReleaser _(fFileSystem->GetPortPool(), port); + + // prepare the request + RequestAllocator allocator(port->GetPort()); + RewindQueryRequest* request; + status_t error = AllocateRequest(allocator, &request); + if (error != B_OK) + return error; + + request->volume = fUserlandVolume; + request->queryCookie = cookie; + + // send the request + KernelRequestHandler handler(this, REWIND_QUERY_REPLY); + RewindQueryReply* reply; + error = _SendRequest(port, &allocator, &handler, (Request**)&reply); + if (error != B_OK) + return error; + RequestReleaser requestReleaser(port, reply); + + // process the reply + if (reply->error != B_OK) + return reply->error; + return error; +} + // #pragma mark - // #pragma mark ----- private implementations ----- Modified: haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/kernel_add_on/Volume.h =================================================================== --- haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/kernel_add_on/Volume.h 2007-04-03 04:31:30 UTC (rev 20521) +++ haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/kernel_add_on/Volume.h 2007-04-03 04:40:54 UTC (rev 20522) @@ -12,15 +12,18 @@ class Request; class RequestAllocator; class RequestHandler; +class RequestPort; +struct userlandfs_ioctl; } using UserlandFSUtil::Request; using UserlandFSUtil::RequestAllocator; using UserlandFSUtil::RequestHandler; +using UserlandFSUtil::RequestPort; +using UserlandFSUtil::userlandfs_ioctl; class FileSystem; -struct userlandfs_ioctl; class Volume : public Referencable { public: @@ -55,6 +58,8 @@ // vnodes status_t Lookup(fs_vnode dir, const char* entryName, vnode_id* vnid, int* type); + status_t GetVNodeName(fs_vnode node, char* buffer, + size_t bufferSize); status_t ReadVNode(vnode_id vnid, bool reenter, fs_vnode* node); status_t WriteVNode(fs_vnode node, bool reenter); @@ -141,6 +146,8 @@ size_t bufferSize, size_t* bytesWritten); status_t ReadAttrStat(fs_vnode node, fs_cookie cookie, struct stat *st); + status_t WriteAttrStat(fs_vnode node, fs_cookie cookie, + const struct stat *st, int statMask); status_t RenameAttr(fs_vnode oldNode, const char* oldName, fs_vnode newNode, const char* newName); @@ -169,6 +176,7 @@ status_t ReadQuery(fs_cookie cookie, void* buffer, size_t bufferSize, uint32 count, uint32* countRead); + status_t RewindQuery(fs_cookie cookie); private: status_t _Mount(const char* device, uint32 flags, Modified: haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/kernel_add_on/kernel_interface.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/kernel_add_on/kernel_interface.cpp 2007-04-03 04:31:30 UTC (rev 20521) +++ haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/kernel_add_on/kernel_interface.cpp 2007-04-03 04:40:54 UTC (rev 20522) @@ -176,7 +176,19 @@ return error; } -// TODO: userlandfs_get_vnode_name() +// userlandfs_get_vnode_name +static status_t +userlandfs_get_vnode_name(fs_volume fs, fs_vnode node, char *buffer, + size_t bufferSize) +{ + Volume* volume = (Volume*)fs; + PRINT(("userlandfs_get_vnode_name(%p, %p, %p, %lu)\n", fs, node, + buffer, bufferSize)); + status_t error = volume->GetVNodeName(node, buffer, bufferSize); + PRINT(("userlandfs_get_vnode_name() done: (%lx, \"%.*s\")\n", error, + (int)bufferSize, (error == B_OK ? buffer : NULL))); + return error; +} // userlandfs_get_vnode static status_t @@ -546,7 +558,7 @@ PRINT(("userlandfs_read_dir() done: (%lx, %lu)\n", error, *count)); #if DEBUG dirent* entry = buffer; - for (uint32 i = 0; i < *count; i++) { + for (uint32 i = 0; error == B_OK && i < *count; i++) { // R5's kernel vsprintf() doesn't seem to know `%.s', so // we need to work around. char name[B_FILE_NAME_LENGTH]; @@ -722,14 +734,25 @@ struct stat *st) { Volume* volume = (Volume*)fs; - PRINT(("userlandfs_read_attr_stat(%p, %p, %p', %p)\n", fs, node, cookie, + PRINT(("userlandfs_read_attr_stat(%p, %p, %p, %p)\n", fs, node, cookie, st)); status_t error = volume->ReadAttrStat(node, cookie, st); PRINT(("userlandfs_read_attr_stat() done: (%lx)\n", error)); return error; } -// TODO: userlandfs_write_attr_stat +// userlandfs_write_attr_stat +static status_t +userlandfs_write_attr_stat(fs_volume fs, fs_vnode node, fs_cookie cookie, + const struct stat *st, int statMask) +{ + Volume* volume = (Volume*)fs; + PRINT(("userlandfs_write_attr_stat(%p, %p, %p, %p, 0x%x)\n", fs, node, + cookie, st, statMask)); + status_t error = volume->WriteAttrStat(node, cookie, st, statMask); + PRINT(("userlandfs_write_attr_stat() done: (%lx)\n", error)); + return error; +} // userlandfs_rename_attr static status_t @@ -903,7 +926,7 @@ count); PRINT(("userlandfs_read_query() done: (%lx, %ld)\n", error, *count)); #if DEBUG - if (*count > 0) { + if (error == B_OK && *count > 0) { // R5's kernel vsprintf() doesn't seem to know `%.s', so // we need to work around. char name[B_FILE_NAME_LENGTH]; @@ -919,7 +942,16 @@ return error; } -// TODO: userlandfs_rewind_query() +// userlandfs_rewind_query +static status_t +userlandfs_rewind_query(fs_volume fs, fs_cookie cookie) +{ + Volume* volume = (Volume*)fs; + PRINT(("userlandfs_rewind_query(%p, %p)\n", fs, cookie)); + status_t error = volume->RewindQuery(cookie); + PRINT(("userlandfs_rewind_query() done: (%lx)\n", error)); + return error; +} // userlandfs_initialize @@ -1017,7 +1049,7 @@ /* vnode operations */ &userlandfs_lookup, - NULL, // &userlandfs_get_vnode_name, + &userlandfs_get_vnode_name, &userlandfs_get_vnode, &userlandfs_put_vnode, &userlandfs_remove_vnode, @@ -1079,7 +1111,7 @@ &userlandfs_write_attr, &userlandfs_read_attr_stat, - NULL, // &userlandfs_write_attr_stat, + &userlandfs_write_attr_stat, &userlandfs_rename_attr, &userlandfs_remove_attr, @@ -1099,7 +1131,7 @@ &userlandfs_close_query, &userlandfs_free_query_cookie, &userlandfs_read_query, - NULL, // &userlandfs_rewind_query, + &userlandfs_rewind_query }; module_info *modules[] = { Modified: haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/private/Requests.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/private/Requests.cpp 2007-04-03 04:31:30 UTC (rev 20521) +++ haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/private/Requests.cpp 2007-04-03 04:40:54 UTC (rev 20522) @@ -53,6 +53,14 @@ // return B_OK; //} +// GetVNodeNameReply +status_t +GetVNodeNameReply::GetAddressInfos(AddressInfo* infos, int32* count) +{ + ADD_STRING(buffer); + return B_OK; +} + // CreateRequest status_t CreateRequest::GetAddressInfos(AddressInfo* infos, int32* count) @@ -496,11 +504,13 @@ return false; // vnodes case LOOKUP_REQUEST: + case GET_VNODE_NAME_REQUEST: case READ_VNODE_REQUEST: case WRITE_VNODE_REQUEST: case FS_REMOVE_VNODE_REQUEST: return true; case LOOKUP_REPLY: + case GET_VNODE_NAME_REPLY: case READ_VNODE_REPLY: case WRITE_VNODE_REPLY: case FS_REMOVE_VNODE_REPLY: @@ -587,6 +597,7 @@ case READ_ATTR_REQUEST: case WRITE_ATTR_REQUEST: case READ_ATTR_STAT_REQUEST: + case WRITE_ATTR_STAT_REQUEST: case RENAME_ATTR_REQUEST: case REMOVE_ATTR_REQUEST: return true; @@ -594,10 +605,10 @@ case OPEN_ATTR_REPLY: case CLOSE_ATTR_REPLY: case FREE_ATTR_COOKIE_REPLY: - case READ_ATTR_REPLY: case WRITE_ATTR_REPLY: case READ_ATTR_STAT_REPLY: + case WRITE_ATTR_STAT_REPLY: case RENAME_ATTR_REPLY: case REMOVE_ATTR_REPLY: return false; @@ -625,11 +636,13 @@ case CLOSE_QUERY_REQUEST: case FREE_QUERY_COOKIE_REQUEST: case READ_QUERY_REQUEST: + case REWIND_QUERY_REQUEST: return true; case OPEN_QUERY_REPLY: case CLOSE_QUERY_REPLY: case FREE_QUERY_COOKIE_REPLY: case READ_QUERY_REPLY: + case REWIND_QUERY_REPLY: return false; // userland -> kernel requests @@ -697,11 +710,13 @@ return true; // vnodes case LOOKUP_REQUEST: + case GET_VNODE_NAME_REQUEST: case READ_VNODE_REQUEST: case WRITE_VNODE_REQUEST: case FS_REMOVE_VNODE_REQUEST: return false; case LOOKUP_REPLY: + case GET_VNODE_NAME_REPLY: case READ_VNODE_REPLY: case WRITE_VNODE_REPLY: case FS_REMOVE_VNODE_REPLY: @@ -789,6 +804,7 @@ case WRITE_ATTR_REQUEST: case RENAME_ATTR_REQUEST: case READ_ATTR_STAT_REQUEST: + case WRITE_ATTR_STAT_REQUEST: case REMOVE_ATTR_REQUEST: return false; case CREATE_ATTR_REPLY: @@ -798,6 +814,7 @@ case READ_ATTR_REPLY: case WRITE_ATTR_REPLY: case READ_ATTR_STAT_REPLY: + case WRITE_ATTR_STAT_REPLY: case RENAME_ATTR_REPLY: case REMOVE_ATTR_REPLY: return true; @@ -825,11 +842,13 @@ case CLOSE_QUERY_REQUEST: case FREE_QUERY_COOKIE_REQUEST: case READ_QUERY_REQUEST: + case REWIND_QUERY_REQUEST: return false; case OPEN_QUERY_REPLY: case CLOSE_QUERY_REPLY: case FREE_QUERY_COOKIE_REPLY: case READ_QUERY_REPLY: + case REWIND_QUERY_REPLY: return true; // userland -> kernel requests Modified: haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/private/SingleReplyRequestHandler.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/private/SingleReplyRequestHandler.cpp 2007-04-03 04:31:30 UTC (rev 20521) +++ haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/private/SingleReplyRequestHandler.cpp 2007-04-03 04:40:54 UTC (rev 20522) @@ -1,9 +1,10 @@ // SingleReplyRequestHandler.cpp +#include "SingleReplyRequestHandler.h" + #include "Compatibility.h" #include "Debug.h" #include "Request.h" -#include "SingleReplyRequestHandler.h" // constructor SingleReplyRequestHandler::SingleReplyRequestHandler() Modified: haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/server/BeOSKernelVolume.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/server/BeOSKernelVolume.cpp 2007-04-03 04:31:30 UTC (rev 20521) +++ haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/server/BeOSKernelVolume.cpp 2007-04-03 04:40:54 UTC (rev 20522) @@ -157,6 +157,16 @@ return error; } +// LookupNoType +status_t +BeOSKernelVolume::LookupNoType(fs_vnode dir, const char* entryName, + vnode_id* vnid) +{ + if (!fFSOps->walk) + return B_BAD_VALUE; + return fFSOps->walk(fVolumeCookie, dir, entryName, NULL, vnid); +} + // ReadVNode status_t BeOSKernelVolume::ReadVNode(vnode_id vnid, bool reenter, fs_vnode* node) Modified: haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/server/BeOSKernelVolume.h =================================================================== --- haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/server/BeOSKernelVolume.h 2007-04-03 04:31:30 UTC (rev 20521) +++ haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/server/BeOSKernelVolume.h 2007-04-03 04:40:54 UTC (rev 20522) @@ -27,6 +27,9 @@ // vnodes virtual status_t Lookup(fs_vnode dir, const char* entryName, vnode_id* vnid, int* type); + virtual status_t LookupNoType(fs_vnode dir, + const char* entryName, vnode_id* vnid); + // not required virtual status_t ReadVNode(vnode_id vnid, bool reenter, fs_vnode* node); virtual status_t WriteVNode(fs_vnode node, bool reenter); Modified: haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/server/HaikuKernelVolume.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/server/HaikuKernelVolume.cpp 2007-04-03 04:31:30 UTC (rev 20521) +++ haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/server/HaikuKernelVolume.cpp 2007-04-03 04:40:54 UTC (rev 20522) @@ -126,6 +126,17 @@ return fFSModule->lookup(fVolumeCookie, dir, entryName, vnid, type); } +// GetVNodeName +status_t +HaikuKernelVolume::GetVNodeName(fs_vnode node, char* buffer, size_t bufferSize) +{ + // If not implemented by the client file system, we invoke our super class + // version, which emulates the functionality. + if (!fFSModule->get_vnode_name) + return Volume::GetVNodeName(node, buffer, bufferSize); + return fFSModule->get_vnode_name(fVolumeCookie, node, buffer, bufferSize); +} + // ReadVNode status_t HaikuKernelVolume::ReadVNode(vnode_id vnid, bool reenter, fs_vnode* node) @@ -563,6 +574,17 @@ return fFSModule->read_attr_stat(fVolumeCookie, node, cookie, st); } +// WriteAttrStat +status_t +HaikuKernelVolume::WriteAttrStat(fs_vnode node, fs_cookie cookie, + const struct stat* st, int statMask) +{ + if (!fFSModule->write_attr_stat) + return B_BAD_VALUE; + return fFSModule->write_attr_stat(fVolumeCookie, node, cookie, st, + statMask); +} + // RenameAttr status_t HaikuKernelVolume::RenameAttr(fs_vnode oldNode, const char* oldName, @@ -710,3 +732,13 @@ return fFSModule->read_query(fVolumeCookie, cookie, (struct dirent*)buffer, bufferSize, countRead); } + +// RewindQuery +status_t +HaikuKernelVolume::RewindQuery(fs_cookie cookie) +{ + if (!fFSModule->rewind_query) + return B_BAD_VALUE; + return fFSModule->rewind_query(fVolumeCookie, cookie); +} + Modified: haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/server/HaikuKernelVolume.h =================================================================== --- haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/server/HaikuKernelVolume.h 2007-04-03 04:31:30 UTC (rev 20521) +++ haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/server/HaikuKernelVolume.h 2007-04-03 04:40:54 UTC (rev 20522) @@ -33,6 +33,8 @@ // vnodes virtual status_t Lookup(fs_vnode dir, const char* entryName, vnode_id* vnid, int* type); + virtual status_t GetVNodeName(fs_vnode node, char* buffer, + size_t bufferSize); virtual status_t ReadVNode(vnode_id vnid, bool reenter, fs_vnode* node); virtual status_t WriteVNode(fs_vnode node, bool reenter); @@ -119,6 +121,8 @@ size_t bufferSize, size_t* bytesWritten); virtual status_t ReadAttrStat(fs_vnode node, fs_cookie cookie, struct stat *st); + virtual status_t WriteAttrStat(fs_vnode node, fs_cookie cookie, + const struct stat* st, int statMask); virtual status_t RenameAttr(fs_vnode oldNode, const char* oldName, fs_vnode newNode, const char* newName); @@ -147,6 +151,7 @@ virtual status_t ReadQuery(fs_cookie cookie, void* buffer, size_t bufferSize, uint32 count, uint32* countRead); + virtual status_t RewindQuery(fs_cookie cookie); private: file_system_module_info* fFSModule; Modified: haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/server/UserlandRequestHandler.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/server/UserlandRequestHandler.cpp 2007-04-03 04:31:30 UTC (rev 20521) +++ haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/server/UserlandRequestHandler.cpp 2007-04-03 04:40:54 UTC (rev 20522) @@ -60,6 +60,8 @@ // vnodes case LOOKUP_REQUEST: return _HandleRequest((LookupRequest*)request); + case GET_VNODE_NAME_REQUEST: + return _HandleRequest((GetVNodeNameRequest*)request); case READ_VNODE_REQUEST: return _HandleRequest((ReadVNodeRequest*)request); case WRITE_VNODE_REQUEST: @@ -152,6 +154,8 @@ return _HandleRequest((WriteAttrRequest*)request); case READ_ATTR_STAT_REQUEST: return _HandleRequest((ReadAttrStatRequest*)request); + case WRITE_ATTR_STAT_REQUEST: + return _HandleRequest((WriteAttrStatRequest*)request); case RENAME_ATTR_REQUEST: return _HandleRequest((RenameAttrRequest*)request); case REMOVE_ATTR_REQUEST: @@ -184,6 +188,8 @@ return _HandleRequest((FreeQueryCookieRequest*)request); case READ_QUERY_REQUEST: return _HandleRequest((ReadQueryRequest*)request); + case REWIND_QUERY_REQUEST: + return _HandleRequest((RewindQueryRequest*)request); } PRINT(("UserlandRequestHandler::HandleRequest(): unexpected request: %lu\n", request->GetType())); @@ -396,6 +402,45 @@ // _HandleRequest status_t +UserlandRequestHandler::_HandleRequest(GetVNodeNameRequest* request) +{ + // check and execute the request + status_t result = B_OK; + Volume* volume = (Volume*)request->volume; + if (!volume) + result = B_BAD_VALUE; + + void* node = request->node; + size_t bufferSize = request->size; + + // allocate the reply + RequestAllocator allocator(fPort->GetPort()); + GetVNodeNameReply* reply; + status_t error = AllocateRequest(allocator, &reply); + if (error != B_OK) + RETURN_ERROR(error); + char* buffer; + if (result == B_OK) { + result = allocator.AllocateAddress(reply->buffer, bufferSize, 1, + (void**)&buffer, true); + } + + // execute the request + if (result == B_OK) { + RequestThreadContext context(volume); + result = volume->GetVNodeName(node, buffer, bufferSize); + } + + // reconstruct the reply, in case it has been overwritten + reply = new(reply) GetVNodeNameReply; + + // send the reply + reply->error = result; + return _SendReply(allocator, (result == B_OK)); +} + +// _HandleRequest +status_t UserlandRequestHandler::_HandleRequest(ReadVNodeRequest* request) { // check and execute the request @@ -1731,6 +1776,35 @@ // _HandleRequest status_t +UserlandRequestHandler::_HandleRequest(WriteAttrStatRequest* request) +{ + // check and execute the request + status_t result = B_OK; + Volume* volume = (Volume*)request->volume; + if (!volume) + result = B_BAD_VALUE; + + if (result == B_OK) { + RequestThreadContext context(volume); + result = volume->WriteAttrStat(request->node, request->attrCookie, + &request->st, request->mask); + } + + // prepare the reply + RequestAllocator allocator(fPort->GetPort()); + WriteAttrStatReply* reply; + status_t error = AllocateRequest(allocator, &reply); + if (error != B_OK) + RETURN_ERROR(error); + + reply->error = result; + + // send the reply + return _SendReply(allocator, false); +} + +// _HandleRequest +status_t UserlandRequestHandler::_HandleRequest(RenameAttrRequest* request) { // check and execute the request @@ -2173,7 +2247,35 @@ return _SendReply(allocator, (result == B_OK)); } +// _HandleRequest +status_t +UserlandRequestHandler::_HandleRequest(RewindQueryRequest* request) +{ + // check and execute the request + status_t result = B_OK; + Volume* volume = (Volume*)request->volume; + if (!volume) + result = B_BAD_VALUE; + if (result == B_OK) { + RequestThreadContext context(volume); + result = volume->RewindQuery(request->queryCookie); + } + + // prepare the reply + RequestAllocator allocator(fPort->GetPort()); + RewindQueryReply* reply; + status_t error = AllocateRequest(allocator, &reply); + if (error != B_OK) + RETURN_ERROR(error); + + reply->error = result; + + // send the reply + return _SendReply(allocator, false); +} + + // #pragma mark - other Modified: haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/server/UserlandRequestHandler.h =================================================================== --- haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/server/UserlandRequestHandler.h 2007-04-03 04:31:30 UTC (rev 20521) +++ haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/server/UserlandRequestHandler.h 2007-04-03 04:40:54 UTC (rev 20522) @@ -15,6 +15,7 @@ class WriteFSInfoRequest; // vnodes class LookupRequest; +class GetVNodeNameRequest; class ReadVNodeRequest; class WriteVNodeRequest; class FSRemoveVNodeRequest; @@ -61,6 +62,7 @@ class ReadAttrRequest; class WriteAttrRequest; class ReadAttrStatRequest; +class WriteAttrStatRequest; class RenameAttrRequest; class RemoveAttrRequest; // indices @@ -77,6 +79,7 @@ class CloseQueryRequest; class FreeQueryCookieRequest; class ReadQueryRequest; +class RewindQueryRequest; class RequestAllocator; @@ -107,6 +110,7 @@ // vnodes status_t _HandleRequest(LookupRequest* request); + status_t _HandleRequest(GetVNodeNameRequest* request); status_t _HandleRequest(ReadVNodeRequest* request); status_t _HandleRequest(WriteVNodeRequest* request); status_t _HandleRequest(FSRemoveVNodeRequest* request); @@ -159,6 +163,7 @@ status_t _HandleRequest(ReadAttrRequest* request); status_t _HandleRequest(WriteAttrRequest* request); status_t _HandleRequest(ReadAttrStatRequest* request); + status_t _HandleRequest(WriteAttrStatRequest* request); status_t _HandleRequest(RenameAttrRequest* request); status_t _HandleRequest(RemoveAttrRequest* request); @@ -178,6 +183,7 @@ status_t _HandleRequest(CloseQueryRequest* request); status_t _HandleRequest(FreeQueryCookieRequest* request); status_t _HandleRequest(ReadQueryRequest* request); + status_t _HandleRequest(RewindQueryRequest* request); status_t _SendReply(RequestAllocator& allocator, bool expectsReceipt); Modified: haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/server/Volume.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/server/Volume.cpp 2007-04-03 04:31:30 UTC (rev 20521) +++ haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/server/Volume.cpp 2007-04-03 04:40:54 UTC (rev 20522) @@ -2,6 +2,12 @@ #include "Volume.h" +#include +#include +#include + +#include "kernel_emu.h" + // constructor Volume::Volume(FileSystem* fileSystem, mount_id id) : fFileSystem(fileSystem), @@ -79,6 +85,82 @@ return B_BAD_VALUE; } +// LookupNoType +status_t +Volume::LookupNoType(fs_vnode dir, const char* entryName, vnode_id* vnid) +{ + int type; + return Lookup(dir, entryName, vnid, &type); +} + +// GetVNodeName +status_t +Volume::GetVNodeName(fs_vnode node, char* buffer, size_t bufferSize) +{ + // stat the node to get its ID + struct stat st; + status_t error = ReadStat(node, &st); + if (error != B_OK) + return error; + + // look up the parent directory + vnode_id parentID; + error = LookupNoType(node, "..", &parentID); + if (error != B_OK) + return error; + + // get the parent node handle [... truncated: 125 lines follow ...] From bonefish at cs.tu-berlin.de Tue Apr 3 06:54:49 2007 From: bonefish at cs.tu-berlin.de (Ingo Weinhold) Date: Tue, 03 Apr 2007 06:54:49 +0200 Subject: [Haiku-commits] r20518 - haiku/trunk/src/add-ons/kernel/file_systems/userlandfs/server In-Reply-To: <54998127915-BeMail@zon> References: <54998127915-BeMail@zon> Message-ID: <20070403065449.5981.1@cs.tu-berlin.de> On 2007-04-03 at 02:28:05 [+0200], Axel D?rfler wrote: > bonefish at BerliOS wrote: > > Log: > > Synchronized with kernel file cache changes in r20509. > > On the next next change I will probably remember to do that myself, > thanks :-) If you want to do that, I certainly won't object, but be warned: Although the code is pretty much the same as in the kernel, there are enough small changes (some VM/VFS functions have slightly different parameters, the structures look different), that larger patches won't apply cleanly. CU, Ingo From hugosantos at mail.berlios.de Tue Apr 3 07:38:54 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Tue, 3 Apr 2007 07:38:54 +0200 Subject: [Haiku-commits] r20523 - haiku/trunk/src/servers/net Message-ID: <200704030538.l335csuu018095@sheep.berlios.de> Author: hugosantos Date: 2007-04-03 07:38:45 +0200 (Tue, 03 Apr 2007) New Revision: 20523 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20523&view=rev Added: haiku/trunk/src/servers/net/StatusReplicant.cpp haiku/trunk/src/servers/net/StatusReplicant.h Modified: haiku/trunk/src/servers/net/AutoconfigLooper.cpp haiku/trunk/src/servers/net/DHCPClient.cpp haiku/trunk/src/servers/net/Jamfile haiku/trunk/src/servers/net/NetServer.cpp haiku/trunk/src/servers/net/NetServer.h Log: net_server: initial replicant version. * Still picture-less and thus ugly. * It provides updated information on what the net_server is doing in terms of interface configuration. * It is also able to show simplistic address information for configured interfaces. Modified: haiku/trunk/src/servers/net/AutoconfigLooper.cpp =================================================================== --- haiku/trunk/src/servers/net/AutoconfigLooper.cpp 2007-04-03 04:40:54 UTC (rev 20522) +++ haiku/trunk/src/servers/net/AutoconfigLooper.cpp 2007-04-03 05:38:45 UTC (rev 20523) @@ -40,6 +40,11 @@ void AutoconfigLooper::_ReadyToRun() { + BMessage interface(kMsgConfigureInterface); + interface.AddString("device", fDevice.String()); + interface.AddInt32("net:status", kStatusPreparing); + fTarget.SendMessage(&interface); + // start with DHCP DHCPClient* client = new DHCPClient(fTarget, fDevice.String()); @@ -57,8 +62,7 @@ // TODO: have a look at zeroconf // TODO: this could also be done add-on based - BMessage interface; - interface.AddString("device", fDevice.String()); + interface.ReplaceInt32("net:status", kStatusLinkNoConfig); uint8 mac[6]; uint8 last = 56; @@ -80,7 +84,7 @@ address.AddString("gateway", "192.168.0.254"); interface.AddMessage("address", &address); - fTarget.SendMessage(kMsgConfigureInterface, &interface); + fTarget.SendMessage(&interface); } Modified: haiku/trunk/src/servers/net/DHCPClient.cpp =================================================================== --- haiku/trunk/src/servers/net/DHCPClient.cpp 2007-04-03 04:40:54 UTC (rev 20522) +++ haiku/trunk/src/servers/net/DHCPClient.cpp 2007-04-03 05:38:45 UTC (rev 20523) @@ -474,6 +474,7 @@ fConfiguration.MakeEmpty(); fConfiguration.AddString("device", fDevice.String()); + fConfiguration.AddInt32("net:status", kStatusConnected); BMessage address; address.AddString("family", "inet"); Modified: haiku/trunk/src/servers/net/Jamfile =================================================================== --- haiku/trunk/src/servers/net/Jamfile 2007-04-03 04:40:54 UTC (rev 20522) +++ haiku/trunk/src/servers/net/Jamfile 2007-04-03 05:38:45 UTC (rev 20523) @@ -14,6 +14,7 @@ AutoconfigLooper.cpp DHCPClient.cpp Services.cpp + StatusReplicant.cpp : be libnetwork.so $(TARGET_LIBSTDC++) # for PPP Modified: haiku/trunk/src/servers/net/NetServer.cpp =================================================================== --- haiku/trunk/src/servers/net/NetServer.cpp 2007-04-03 04:40:54 UTC (rev 20522) +++ haiku/trunk/src/servers/net/NetServer.cpp 2007-04-03 05:38:45 UTC (rev 20523) @@ -11,12 +11,15 @@ #include "NetServer.h" #include "Services.h" #include "Settings.h" +#include "StatusReplicant.h" #include +#include #include #include #include #include +#include #include #include @@ -36,7 +39,12 @@ #include +const char *kSignature = "application/x-vnd.haiku-net_server"; +static const char *kDeskbarSignature = "application/x-vnd.Be-TSKB"; + + typedef std::map LooperMap; +typedef std::map StatusMap; class NetServer : public BServer { @@ -61,10 +69,15 @@ void _ConfigureInterfaces(int socket, BMessage* _missingDevice = NULL); void _BringUpInterfaces(); void _StartServices(); + status_t _AddStatusReplicant(bool force); + void _UpdateDeviceStatus(const char *device, int status); + void _UpdateReplicantStatus(); Settings fSettings; LooperMap fDeviceMap; + StatusMap fStatusMap; BMessenger fServices; + BMessenger fStatusMessenger; }; @@ -236,7 +249,7 @@ NetServer::NetServer(status_t& error) - : BServer("application/x-vnd.haiku-net_server", false, &error) + : BServer(kSignature, false, &error) { } @@ -266,6 +279,13 @@ fSettings.StartMonitoring(this); _BringUpInterfaces(); _StartServices(); + + // we have to wait for Deskbar to show up before + // adding the status replicant + be_roster->StartWatching(BMessenger(this), B_REQUEST_LAUNCHED); + // but possibly the Deskbar is already running + // so add immediatly + _AddStatusReplicant(true); } @@ -305,21 +325,52 @@ break; } - // we need a socket to talk to the networking stack - int socket = ::socket(AF_INET, SOCK_DGRAM, 0); - if (socket < 0) - break; + status_t status = B_OK; + if (message->GetInfo("address", NULL) != B_NAME_NOT_FOUND) { + // we need a socket to talk to the networking stack + int socket = ::socket(AF_INET, SOCK_DGRAM, 0); + if (socket < 0) + break; - status_t status = _ConfigureInterface(socket, *message, true); + status = _ConfigureInterface(socket, *message, true); - BMessage reply(B_REPLY); - reply.AddInt32("status", status); - message->SendReply(&reply); + BMessage reply(B_REPLY); + reply.AddInt32("status", status); + message->SendReply(&reply); - close(socket); + close(socket); + } + + if (status == B_OK) { + const char *device; + int32 net_status; + if (message->FindInt32("net:status", &net_status) == B_OK && + message->FindString("device", &device) == B_OK) { + _UpdateDeviceStatus(device, net_status); + } + } + break; } + case B_SOME_APP_LAUNCHED: + { + // check if Deskbar was launched + const char *signature; + if (message->FindString("be:signature", &signature) == B_OK) { + if (strcmp(signature, kDeskbarSignature) == 0) + _AddStatusReplicant(true); + } + break; + } + + case kRegisterStatusReplicant: + { + message->FindMessenger("messenger", &fStatusMessenger); + _UpdateReplicantStatus(); + break; + } + default: BApplication::MessageReceived(message); return; @@ -732,6 +783,13 @@ iterator->second->Quit(); fDeviceMap.erase(iterator); + + StatusMap::iterator it = fStatusMap.find(device); + if (it != fStatusMap.end()) { + fStatusMap.erase(it); + _UpdateReplicantStatus(); + } + return true; } @@ -877,6 +935,67 @@ } +status_t +NetServer::_AddStatusReplicant(bool force) +{ + BDeskbar deskbar; + status_t status; + + if (deskbar.HasItem(kStatusReplicant)) { + if (force) { + status = deskbar.RemoveItem(kStatusReplicant); + if (status != B_OK) + return status; + } else { + return B_OK; + } + } + + StatusReplicant *replicant = new StatusReplicant(); + status = deskbar.AddItem(replicant); + delete replicant; + + return status; +} + + +void +NetServer::_UpdateDeviceStatus(const char *device, int status) +{ + StatusMap::iterator it = fStatusMap.find(device); + if (it != fStatusMap.end() && it->second == status) + return; + + fStatusMap[device] = status; + _UpdateReplicantStatus(); +} + + +void +NetServer::_UpdateReplicantStatus() +{ + if (!fStatusMessenger.IsValid()) + return; + + int prevaling = kStatusUnknown; + + BMessage message(kStatusUpdate); + + for (StatusMap::iterator it = fStatusMap.begin(); + it != fStatusMap.end(); ++it) { + if (it->second > prevaling) + prevaling = it->second; + + message.AddString("intf:name", it->first.c_str()); + message.AddInt32("intf:status", it->second); + } + + message.AddInt32("net:status", prevaling); + + fStatusMessenger.SendMessage(&message); +} + + // #pragma mark - Modified: haiku/trunk/src/servers/net/NetServer.h =================================================================== --- haiku/trunk/src/servers/net/NetServer.h 2007-04-03 04:40:54 UTC (rev 20522) +++ haiku/trunk/src/servers/net/NetServer.h 2007-04-03 05:38:45 UTC (rev 20523) @@ -15,7 +15,18 @@ static const uint32 kMsgConfigureInterface = 'COif'; +extern const char *kSignature; +enum { + kStatusUnknown = 0, + kStatusNoLink, + kStatusLinkNoConfig, + kStatusConnected, + kStatusPreparing, + + kStatusCount +}; + extern bool get_family_index(const char* name, int32& familyIndex); extern int family_at_index(int32 index); extern bool parse_address(int32 familyIndex, const char* argument, Added: haiku/trunk/src/servers/net/StatusReplicant.cpp =================================================================== --- haiku/trunk/src/servers/net/StatusReplicant.cpp 2007-04-03 04:40:54 UTC (rev 20522) +++ haiku/trunk/src/servers/net/StatusReplicant.cpp 2007-04-03 05:38:45 UTC (rev 20523) @@ -0,0 +1,278 @@ +/* + * Copyright 2007, Haiku, Inc. All Rights Reserved. + * Distributed under the terms of the MIT License. + * + * Authors: + * Hugo Santos, hugosantos at gmail.com + */ + +#include "NetServer.h" +#include "StatusReplicant.h" + +#include +#include +#include +#include +#include + +#include +#include +#include + +const char *kStatusReplicant = "NetStatusView"; +static const uint32 kShowConfiguration = 'shcf'; + +static const uint8 kStatusColors[kStatusCount][3] = { + { 0, 0, 0 }, // Unknown + { 255, 0, 0 }, // NoLink + { 0, 0, 255 }, // LinkNoConfig + { 0, 255, 0 }, // Connected + { 255, 255, 0 }, // Preparing +}; + +struct information_entry { + const char *label; + int ioc; +}; + +static const information_entry kInformationEntries[] = { + { "Address", SIOCGIFADDR }, + { "Broadcast", SIOCGIFBRDADDR }, + { "Netmask", SIOCGIFNETMASK }, + { NULL } +}; + + +static const char *kStatusDescriptions[] = { + "Unknown", + "No Link", + "No stateful configuration", + "Ready", + "Configuring", +}; + + +StatusReplicant::StatusReplicant() + : BView(BRect(0, 0, 15, 15), kStatusReplicant, B_FOLLOW_ALL, 0), + fPopup("", false, false) +{ +} + + +StatusReplicant::StatusReplicant(BMessage *message) + : BView(message), fPopup("", false, false) +{ + // TODO: Load status bitmaps from resources + for (int i = 0; i < kStatusCount; i++) + fBitmaps[i] = NULL; +} + + +StatusReplicant::~StatusReplicant() +{ +} + + +StatusReplicant * +StatusReplicant::Instantiate(BMessage *data) +{ + if (validate_instantiation(data, kStatusReplicant)) + return new StatusReplicant(data); + return NULL; +} + + +status_t +StatusReplicant::Archive(BMessage *data, bool deep) const +{ + BView::Archive(data, deep); + data->AddString("add_on", kSignature); + data->AddString("class", kStatusReplicant); + return B_OK; +} + + +void +StatusReplicant::AttachedToWindow() +{ + BMessage message(kRegisterStatusReplicant); + message.AddMessenger("messenger", BMessenger(this)); + + if (BMessenger(kSignature).SendMessage(&message) != B_OK) { + // TODO: Remove myself from Deskbar + } + + ChangeStatus(kStatusUnknown); + PrepareMenu(InterfaceStatusList()); +} + + +void +StatusReplicant::MessageReceived(BMessage *message) +{ + switch (message->what) { + case kStatusUpdate: + UpdateFromMessage(message); + break; + case kShowConfiguration: + ShowConfiguration(message); + break; + default: + BView::MessageReceived(message); + break; + } +} + + +void +StatusReplicant::MouseDown(BPoint point) +{ + uint32 buttons; + BPoint where; + + GetMouse(&where, &buttons, true); + where = ConvertToScreen(point); + + fPopup.SetTargetForItems(this); + fPopup.Go(where, true, true); +} + + +void +StatusReplicant::UpdateFromMessage(BMessage *message) +{ + int32 newStatus, intfStatus; + + if (message->FindInt32("net:status", &newStatus) != B_OK + || newStatus < 0 || newStatus >= kStatusCount) + return; + + InterfaceStatusList status; + int index = 0; + while (message->FindInt32("intf:status", index, &intfStatus) == B_OK) { + if (intfStatus < 0 || intfStatus >= kStatusCount) + break; + + const char *name; + if (message->FindString("intf:name", index, &name) != B_OK) + break; + + status.push_back(InterfaceStatus(name, intfStatus)); + + index++; + } + + ChangeStatus(newStatus); + PrepareMenu(status); +} + + +void +StatusReplicant::ShowConfiguration(BMessage *message) +{ + const char *device; + if (message->FindString("intf:name", &device) != B_OK) + return; + + int32 status; + if (message->FindInt32("intf:status", &status) != B_OK) + return; + + if (status != kStatusConnected && status != kStatusLinkNoConfig) + return; + + int sock = socket(AF_INET, SOCK_DGRAM, 0); + if (sock < 0) + return; + + if (strlen(device) > IF_NAMESIZE) + return; + + ifreq request; + memset(&request, 0, sizeof(request)); + strcpy(request.ifr_name, device); + + string text = device; + text += " information:\n"; + size_t boldLength = text.size(); + + for (int i = 0; kInformationEntries[i].label; i++) { + if (ioctl(sock, kInformationEntries[i].ioc, &request, + sizeof(request)) < 0) { + close(sock); + return; + } + + char address[32]; + if (inet_ntop(AF_INET, &((sockaddr_in *)&request.ifr_addr)->sin_addr, + address, sizeof(address)) == NULL) { + close(sock); + return; + } + + text += "\n"; + text += kInformationEntries[i].label; + text += ": "; + text += address; + } + + close(sock); + + BAlert *info = new BAlert(device, text.c_str(), "Ok"); + BTextView *view = info->TextView(); + BFont font; + + view->SetStylable(true); + view->GetFont(&font); + font.SetSize(12); + font.SetFace(B_BOLD_FACE); + view->SetFontAndColor(0, boldLength, &font); + + info->Go(NULL); +} + + +void +StatusReplicant::PrepareMenu(const InterfaceStatusList &status) +{ + while (fPopup.RemoveItem((int32)0)); + + if (status.empty()) { + fPopup.AddItem(new BMenuItem("No interfaces available.", NULL)); + fPopup.ItemAt(0)->SetEnabled(false); + } else { + for (InterfaceStatusList::const_iterator i = status.begin(); + i != status.end(); ++i) { + std::string label = i->first; + label += ": "; + label += kStatusDescriptions[i->second]; + + BMessage *message = new BMessage(kShowConfiguration); + message->AddString("intf:name", i->first.c_str()); + message->AddInt32("intf:status", i->second); + + BMenuItem *item = new BMenuItem(label.c_str(), message); + if (i->second != kStatusConnected && + i->second != kStatusLinkNoConfig) + item->SetEnabled(false); + fPopup.AddItem(item); + } + } +} + + +void +StatusReplicant::ChangeStatus(int newStatus) +{ + if (fBitmaps[newStatus]) { + SetViewColor(Parent()->ViewColor()); + SetViewBitmap(fBitmaps[newStatus]); + } else { + ClearViewBitmap(); + SetViewColor(kStatusColors[newStatus][0], + kStatusColors[newStatus][1], + kStatusColors[newStatus][2]); + } + + Invalidate(); +} Added: haiku/trunk/src/servers/net/StatusReplicant.h =================================================================== --- haiku/trunk/src/servers/net/StatusReplicant.h 2007-04-03 04:40:54 UTC (rev 20522) +++ haiku/trunk/src/servers/net/StatusReplicant.h 2007-04-03 05:38:45 UTC (rev 20523) @@ -0,0 +1,52 @@ +/* + * Copyright 2007, Haiku, Inc. All Rights Reserved. + * Distributed under the terms of the MIT License. + * + * Authors: + * Hugo Santos, hugosantos at gmail.com + */ + +#ifndef _STATUS_REPLICANT_H +#define _STATUS_REPLICANT_H + +#include "NetServer.h" + +#include +#include + +#include +#include +#include + +static const uint32 kRegisterStatusReplicant = 'rnsr'; +static const uint32 kStatusUpdate = 'stup'; +extern const char *kStatusReplicant; + +class StatusReplicant : public BView { +public: + StatusReplicant(); + StatusReplicant(BMessage *); + virtual ~StatusReplicant(); + + static StatusReplicant *Instantiate(BMessage *); + status_t Archive(BMessage *, bool deep) const; + + void AttachedToWindow(); + void MessageReceived(BMessage *); + + void MouseDown(BPoint point); + +private: + typedef std::pair InterfaceStatus; + typedef std::vector InterfaceStatusList; + + void UpdateFromMessage(BMessage *); + void ShowConfiguration(BMessage *); + void PrepareMenu(const InterfaceStatusList &); + void ChangeStatus(int newStatus); + + BPopUpMenu fPopup; + BBitmap *fBitmaps[kStatusCount]; +}; + +#endif From hugosantos at mail.berlios.de Tue Apr 3 07:47:07 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Tue, 3 Apr 2007 07:47:07 +0200 Subject: [Haiku-commits] r20524 - haiku/trunk/src/servers/net Message-ID: <200704030547.l335l7uq018347@sheep.berlios.de> Author: hugosantos Date: 2007-04-03 07:47:00 +0200 (Tue, 03 Apr 2007) New Revision: 20524 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20524&view=rev Modified: haiku/trunk/src/servers/net/NetServer.cpp haiku/trunk/src/servers/net/StatusReplicant.cpp Log: tiny cleanups Modified: haiku/trunk/src/servers/net/NetServer.cpp =================================================================== --- haiku/trunk/src/servers/net/NetServer.cpp 2007-04-03 05:38:45 UTC (rev 20523) +++ haiku/trunk/src/servers/net/NetServer.cpp 2007-04-03 05:47:00 UTC (rev 20524) @@ -366,8 +366,8 @@ case kRegisterStatusReplicant: { - message->FindMessenger("messenger", &fStatusMessenger); - _UpdateReplicantStatus(); + if (message->FindMessenger("messenger", &fStatusMessenger) == B_OK) + _UpdateReplicantStatus(); break; } Modified: haiku/trunk/src/servers/net/StatusReplicant.cpp =================================================================== --- haiku/trunk/src/servers/net/StatusReplicant.cpp 2007-04-03 05:38:45 UTC (rev 20523) +++ haiku/trunk/src/servers/net/StatusReplicant.cpp 2007-04-03 05:47:00 UTC (rev 20524) @@ -181,13 +181,13 @@ if (status != kStatusConnected && status != kStatusLinkNoConfig) return; + if (strlen(device) > IF_NAMESIZE) + return; + int sock = socket(AF_INET, SOCK_DGRAM, 0); if (sock < 0) return; - if (strlen(device) > IF_NAMESIZE) - return; - ifreq request; memset(&request, 0, sizeof(request)); strcpy(request.ifr_name, device); From hugosantos at mail.berlios.de Tue Apr 3 07:59:22 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Tue, 3 Apr 2007 07:59:22 +0200 Subject: [Haiku-commits] r20525 - haiku/trunk/src/servers/net Message-ID: <200704030559.l335xMjs018889@sheep.berlios.de> Author: hugosantos Date: 2007-04-03 07:59:16 +0200 (Tue, 03 Apr 2007) New Revision: 20525 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20525&view=rev Modified: haiku/trunk/src/servers/net/NetServer.cpp Log: also update configured devices' status, but ignore the loopback interface. Modified: haiku/trunk/src/servers/net/NetServer.cpp =================================================================== --- haiku/trunk/src/servers/net/NetServer.cpp 2007-04-03 05:47:00 UTC (rev 20524) +++ haiku/trunk/src/servers/net/NetServer.cpp 2007-04-03 05:59:16 UTC (rev 20525) @@ -873,7 +873,8 @@ } } - _ConfigureInterface(socket, interface); + if (_ConfigureInterface(socket, interface) == B_OK) + _UpdateDeviceStatus(device, kStatusConnected); } } @@ -962,6 +963,9 @@ void NetServer::_UpdateDeviceStatus(const char *device, int status) { + if (strcmp(device, "loop") == 0) + return; + StatusMap::iterator it = fStatusMap.find(device); if (it != fStatusMap.end() && it->second == status) return; From hugosantos at mail.berlios.de Tue Apr 3 09:00:04 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Tue, 3 Apr 2007 09:00:04 +0200 Subject: [Haiku-commits] r20526 - haiku/trunk/src/servers/net Message-ID: <200704030700.l33704qJ021942@sheep.berlios.de> Author: hugosantos Date: 2007-04-03 08:59:55 +0200 (Tue, 03 Apr 2007) New Revision: 20526 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20526&view=rev Modified: haiku/trunk/src/servers/net/StatusReplicant.cpp Log: small gcc 4 compilation fix Modified: haiku/trunk/src/servers/net/StatusReplicant.cpp =================================================================== --- haiku/trunk/src/servers/net/StatusReplicant.cpp 2007-04-03 05:59:16 UTC (rev 20525) +++ haiku/trunk/src/servers/net/StatusReplicant.cpp 2007-04-03 06:59:55 UTC (rev 20526) @@ -192,7 +192,7 @@ memset(&request, 0, sizeof(request)); strcpy(request.ifr_name, device); - string text = device; + std::string text = device; text += " information:\n"; size_t boldLength = text.size(); From hugosantos at mail.berlios.de Tue Apr 3 09:00:13 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Tue, 3 Apr 2007 09:00:13 +0200 Subject: [Haiku-commits] r20527 - haiku/trunk/src/add-ons/kernel/network/protocols/tcp Message-ID: <200704030700.l3370DhQ021991@sheep.berlios.de> Author: hugosantos Date: 2007-04-03 09:00:04 +0200 (Tue, 03 Apr 2007) New Revision: 20527 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20527&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h Log: fixed a potential problem in TCP's accept() with the init'ing of new connections' MSS Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-03 06:59:55 UTC (rev 20526) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-03 07:00:04 UTC (rev 20527) @@ -236,8 +236,7 @@ return status; } - fReceiveMaxSegmentSize = next->module->get_mtu(next, (sockaddr *)address) - - sizeof(tcp_header); + fReceiveMaxSegmentSize = _GetMSS(address); // Compute the window shift we advertise to our peer - if it doesn't support // this option, this will be reset to 0 (when its SYN is received) @@ -597,7 +596,7 @@ endpoint->fReceiveQueue.SetInitialSequence(segment.sequence + 1); endpoint->fState = SYNCHRONIZE_RECEIVED; endpoint->fAcceptSemaphore = fAcceptSemaphore; - endpoint->fReceiveMaxSegmentSize = endpoint->fRoute->mtu - 40; + endpoint->fReceiveMaxSegmentSize = _GetMSS((sockaddr *)&newSocket->peer); // 40 bytes for IP and TCP header without any options // TODO: make this depending on the RTF_LOCAL flag? endpoint->fReceiveNext = segment.sequence + 1; @@ -1208,6 +1207,13 @@ } +int +TCPEndpoint::_GetMSS(const sockaddr *address) const +{ + return next->module->get_mtu(next, (sockaddr *)address) - sizeof(tcp_header); +} + + // #pragma mark - timer Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h 2007-04-03 06:59:55 UTC (rev 20526) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h 2007-04-03 07:00:04 UTC (rev 20527) @@ -65,6 +65,7 @@ bool _ShouldSendSegment(tcp_segment_header &segment, uint32 length, bool outstandingAcknowledge); status_t _SendQueued(bool force = false); + int _GetMSS(const struct sockaddr *) const; static void _TimeWaitTimer(net_timer *timer, void *data); static void _RetransmitTimer(net_timer *timer, void *data); From stippi at mail.berlios.de Tue Apr 3 12:39:41 2007 From: stippi at mail.berlios.de (stippi at BerliOS) Date: Tue, 3 Apr 2007 12:39:41 +0200 Subject: [Haiku-commits] r20528 - haiku/trunk/src/servers/net Message-ID: <200704031039.l33AdfH7016839@sheep.berlios.de> Author: stippi Date: 2007-04-03 12:39:38 +0200 (Tue, 03 Apr 2007) New Revision: 20528 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20528&view=rev Added: haiku/trunk/src/servers/net/NetworkStatusIcons.h haiku/trunk/src/servers/net/NetworkStatusIcons.rdef Log: * created icons to inform about network connectivity status Added: haiku/trunk/src/servers/net/NetworkStatusIcons.h =================================================================== --- haiku/trunk/src/servers/net/NetworkStatusIcons.h 2007-04-03 07:00:04 UTC (rev 20527) +++ haiku/trunk/src/servers/net/NetworkStatusIcons.h 2007-04-03 10:39:38 UTC (rev 20528) @@ -0,0 +1,15 @@ +/* + * Copyright 2007, Haiku. All rights reserved. + * Distributed under the terms of the MIT License. + */ +#ifndef NETWORK_STATUS_ICONS_H +#define NETWORK_STATUS_ICONS_H + +enum { + kNetworkStatusNoDevice = 1000, + kNetworkStatusNoConnection = 1001, + kNetworkStatusNoSettings = 1002, + kNetworkStatusReady = 1003 +}; + +#endif // NETWORK_STATUS_ICONS_H Added: haiku/trunk/src/servers/net/NetworkStatusIcons.rdef =================================================================== --- haiku/trunk/src/servers/net/NetworkStatusIcons.rdef 2007-04-03 07:00:04 UTC (rev 20527) +++ haiku/trunk/src/servers/net/NetworkStatusIcons.rdef 2007-04-03 10:39:38 UTC (rev 20528) @@ -0,0 +1,95 @@ +/* + * Copyright 2007, Haiku. All rights reserved. + * Distributed under the terms of the MIT License. + * + * Authors: + * Stephan A?mus + */ + +#include "NetworkStatusIcons.h" + +resource(kNetworkStatusNoDevice) #'VICN' array { + $"6E63696608050005B8020016023A692E36692FBA2ECD3E2ECD4B89A449631800" + $"5CFF8305E7020106023C00000000000000003C00004680004680000029B6FFFF" + $"035492020106023C00000000000000003C0000468000468000009FF699FF049A" + $"4304016E0200060238DB5A38CCBABACCBA3ADB5A47AF864AF7C900FF8875FFFF" + $"05050B0A044C60516060505C4E02043334BD6E34B7B534263926BBDC26BE0F33" + $"3EB7B53EBD6E3E403940BE0F40BBDC0A06513A5A3D5A504C5E425842440A044C" + $"484C5E425842440A04513A5A3D4C4842440A044C485A3D5A504C5E02042E22BB" + $"3722B5F022222E22B5F022BB372E3AB5F03ABB373A3A2E3ABB373AB5F00608BF" + $"DBB506B560B506B560B443B639222E22B75822BAB3B718BD20B52EBC80B718BD" + $"20283628322A34263024302E2828282A2826060CA2EBAF2E28B9863226342830" + $"2E302C303036323436BBB3BC32BBB3BC32BCB7BB523A2E3ABA063AB668B9EEB3" + $"FDBBE9B493B9EEB3FD2E2430260614BFDDAFABE82E22B90C22B72B22B506B560" + $"B5E6B468B506B56028282826282A242E30283226302A3436B718BD20B718BD20" + $"B78FBD462E3AB80F3AB9C53ABBB3BC32BADCBCECBBB3BC3234363632302E3030" + $"302C34283226B953282E30262E24B9EEB3FDB9EEB3FDB980B3DD0A042450245C" + $"305C3050090A06020001000A000202061001178400040A010103000A03010400" + $"0A020105000A040109000A05020708000A00010A1001178802040A07010A00" +}; + +resource(kNetworkStatusNoConnection) #'VICN' array { + $"6E63696608050005B8020016023A692E36692FBA2ECD3E2ECD4B89A449631800" + $"5CFF8305E7020106023C00000000000000003C00004680004680000029B6FFFF" + $"035492020106023C00000000000000003C0000468000468000009FF699FF049A" + $"4304016E0200060238DB5A38CCBABACCBA3ADB5A47AF864AF7C900FFF375FFFF" + $"A4060D0A044C60516060505C4E02043334BD6E34B7B534263926BBDC26BE0F33" + $"3EB7B53EBD6E3E403940BE0F40BBDC0A06513A5A3D5A504C5E425842440A044C" + $"484C5E425842440A04513A5A3D4C4842440A044C485A3D5A504C5E04032FBED8" + $"BDCDBED8BDCDBFD0BD34423642BC9342323A3204033E404A3246324A32C179BA" + $"E4C06BBA73C0E9BAE4C06B02042E22BB3722B5F022222E22B5F022BB372E3AB5" + $"F03ABB373A3A2E3ABB373AB5F00608BFDBB506B560B506B560B443B639222E22" + $"B75822BAB3B718BD20B52EBC80B718BD20283628322A34263024302E2828282A" + $"2826060CA2EBAF2E28B98632263428302E302C303036323436BBB3BC32BBB3BC" + $"32BCB7BB523A2E3ABA063AB668B9EEB3FDBBE9B493B9EEB3FD2E2430260614BF" + $"DDAFABE82E22B90C22B72B22B506B560B5E6B468B506B56028282826282A242E" + $"30283226302A3436B718BD20B718BD20B78FBD462E3AB80F3AB9C53ABBB3BC32" + $"BADCBCECBBB3BC3234363632302E3030302C34283226B953282E30262E24B9EE" + $"B3FDB9EEB3FDB980B3DD0A0324502A5C3050090A06020001000A000406020807" + $"1001178400040A010103000A030104000A020105000A04010B000A0502090A00" + $"0A00010C1001178802040A07010C00" +}; + +resource(kNetworkStatusNoSettings) #'VICN' array { + $"6E63696608050005B8020016023A692E36692FBA2ECD3E2ECD4B89A449631800" + $"5CFF8305E7020106023C00000000000000003C00004680004680000029B6FFFF" + $"035492020106023C00000000000000003C0000468000468000009FF699FF049A" + $"4304016E0200060238DB5A38CCBABACCBA3ADB5A47AF864AF7C900FFF375FFFF" + $"A4060C0A044C60516060505C4E02043334BD6E34B7B534263926BBDC26BE0F33" + $"3EB7B53EBD6E3E403940BE0F40BBDC0A06513A5A3D5A504C5E425842440A044C" + $"484C5E425842440A04513A5A3D4C4842440A044C485A3D5A504C5E0404BE3A32" + $"42364232423C3246323E324A404A02042E22BB3722B5F022222E22B5F022BB37" + $"2E3AB5F03ABB373A3A2E3ABB373AB5F00608BFDBB506B560B506B560B443B639" + $"222E22B75822BAB3B718BD20B52EBC80B718BD20283628322A34263024302E28" + $"28282A2826060CA2EBAF2E28B98632263428302E302C303036323436BBB3BC32" + $"BBB3BC32BCB7BB523A2E3ABA063AB668B9EEB3FDBBE9B493B9EEB3FD2E243026" + $"0614BFDDAFABE82E22B90C22B72B22B506B560B5E6B468B506B5602828282628" + $"2A242E30283226302A3436B718BD20B718BD20B78FBD462E3AB80F3AB9C53ABB" + $"B3BC32BADCBCECBBB3BC3234363632302E3030302C34283226B953282E30262E" + $"24B9EEB3FDB9EEB3FDB980B3DD0A0324502A5C3050090A06020001000A000306" + $"02071001178400040A010103000A030104000A020105000A04010A000A050208" + $"09000A00010B1001178802040A07010B00" +}; + +resource(kNetworkStatusReady) #'VICN' array { + $"6E63696608050005B8020016023A692E36692FBA2ECD3E2ECD4B89A449631800" + $"5CFF8305E7020106023C00000000000000003C00004680004680000029B6FFFF" + $"035492020106023C00000000000000003C0000468000468000009FF699FF049A" + $"4304016E020006023959B6382F60BA2F603B59B647C1424B11D30056FF22FF05" + $"D0050C0A044C60516060505C4E02043334BD6E34B7B534263926BBDC26BE0F33" + $"3EB7B53EBD6E3E403940BE0F40BBDC0A06513A5A3D5A504C5E425842440A044C" + $"484C5E425842440A04513A5A3D4C4842440A044C485A3D5A504C5E0404BE404A" + $"3246324A323E4236423C42323A3202042E22BB3722B5F022222E22B5F022BB37" + $"2E3AB5F03ABB373A3A2E3ABB373AB5F00608BFDBB506B560B506B560B443B639" + $"222E22B75822BAB3B718BD20B52EBC80B718BD20283628322A34263024302E28" + $"28282A2826060CA2EBAF2E28B98632263428302E302C303036323436BBB3BC32" + $"BBB3BC32BCB7BB523A2E3ABA063AB668B9EEB3FDBBE9B493B9EEB3FD2E243026" + $"0614BFDDAFABE82E22B90C22B72B22B506B560B5E6B468B506B5602828282628" + $"2A242E30283226302A3436B718BD20B718BD20B78FBD462E3AB80F3AB9C53ABB" + $"B3BC32BADCBCECBBB3BC3234363632302E3030302C34283226B953282E30262E" + $"24B9EEB3FDB9EEB3FDB980B3DD02042A50B84D50B5AA50B49756B497C732B497" + $"C9D52A5CB5AA5CB84D5C305630C9D530C732090A06020001000A000306020710" + $"01178400040A010103000A030104000A020105000A04010A000A05020809000A" + $"00010B1001178800040A07010B00" +}; + From stippi at mail.berlios.de Tue Apr 3 12:42:48 2007 From: stippi at mail.berlios.de (stippi at BerliOS) Date: Tue, 3 Apr 2007 12:42:48 +0200 Subject: [Haiku-commits] r20529 - haiku/trunk/src/servers/net Message-ID: <200704031042.l33AgmXH021597@sheep.berlios.de> Author: stippi Date: 2007-04-03 12:42:48 +0200 (Tue, 03 Apr 2007) New Revision: 20529 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20529&view=rev Modified: haiku/trunk/src/servers/net/NetworkStatusIcons.h haiku/trunk/src/servers/net/NetworkStatusIcons.rdef Log: * added icon for "connecting" status Modified: haiku/trunk/src/servers/net/NetworkStatusIcons.h =================================================================== --- haiku/trunk/src/servers/net/NetworkStatusIcons.h 2007-04-03 10:39:38 UTC (rev 20528) +++ haiku/trunk/src/servers/net/NetworkStatusIcons.h 2007-04-03 10:42:48 UTC (rev 20529) @@ -9,7 +9,8 @@ kNetworkStatusNoDevice = 1000, kNetworkStatusNoConnection = 1001, kNetworkStatusNoSettings = 1002, - kNetworkStatusReady = 1003 + kNetworkStatusConnecting = 1003, + kNetworkStatusReady = 1004 }; #endif // NETWORK_STATUS_ICONS_H Modified: haiku/trunk/src/servers/net/NetworkStatusIcons.rdef =================================================================== --- haiku/trunk/src/servers/net/NetworkStatusIcons.rdef 2007-04-03 10:39:38 UTC (rev 20528) +++ haiku/trunk/src/servers/net/NetworkStatusIcons.rdef 2007-04-03 10:42:48 UTC (rev 20529) @@ -71,6 +71,28 @@ $"09000A00010B1001178802040A07010B00" }; +resource(kNetworkStatusConnecting) #'VICN' array { + $"6E63696608050005B8020016023A692E36692FBA2ECD3E2ECD4B89A449631800" + $"5CFF8305E7020106023C00000000000000003C00004680004680000029B6FFFF" + $"035492020106023C00000000000000003C0000468000468000009FF699FF049A" + $"4304016E020016023959B6382F60BA2F603B59B647C1424B11D300DCFFAC0C0A" + $"044C60516060505C4E02043334BD6E34B7B534263926BBDC26BE0F333EB7B53E" + $"BD6E3E403940BE0F40BBDC0A06513A5A3D5A504C5E425842440A044C484C5E42" + $"5842440A04513A5A3D4C4842440A044C485A3D5A504C5E0404BE404A3246324A" + $"323E4236423C42323A3202042E22BB3722B5F022222E22B5F022BB372E3AB5F0" + $"3ABB373A3A2E3ABB373AB5F00608BFDBB506B560B506B560B443B639222E22B7" + $"5822BAB3B718BD20B52EBC80B718BD20283628322A34263024302E2828282A28" + $"26060CA2EBAF2E28B98632263428302E302C303036323436BBB3BC32BBB3BC32" + $"BCB7BB523A2E3ABA063AB668B9EEB3FDBBE9B493B9EEB3FD2E2430260614BFDD" + $"AFABE82E22B90C22B72B22B506B560B5E6B468B506B56028282826282A242E30" + $"283226302A3436B718BD20B718BD20B78FBD462E3AB80F3AB9C53ABBB3BC32BA" + $"DCBCECBBB3BC3234363632302E3030302C34283226B953282E30262E24B9EEB3" + $"FDB9EEB3FDB980B3DD02042A50B84D50B5AA50B49756B497C732B497C9D52A5C" + $"B5AA5CB84D5C305630C9D530C732090A06020001000A00030602071001178400" + $"040A010103000A030104000A020105000A04010A000A05020809000A00010B10" + $"01178800040A07010B00" +}; + resource(kNetworkStatusReady) #'VICN' array { $"6E63696608050005B8020016023A692E36692FBA2ECD3E2ECD4B89A449631800" $"5CFF8305E7020106023C00000000000000003C00004680004680000029B6FFFF" From axeld at mail.berlios.de Tue Apr 3 13:23:38 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Tue, 3 Apr 2007 13:23:38 +0200 Subject: [Haiku-commits] r20530 - haiku/trunk/src/system/kernel/vm Message-ID: <200704031123.l33BNcku032153@sheep.berlios.de> Author: axeld Date: 2007-04-03 13:23:37 +0200 (Tue, 03 Apr 2007) New Revision: 20530 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20530&view=rev Modified: haiku/trunk/src/system/kernel/vm/vm.cpp haiku/trunk/src/system/kernel/vm/vm_cache.c Log: * The test for existing mappings in vm_remove_consumer() was a bit too aggressive; if the page is currently copied, the source page still has mappings. * vm_copy_on_write_area() did not set the cache type for the upper cache. Modified: haiku/trunk/src/system/kernel/vm/vm.cpp =================================================================== --- haiku/trunk/src/system/kernel/vm/vm.cpp 2007-04-03 10:42:48 UTC (rev 20529) +++ haiku/trunk/src/system/kernel/vm/vm.cpp 2007-04-03 11:23:37 UTC (rev 20530) @@ -1586,6 +1586,7 @@ // we need to hold the cache_ref lock when we want to switch its cache mutex_lock(&lowerCacheRef->lock); + upperCache->type = CACHE_TYPE_RAM; upperCache->temporary = 1; upperCache->scan_skip = lowerCache->scan_skip; upperCache->virtual_base = lowerCache->virtual_base; Modified: haiku/trunk/src/system/kernel/vm/vm_cache.c =================================================================== --- haiku/trunk/src/system/kernel/vm/vm_cache.c 2007-04-03 10:42:48 UTC (rev 20529) +++ haiku/trunk/src/system/kernel/vm/vm_cache.c 2007-04-03 11:23:37 UTC (rev 20530) @@ -528,16 +528,22 @@ cache, cacheRef->ref_count, consumer)); for (page = cache->page_list; page != NULL; page = nextPage) { + vm_page *consumerPage; nextPage = page->cache_next; - if (vm_cache_lookup_page(consumerRef, - (off_t)page->cache_offset << PAGE_SHIFT) == NULL) { - // the page already is not yet in the consumer cache - move it upwards + consumerPage = vm_cache_lookup_page(consumerRef, + (off_t)page->cache_offset << PAGE_SHIFT); + if (consumerPage == NULL) { + // the page already is not yet in the consumer cache - move + // it upwards vm_cache_remove_page(cacheRef, page); vm_cache_insert_page(consumerRef, page, (off_t)page->cache_offset << PAGE_SHIFT); - } else if (page->mappings != 0 || page->wired_count != 0) - panic("page %p has still mappings!", page); + } else if (consumerPage->state != PAGE_STATE_BUSY + && (page->mappings != 0 || page->wired_count != 0)) { + panic("page %p has still mappings (consumer cache %p)!", + page, consumerRef); + } } newSource = cache->source; From axeld at mail.berlios.de Tue Apr 3 13:55:03 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Tue, 3 Apr 2007 13:55:03 +0200 Subject: [Haiku-commits] r20531 - haiku/trunk/src/servers/net Message-ID: <200704031155.l33Bt34j024780@sheep.berlios.de> Author: axeld Date: 2007-04-03 13:55:03 +0200 (Tue, 03 Apr 2007) New Revision: 20531 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20531&view=rev Modified: haiku/trunk/src/servers/net/Jamfile haiku/trunk/src/servers/net/NetServer.cpp haiku/trunk/src/servers/net/StatusReplicant.cpp haiku/trunk/src/servers/net/StatusReplicant.h Log: * Implemented loading icons from resources - doesn't seem to work yet, though. * Fixed leaking menu items in StatusReplicant::_PrepareMenu(). * Renamed private methods to have an underscore prefix. * Some minor style cleanup. Modified: haiku/trunk/src/servers/net/Jamfile =================================================================== --- haiku/trunk/src/servers/net/Jamfile 2007-04-03 11:23:37 UTC (rev 20530) +++ haiku/trunk/src/servers/net/Jamfile 2007-04-03 11:55:03 UTC (rev 20531) @@ -1,6 +1,7 @@ SubDir HAIKU_TOP src servers net ; UsePrivateHeaders app net ; +UseLibraryHeaders icon ; #UseHeaders [ FDirName $(HAIKU_TOP) src add-ons kernel network ppp shared libppp headers ] ; #UseHeaders [ FDirName $(HAIKU_TOP) src add-ons kernel network ppp shared libkernelppp headers ] ; Modified: haiku/trunk/src/servers/net/NetServer.cpp =================================================================== --- haiku/trunk/src/servers/net/NetServer.cpp 2007-04-03 11:23:37 UTC (rev 20530) +++ haiku/trunk/src/servers/net/NetServer.cpp 2007-04-03 11:55:03 UTC (rev 20531) @@ -990,8 +990,8 @@ if (it->second > prevaling) prevaling = it->second; - message.AddString("intf:name", it->first.c_str()); - message.AddInt32("intf:status", it->second); + message.AddString("interface:name", it->first.c_str()); + message.AddInt32("interface:status", it->second); } message.AddInt32("net:status", prevaling); Modified: haiku/trunk/src/servers/net/StatusReplicant.cpp =================================================================== --- haiku/trunk/src/servers/net/StatusReplicant.cpp 2007-04-03 11:23:37 UTC (rev 20530) +++ haiku/trunk/src/servers/net/StatusReplicant.cpp 2007-04-03 11:55:03 UTC (rev 20531) @@ -6,19 +6,27 @@ * Hugo Santos, hugosantos at gmail.com */ -#include "NetServer.h" + #include "StatusReplicant.h" +#include "NetServer.h" +#include "NetworkStatusIcons.h" + #include +#include +#include +#include #include #include #include +#include #include #include #include #include + const char *kStatusReplicant = "NetStatusView"; static const uint32 kShowConfiguration = 'shcf'; @@ -42,7 +50,6 @@ { NULL } }; - static const char *kStatusDescriptions[] = { "Unknown", "No Link", @@ -54,22 +61,25 @@ StatusReplicant::StatusReplicant() : BView(BRect(0, 0, 15, 15), kStatusReplicant, B_FOLLOW_ALL, 0), - fPopup("", false, false) + fPopUp("", false, false) { + _Init(); } StatusReplicant::StatusReplicant(BMessage *message) - : BView(message), fPopup("", false, false) + : BView(message), + fPopUp("", false, false) { - // TODO: Load status bitmaps from resources - for (int i = 0; i < kStatusCount; i++) - fBitmaps[i] = NULL; + _Init(); } StatusReplicant::~StatusReplicant() { + for (int32 i = 0; i < kStatusCount; i++) { + delete fBitmaps[i]; + } } @@ -78,6 +88,7 @@ { if (validate_instantiation(data, kStatusReplicant)) return new StatusReplicant(data); + return NULL; } @@ -102,8 +113,8 @@ // TODO: Remove myself from Deskbar } - ChangeStatus(kStatusUnknown); - PrepareMenu(InterfaceStatusList()); + _ChangeStatus(kStatusUnknown); + _PrepareMenu(InterfaceStatusList()); } @@ -111,15 +122,16 @@ StatusReplicant::MessageReceived(BMessage *message) { switch (message->what) { - case kStatusUpdate: - UpdateFromMessage(message); - break; - case kShowConfiguration: - ShowConfiguration(message); - break; - default: - BView::MessageReceived(message); - break; + case kStatusUpdate: + _UpdateFromMessage(message); + break; + case kShowConfiguration: + _ShowConfiguration(message); + break; + + default: + BView::MessageReceived(message); + break; } } @@ -133,49 +145,79 @@ GetMouse(&where, &buttons, true); where = ConvertToScreen(point); - fPopup.SetTargetForItems(this); - fPopup.Go(where, true, true); + fPopUp.SetTargetForItems(this); + fPopUp.Go(where, true, true); } void -StatusReplicant::UpdateFromMessage(BMessage *message) +StatusReplicant::_Init() { - int32 newStatus, intfStatus; + // Load status bitmaps from resources + BResources* resources = BApplication::AppResources(); + + for (int i = 0; i < kStatusCount; i++) { + fBitmaps[i] = NULL; + + if (resources != NULL) { + const void* data = NULL; + size_t size; + data = resources->LoadResource(B_VECTOR_ICON_TYPE, + kNetworkStatusNoDevice + i, &size); + if (data != NULL) { + BBitmap* icon = new BBitmap(Bounds(), B_RGB32); + if (icon->InitCheck() == B_OK + && BIconUtils::GetVectorIcon((const uint8 *)data, + size, icon) == B_OK) { + fBitmaps[i] = icon; + } else + delete icon; + + free((void*)data); + } + } + } +} + + +void +StatusReplicant::_UpdateFromMessage(BMessage *message) +{ + int32 newStatus; if (message->FindInt32("net:status", &newStatus) != B_OK - || newStatus < 0 || newStatus >= kStatusCount) + || newStatus < 0 || newStatus >= kStatusCount) return; InterfaceStatusList status; - int index = 0; - while (message->FindInt32("intf:status", index, &intfStatus) == B_OK) { - if (intfStatus < 0 || intfStatus >= kStatusCount) + int32 interfaceStatus; + + for (uint32 index = 0; message->FindInt32("interface:status", index, + &interfaceStatus) == B_OK; index++) { + if (interfaceStatus < 0 || interfaceStatus >= kStatusCount) break; const char *name; - if (message->FindString("intf:name", index, &name) != B_OK) + if (message->FindString("interface:name", index, &name) != B_OK) break; - status.push_back(InterfaceStatus(name, intfStatus)); - - index++; + status.push_back(InterfaceStatus(name, interfaceStatus)); } - ChangeStatus(newStatus); - PrepareMenu(status); + _ChangeStatus(newStatus); + _PrepareMenu(status); } void -StatusReplicant::ShowConfiguration(BMessage *message) +StatusReplicant::_ShowConfiguration(BMessage *message) { const char *device; - if (message->FindString("intf:name", &device) != B_OK) + if (message->FindString("interface:name", &device) != B_OK) return; int32 status; - if (message->FindInt32("intf:status", &status) != B_OK) + if (message->FindInt32("interface:status", &status) != B_OK) return; if (status != kStatusConnected && status != kStatusLinkNoConfig) @@ -233,13 +275,13 @@ void -StatusReplicant::PrepareMenu(const InterfaceStatusList &status) +StatusReplicant::_PrepareMenu(const InterfaceStatusList &status) { - while (fPopup.RemoveItem((int32)0)); + fPopUp.RemoveItems(0, fPopUp.CountItems(), true); if (status.empty()) { - fPopup.AddItem(new BMenuItem("No interfaces available.", NULL)); - fPopup.ItemAt(0)->SetEnabled(false); + fPopUp.AddItem(new BMenuItem("No interfaces available.", NULL)); + fPopUp.ItemAt(0)->SetEnabled(false); } else { for (InterfaceStatusList::const_iterator i = status.begin(); i != status.end(); ++i) { @@ -248,21 +290,21 @@ label += kStatusDescriptions[i->second]; BMessage *message = new BMessage(kShowConfiguration); - message->AddString("intf:name", i->first.c_str()); - message->AddInt32("intf:status", i->second); + message->AddString("interface:name", i->first.c_str()); + message->AddInt32("interface:status", i->second); BMenuItem *item = new BMenuItem(label.c_str(), message); if (i->second != kStatusConnected && i->second != kStatusLinkNoConfig) item->SetEnabled(false); - fPopup.AddItem(item); + fPopUp.AddItem(item); } } } void -StatusReplicant::ChangeStatus(int newStatus) +StatusReplicant::_ChangeStatus(int newStatus) { if (fBitmaps[newStatus]) { SetViewColor(Parent()->ViewColor()); Modified: haiku/trunk/src/servers/net/StatusReplicant.h =================================================================== --- haiku/trunk/src/servers/net/StatusReplicant.h 2007-04-03 11:23:37 UTC (rev 20530) +++ haiku/trunk/src/servers/net/StatusReplicant.h 2007-04-03 11:55:03 UTC (rev 20531) @@ -5,10 +5,10 @@ * Authors: * Hugo Santos, hugosantos at gmail.com */ - #ifndef _STATUS_REPLICANT_H #define _STATUS_REPLICANT_H + #include "NetServer.h" #include @@ -18,35 +18,38 @@ #include #include + static const uint32 kRegisterStatusReplicant = 'rnsr'; static const uint32 kStatusUpdate = 'stup'; extern const char *kStatusReplicant; + class StatusReplicant : public BView { -public: - StatusReplicant(); - StatusReplicant(BMessage *); - virtual ~StatusReplicant(); + public: + StatusReplicant(); + StatusReplicant(BMessage *archive); + virtual ~StatusReplicant(); - static StatusReplicant *Instantiate(BMessage *); - status_t Archive(BMessage *, bool deep) const; + static StatusReplicant *Instantiate(BMessage *archive); + status_t Archive(BMessage *archive, bool deep) const; - void AttachedToWindow(); - void MessageReceived(BMessage *); + void AttachedToWindow(); + void MessageReceived(BMessage *message); - void MouseDown(BPoint point); + void MouseDown(BPoint point); -private: - typedef std::pair InterfaceStatus; - typedef std::vector InterfaceStatusList; + private: + typedef std::pair InterfaceStatus; + typedef std::vector InterfaceStatusList; - void UpdateFromMessage(BMessage *); - void ShowConfiguration(BMessage *); - void PrepareMenu(const InterfaceStatusList &); - void ChangeStatus(int newStatus); + void _Init(); + void _UpdateFromMessage(BMessage *message); + void _ShowConfiguration(BMessage *message); + void _PrepareMenu(const InterfaceStatusList &list); + void _ChangeStatus(int newStatus); - BPopUpMenu fPopup; - BBitmap *fBitmaps[kStatusCount]; + BPopUpMenu fPopUp; + BBitmap *fBitmaps[kStatusCount]; }; -#endif +#endif // _STATUS_REPLICANT_H From axeld at mail.berlios.de Tue Apr 3 14:24:33 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Tue, 3 Apr 2007 14:24:33 +0200 Subject: [Haiku-commits] r20532 - haiku/trunk/src/servers/net Message-ID: <200704031224.l33COXYg026844@sheep.berlios.de> Author: axeld Date: 2007-04-03 14:24:32 +0200 (Tue, 03 Apr 2007) New Revision: 20532 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20532&view=rev Modified: haiku/trunk/src/servers/net/Jamfile haiku/trunk/src/servers/net/NetServer.cpp haiku/trunk/src/servers/net/StatusReplicant.cpp haiku/trunk/src/servers/net/StatusReplicant.h Log: The network status icons are now correctly read from the resources (I even forgot to add them to the server before :-)). Modified: haiku/trunk/src/servers/net/Jamfile =================================================================== --- haiku/trunk/src/servers/net/Jamfile 2007-04-03 11:55:03 UTC (rev 20531) +++ haiku/trunk/src/servers/net/Jamfile 2007-04-03 12:24:32 UTC (rev 20532) @@ -7,7 +7,7 @@ #UseHeaders [ FDirName $(HAIKU_TOP) src add-ons kernel network ppp shared libkernelppp headers ] ; #UseHeaders [ FDirName $(HAIKU_TOP) src tests kits net DialUpPreflet ] ; -AddResources net_server : net_server.rdef ; +AddResources net_server : net_server.rdef NetworkStatusIcons.rdef ; Server net_server : NetServer.cpp Modified: haiku/trunk/src/servers/net/NetServer.cpp =================================================================== --- haiku/trunk/src/servers/net/NetServer.cpp 2007-04-03 11:55:03 UTC (rev 20531) +++ haiku/trunk/src/servers/net/NetServer.cpp 2007-04-03 12:24:32 UTC (rev 20532) @@ -986,7 +986,7 @@ BMessage message(kStatusUpdate); for (StatusMap::iterator it = fStatusMap.begin(); - it != fStatusMap.end(); ++it) { + it != fStatusMap.end(); ++it) { if (it->second > prevaling) prevaling = it->second; Modified: haiku/trunk/src/servers/net/StatusReplicant.cpp =================================================================== --- haiku/trunk/src/servers/net/StatusReplicant.cpp 2007-04-03 11:55:03 UTC (rev 20531) +++ haiku/trunk/src/servers/net/StatusReplicant.cpp 2007-04-03 12:24:32 UTC (rev 20532) @@ -30,12 +30,12 @@ const char *kStatusReplicant = "NetStatusView"; static const uint32 kShowConfiguration = 'shcf'; -static const uint8 kStatusColors[kStatusCount][3] = { - { 0, 0, 0 }, // Unknown - { 255, 0, 0 }, // NoLink - { 0, 0, 255 }, // LinkNoConfig - { 0, 255, 0 }, // Connected - { 255, 255, 0 }, // Preparing +static const rgb_color kStatusColors[kStatusCount] = { + { 0, 0, 0 }, // Unknown + { 255, 0, 0 }, // NoLink + { 0, 0, 255 }, // LinkNoConfig + { 0, 255, 0 }, // Connected + { 255, 255, 0 }, // Preparing }; struct information_entry { @@ -59,17 +59,36 @@ }; +static status_t +our_image(image_info *image) +{ + int32 cookie = 0; + while (get_next_image_info(B_CURRENT_TEAM, &cookie, image) == B_OK) { + if ((char *)our_image >= (char *)image->text && + (char *)our_image <= (char *)image->text + image->text_size) + return B_OK; + } + + return B_ERROR; +} + + +// #pragma mark - + + StatusReplicant::StatusReplicant() - : BView(BRect(0, 0, 15, 15), kStatusReplicant, B_FOLLOW_ALL, 0), - fPopUp("", false, false) + : BView(BRect(0, 0, 15, 15), kStatusReplicant, B_FOLLOW_ALL, B_WILL_DRAW), + fPopUp("", false, false), + fStatus(kStatusUnknown) { - _Init(); + _Init(false); } StatusReplicant::StatusReplicant(BMessage *message) : BView(message), - fPopUp("", false, false) + fPopUp("", false, false), + fStatus(kStatusUnknown) { _Init(); } @@ -137,6 +156,18 @@ void +StatusReplicant::Draw(BRect updateRect) +{ + if (fBitmaps[fStatus] == NULL) + return; + + SetDrawingMode(B_OP_ALPHA); + DrawBitmap(fBitmaps[fStatus]); + SetDrawingMode(B_OP_COPY); +} + + +void StatusReplicant::MouseDown(BPoint point) { uint32 buttons; @@ -151,31 +182,42 @@ void -StatusReplicant::_Init() +StatusReplicant::_Init(bool isReplicant) { // Load status bitmaps from resources - BResources* resources = BApplication::AppResources(); - for (int i = 0; i < kStatusCount; i++) { fBitmaps[i] = NULL; + } - if (resources != NULL) { - const void* data = NULL; - size_t size; - data = resources->LoadResource(B_VECTOR_ICON_TYPE, - kNetworkStatusNoDevice + i, &size); - if (data != NULL) { - BBitmap* icon = new BBitmap(Bounds(), B_RGB32); - if (icon->InitCheck() == B_OK - && BIconUtils::GetVectorIcon((const uint8 *)data, - size, icon) == B_OK) { - fBitmaps[i] = icon; - } else - delete icon; + if (!isReplicant) + return; - free((void*)data); - } + image_info info; + if (our_image(&info) != B_OK) + return; + + BFile file(info.name, B_READ_ONLY); + if (file.InitCheck() < B_OK) + return; + + BResources resources(&file); + if (resources.InitCheck() < B_OK) + return; + + for (int i = 0; i < kStatusCount; i++) { + const void* data = NULL; + size_t size; + data = resources.LoadResource(B_VECTOR_ICON_TYPE, + kNetworkStatusNoDevice + i, &size); + if (data != NULL) { + BBitmap* icon = new BBitmap(Bounds(), B_RGB32); + if (icon->InitCheck() == B_OK + && BIconUtils::GetVectorIcon((const uint8 *)data, + size, icon) == B_OK) { + fBitmaps[i] = icon; + } else + delete icon; } } } @@ -306,15 +348,15 @@ void StatusReplicant::_ChangeStatus(int newStatus) { - if (fBitmaps[newStatus]) { + if (fStatus == newStatus) + return; + + fStatus = newStatus; + + if (fBitmaps[newStatus]) SetViewColor(Parent()->ViewColor()); - SetViewBitmap(fBitmaps[newStatus]); - } else { - ClearViewBitmap(); - SetViewColor(kStatusColors[newStatus][0], - kStatusColors[newStatus][1], - kStatusColors[newStatus][2]); - } + else + SetViewColor(kStatusColors[newStatus]); Invalidate(); } Modified: haiku/trunk/src/servers/net/StatusReplicant.h =================================================================== --- haiku/trunk/src/servers/net/StatusReplicant.h 2007-04-03 11:55:03 UTC (rev 20531) +++ haiku/trunk/src/servers/net/StatusReplicant.h 2007-04-03 12:24:32 UTC (rev 20532) @@ -31,25 +31,26 @@ virtual ~StatusReplicant(); static StatusReplicant *Instantiate(BMessage *archive); - status_t Archive(BMessage *archive, bool deep) const; + virtual status_t Archive(BMessage *archive, bool deep) const; - void AttachedToWindow(); - void MessageReceived(BMessage *message); + virtual void AttachedToWindow(); + virtual void MessageReceived(BMessage *message); + virtual void Draw(BRect updateRect); + virtual void MouseDown(BPoint point); - void MouseDown(BPoint point); - private: typedef std::pair InterfaceStatus; typedef std::vector InterfaceStatusList; - void _Init(); + void _Init(bool isReplicant = true); void _UpdateFromMessage(BMessage *message); void _ShowConfiguration(BMessage *message); void _PrepareMenu(const InterfaceStatusList &list); void _ChangeStatus(int newStatus); - BPopUpMenu fPopUp; - BBitmap *fBitmaps[kStatusCount]; + BPopUpMenu fPopUp; + BBitmap* fBitmaps[kStatusCount]; + int32 fStatus; }; #endif // _STATUS_REPLICANT_H From hugosantos at mail.berlios.de Tue Apr 3 16:25:53 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Tue, 3 Apr 2007 16:25:53 +0200 Subject: [Haiku-commits] r20533 - haiku/trunk/src/add-ons/kernel/network/protocols/tcp Message-ID: <200704031425.l33EProS002846@sheep.berlios.de> Author: hugosantos Date: 2007-04-03 16:25:39 +0200 (Tue, 03 Apr 2007) New Revision: 20533 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20533&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp Log: cleaned up the TRACE() calls in TCPEndPoint a bit. Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-03 12:24:32 UTC (rev 20532) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-03 14:25:39 UTC (rev 20533) @@ -209,7 +209,7 @@ RecursiveLocker locker(&fLock); - TRACE((" TCP: Connect(): in state %d\n", fState)); + TRACE((" TCP:%p.Connect(): in state %d\n", this, fState)); // Can only call connect() from CLOSED or LISTEN states // otherwise endpoint is considered already connected @@ -223,7 +223,7 @@ // TODO: get a net_route_info instead! if (fRoute == NULL) { fRoute = gDatalinkModule->get_route(gDomain, (sockaddr *)address); - TRACE((" TCP: Connect(): Using Route %p\n", fRoute)); + TRACE((" TCP:%p.Connect(): Using Route %p\n", this, fRoute)); if (fRoute == NULL) return ENETUNREACH; } @@ -232,7 +232,8 @@ status_t status = gEndpointManager->SetConnection(this, (sockaddr *)&socket->address, address, fRoute->interface->address); if (status < B_OK) { - TRACE((" TCP: Connect(): could not add connection: %s!\n", strerror(status))); + TRACE((" TCP:%p.Connect(): could not add connection: %s!\n", + this, strerror(status))); return status; } @@ -246,7 +247,7 @@ fReceiveWindowShift++; } - TRACE((" TCP: Connect(): starting 3-way handshake...\n")); + TRACE((" TCP:%p.Connect(): starting 3-way handshake...\n", this)); fState = SYNCHRONIZE_SENT; fInitialSendSequence = system_time() >> 4; @@ -274,7 +275,8 @@ status = acquire_sem_etc(fSendLock, 1, B_RELATIVE_TIMEOUT | B_CAN_INTERRUPT, timeout); - TRACE((" TCP: Connect(): Connection complete: %s\n", strerror(status))); + TRACE((" TCP:%p.Connect(): Connection complete: %s\n", + this, strerror(status))); return status; } @@ -381,7 +383,7 @@ * fSendMaxSegmentSize; chunk = gBufferModule->split(buffer, chunkSize); -TRACE((" TCP::Send() split buffer at %lu (buffer size %lu, mss %lu) -> %p\n", chunkSize, socket->send.buffer_size, fSendMaxSegmentSize, chunk)); +TRACE((" TCP:%p.Send() split buffer at %lu (buffer size %lu, mss %lu) -> %p\n", this, chunkSize, socket->send.buffer_size, fSendMaxSegmentSize, chunk)); if (chunk == NULL) return B_NO_MEMORY; } else @@ -476,7 +478,8 @@ RecursiveLocker locker(fLock); -TRACE(("read %lu bytes, %lu are available\n", numBytes, fReceiveQueue.Available())); + TRACE(("TCP: %p.ReadData(): read %lu bytes, %lu are available\n", + this, numBytes, fReceiveQueue.Available())); if (numBytes < fReceiveQueue.Available()) release_sem_etc(fReceiveLock, 1, B_DO_NOT_RESCHEDULE); @@ -723,7 +726,7 @@ // this is a pure acknowledge segment - we're on the sending end if (fSendUnacknowledged < segment.acknowledge && fSendMax >= segment.acknowledge) { -TRACE(("header prediction send!\n")); + TRACE(("TCP:%p.Receive(): header prediction send!\n", this)); // and it only acknowledges outstanding data // TODO: update RTT estimators @@ -746,11 +749,12 @@ } else if (segment.acknowledge == fSendUnacknowledged && fReceiveQueue.IsContiguous() && fReceiveQueue.Free() >= buffer->size) { -TRACE(("header prediction receive!\n")); + TRACE(("TCP:%p.Receive(): header prediction receive!\n", this)); // we're on the receiving end of the connection, and this segment // is the one we were expecting, in-sequence fReceiveNext += buffer->size; -TRACE(("receive next = %lu!\n", (uint32)fReceiveNext)); + TRACE(("TCP:%p.Receive(): receive next = %lu!\n", + this, (uint32)fReceiveNext)); fReceiveQueue.Add(buffer, segment.sequence); release_sem_etc(fReceiveLock, 1, B_DO_NOT_RESCHEDULE); @@ -806,7 +810,7 @@ } // remove duplicate data at the start -TRACE(("* remove %ld bytes from the start\n", drop)); + TRACE(("* remove %ld bytes from the start\n", drop)); gBufferModule->remove_header(buffer, drop); segment.sequence += drop; } @@ -831,7 +835,7 @@ } segment.flags &= ~(TCP_FLAG_FINISH | TCP_FLAG_PUSH); -TRACE(("* remove %ld bytes from the end\n", drop)); + TRACE(("* remove %ld bytes from the end\n", drop)); gBufferModule->remove_trailer(buffer, drop); } @@ -860,7 +864,7 @@ // TODO: handle this! if (buffer->size == 0 && advertisedWindow == fSendWindow && (segment.flags & TCP_FLAG_FINISH) == 0) { -TRACE(("duplicate ack!\n")); + TRACE(("TCP:%p.Receive(): duplicate ack!\n", this)); fDuplicateAcknowledgeCount++; gStackModule->cancel_timer(&fRetransmitTimer); @@ -877,10 +881,10 @@ // there is no outstanding data to be acknowledged // TODO: if the transmit timer function is already waiting // to acquire this endpoint's lock, we should stop it anyway -TRACE(("all inflight data ack'd!\n")); + TRACE(("TCP:%p.Receive(): all inflight data ack'd!\n", this)); gStackModule->cancel_timer(&fRetransmitTimer); } else { -TRACE(("set retransmit timer!\n")); + TRACE(("TCP:%p.Receive(): set retransmit timer!\n", this)); // TODO: set retransmit timer correctly if (!gStackModule->is_timer_active(&fRetransmitTimer)) gStackModule->set_timer(&fRetransmitTimer, 1000000LL); @@ -894,7 +898,7 @@ if (segment.acknowledge > fSendQueue.LastSequence() && fState > ESTABLISHED) { // our TCP_FLAG_FINISH has been acknowledged -TRACE(("FIN has been acknowledged!\n")); + TRACE(("TCP:%p.Receive(): FIN has been acknowledged!\n", this)); switch (fState) { case FINISH_SENT: @@ -924,7 +928,7 @@ // TODO: ignore data *after* FIN if (segment.flags & TCP_FLAG_FINISH) { -TRACE(("peer is finishing connection!")); + TRACE(("TCP:%p.Receive(): peer is finishing connection!\n", this)); fReceiveNext++; fFlags |= FLAG_NO_RECEIVE; @@ -967,7 +971,7 @@ if (buffer->size > 0) { fReceiveQueue.Add(buffer, segment.sequence); fReceiveNext = fReceiveQueue.NextSequence(); -TRACE(("adding data, receive next = %lu!\n", (uint32)fReceiveNext)); + TRACE(("TCP %p.Receive(): adding data, receive next = %lu!\n", this, (uint32)fReceiveNext)); release_sem_etc(fReceiveLock, 1, B_DO_NOT_RESCHEDULE); // TODO: real conditional locking needed! From hugosantos at mail.berlios.de Tue Apr 3 16:26:03 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Tue, 3 Apr 2007 16:26:03 +0200 Subject: [Haiku-commits] r20534 - haiku/trunk/src/add-ons/kernel/network/protocols/tcp Message-ID: <200704031426.l33EQ34B002875@sheep.berlios.de> Author: hugosantos Date: 2007-04-03 16:25:53 +0200 (Tue, 03 Apr 2007) New Revision: 20534 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20534&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h Log: fixed a bug in TCP where applications weren't properly signaled when the connection was terminated by the server and there was no more data to be read from the buffer. Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-03 14:25:39 UTC (rev 20533) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-03 14:25:53 UTC (rev 20534) @@ -430,7 +430,7 @@ } -size_t +ssize_t TCPEndpoint::SendAvailable() { TRACE(("TCP:%p.SendAvailable()\n", this)); @@ -487,13 +487,13 @@ } -size_t +ssize_t TCPEndpoint::ReadAvailable() { TRACE(("TCP:%p.ReadAvailable()\n", this)); RecursiveLocker locker(fLock); - return fReceiveQueue.Available(); + return _AvailableBytesOrDisconnect(); } @@ -934,7 +934,7 @@ release_sem_etc(fReceiveLock, 1, B_DO_NOT_RESCHEDULE); // TODO: real conditional locking needed! - gSocketModule->notify(socket, B_SELECT_READ, fReceiveQueue.Available()); + gSocketModule->notify(socket, B_SELECT_READ, _AvailableBytesOrDisconnect()); // other side is closing connection; change states switch (fState) { @@ -1218,6 +1218,20 @@ } +ssize_t +TCPEndpoint::_AvailableBytesOrDisconnect() const +{ + size_t availableBytes = fReceiveQueue.Available(); + if (availableBytes > 0) + return availableBytes; + + if ((fFlags & FLAG_NO_RECEIVE) != 0) + return ENOTCONN; + + return 0; +} + + // #pragma mark - timer Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h 2007-04-03 14:25:39 UTC (rev 20533) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h 2007-04-03 14:25:53 UTC (rev 20534) @@ -41,9 +41,9 @@ status_t Listen(int count); status_t Shutdown(int direction); status_t SendData(net_buffer *buffer); - size_t SendAvailable(); + ssize_t SendAvailable(); status_t ReadData(size_t numBytes, uint32 flags, net_buffer **_buffer); - size_t ReadAvailable(); + ssize_t ReadAvailable(); tcp_state State() const { return fState; } bool IsBound() const; @@ -66,6 +66,7 @@ bool outstandingAcknowledge); status_t _SendQueued(bool force = false); int _GetMSS(const struct sockaddr *) const; + ssize_t _AvailableBytesOrDisconnect() const; static void _TimeWaitTimer(net_timer *timer, void *data); static void _RetransmitTimer(net_timer *timer, void *data); From axeld at mail.berlios.de Tue Apr 3 16:42:09 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Tue, 3 Apr 2007 16:42:09 +0200 Subject: [Haiku-commits] r20535 - in haiku/trunk/headers: posix/net private/net Message-ID: <200704031442.l33Eg9LM003562@sheep.berlios.de> Author: axeld Date: 2007-04-03 16:42:07 +0200 (Tue, 03 Apr 2007) New Revision: 20535 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20535&view=rev Added: haiku/trunk/headers/posix/net/if_media.h Modified: haiku/trunk/headers/posix/net/if.h haiku/trunk/headers/private/net/ether_driver.h Log: * Rewrote ether_driver.h, removed some BONE stuff we don't support at this point; it might also be a good idea to change the constants to better match the usual style. * Added a BSD-style if_media.h. * Added interface flags IFF_LINK, IFF_AUTO_CONFIGURED, and IFF_CONFIGURING. The former will be set automatically by the stack, the rest will be set by the net_server depending on the current state. Modified: haiku/trunk/headers/posix/net/if.h =================================================================== --- haiku/trunk/headers/posix/net/if.h 2007-04-03 14:25:53 UTC (rev 20534) +++ haiku/trunk/headers/posix/net/if.h 2007-04-03 14:42:07 UTC (rev 20535) @@ -1,5 +1,5 @@ /* - * Copyright 2006, Haiku, Inc. All Rights Reserved. + * Copyright 2006-2007, Haiku, Inc. All Rights Reserved. * Distributed under the terms of the MIT License. */ #ifndef _NET_IF_H @@ -56,16 +56,19 @@ }; /* interface flags */ -#define IFF_UP 0x0001 -#define IFF_BROADCAST 0x0002 /* valid broadcast address */ -#define IFF_LOOPBACK 0x0008 -#define IFF_POINTOPOINT 0x0010 /* point-to-point link */ -#define IFF_NOARP 0x0040 /* no address resolution */ -#define IFF_AUTOUP 0x0080 /* auto dial */ -#define IFF_PROMISC 0x0100 /* receive all packets */ -#define IFF_ALLMULTI 0x0200 /* receive all multicast packets */ -#define IFF_SIMPLEX 0x0800 /* doesn't receive own transmissions */ -#define IFF_MULTICAST 0x8000 /* supports multicast */ +#define IFF_UP 0x0001 +#define IFF_BROADCAST 0x0002 /* valid broadcast address */ +#define IFF_LOOPBACK 0x0008 +#define IFF_POINTOPOINT 0x0010 /* point-to-point link */ +#define IFF_NOARP 0x0040 /* no address resolution */ +#define IFF_AUTOUP 0x0080 /* auto dial */ +#define IFF_PROMISC 0x0100 /* receive all packets */ +#define IFF_ALLMULTI 0x0200 /* receive all multicast packets */ +#define IFF_SIMPLEX 0x0800 /* doesn't receive own transmissions */ +#define IFF_LINK 0x1000 /* has link */ +#define IFF_AUTO_CONFIGURED 0x2000 /* has been automatically configured */ +#define IFF_CONFIGURING 0x4000 /* auto configuration in progress */ +#define IFF_MULTICAST 0x8000 /* supports multicast */ struct ifconf { int ifc_len; /* size of buffer */ Added: haiku/trunk/headers/posix/net/if_media.h =================================================================== --- haiku/trunk/headers/posix/net/if_media.h 2007-04-03 14:25:53 UTC (rev 20534) +++ haiku/trunk/headers/posix/net/if_media.h 2007-04-03 14:42:07 UTC (rev 20535) @@ -0,0 +1,55 @@ +/* + * Copyright 2007, Haiku, Inc. All Rights Reserved. + * Distributed under the terms of the MIT License. + */ +#ifndef _NET_IF_MEDIA_H +#define _NET_IF_MEDIA_H + + +/* bits usage + * ---- ----- + * 0-4 Media subtype + * 5-7 Media type + * 8-15 Type specific options + * 16-31 General options + */ + +/* Media types */ + +#define IFM_ETHER 0x00000020 /* Ethernet */ +#define IFM_TOKEN 0x00000040 /* Token Ring */ +#define IFM_FDDI 0x00000060 /* Fiber Distributed Data Interface */ +#define IFM_IEEE80211 0x00000080 /* Wireless IEEE 802.11 */ +#define IFM_ATM 0x000000a0 +#define IFM_CARP 0x000000c0 /* Common Address Redundancy Protocol */ + +/* Media subtypes */ + +/* Ethernet */ +#define IFM_10_T 3 /* 10Base-T - RJ45 */ +#define IFM_100_TX 6 /* 100Base-TX - RJ45 */ +#define IFM_1000_T 16 /* 1000Base-T - RJ45 */ + +/* General options */ + +#define IFM_FULL_DUPLEX 0x00100000 /* Full duplex */ +#define IFM_HALF_DUPLEX 0x00200000 /* Half duplex */ +#define IFM_LOOP 0x00400000 /* hardware in loopback */ +#define IFM_ACTIVE 0x00800000 /* Media link is active */ + +/* Masks */ + +#define IFM_NMASK 0x000000e0 /* Media type */ +#define IFM_TMASK 0x0000001f /* Media subtype */ +#define IFM_OMASK 0x0000ff00 /* Type specific options */ +#define IFM_GMASK 0xffff0000 /* Generic options */ + +/* Macros for the masks */ + +#define IFM_TYPE(x) ((x) & IFM_NMASK) +#define IFM_SUBTYPE(x) ((x) & IFM_TMASK) +#define IFM_TYPE_OPTIONS(x) \ + ((x) & IFM_OMASK) +#define IFM_OPTIONS(x) ((x) & (IFM_OMASK | IFM_GMASK)) + +#endif /* _NET_IF_MEDIA_H */ Modified: haiku/trunk/headers/private/net/ether_driver.h =================================================================== --- haiku/trunk/headers/private/net/ether_driver.h 2007-04-03 14:25:53 UTC (rev 20534) +++ haiku/trunk/headers/private/net/ether_driver.h 2007-04-03 14:42:07 UTC (rev 20535) @@ -1,71 +1,41 @@ /* - * ether_driver.h - * - * Ethernet driver: handles NE2000 and 3C503 cards + * Copyright 2007, Haiku, Inc. All Rights Reserved. + * Distributed under the terms of the MIT License. */ -/* - Copyright 1999, Be Incorporated. All Rights Reserved. - This file may be used under the terms of the Be Sample Code License. -*/ #ifndef _ETHER_DRIVER_H #define _ETHER_DRIVER_H -#ifdef __cplusplus -extern "C" { -#endif +/*! Standard ethernet driver interface */ + #include -/* - * ioctls: belongs in a public header file - * somewhere, so that the net_server and other ethernet drivers can use. - */ + +/* ioctl() opcodes a driver should support */ enum { - ETHER_GETADDR = B_DEVICE_OP_CODES_END, /* get ethernet address */ - ETHER_INIT, /* set irq and port */ - ETHER_NONBLOCK, /* set/unset nonblocking mode */ - ETHER_ADDMULTI, /* add multicast addr */ - ETHER_REMMULTI, /* rem multicast addr */ - ETHER_SETPROMISC, /* set promiscuous */ - ETHER_GETFRAMESIZE, /* get frame size */ - ETHER_ADDTIMESTAMP, /* (try to) add timestamps to packets (BONE ext) */ - ETHER_HASIOVECS, /* does the driver implement writev ? (BONE ext) (bool *) */ - ETHER_GETIFTYPE, /* get the IFT_ type of the interface (int *) */ - ETHER_GETLINKSTATE /* get line speed, quality, duplex mode, etc. */ + ETHER_GETADDR = B_DEVICE_OP_CODES_END, + /* get ethernet address (required) */ + ETHER_INIT, /* (obsolete) */ + ETHER_NONBLOCK, /* change non blocking mode (int *) */ + ETHER_ADDMULTI, /* add multicast address */ + ETHER_REMMULTI, /* remove multicast address */ + ETHER_SETPROMISC, /* set promiscuous mode (int *) */ + ETHER_GETFRAMESIZE, /* get frame size (required) (int *) */ + ETHER_GETLINKSTATE + /* get line speed, quality, duplex mode, etc. (ether_link_state_t *) */ }; -/* - * 48-bit ethernet address, passed back from ETHER_GETADDR - */ +/* ETHER_GETADDR - MAC address */ typedef struct { - unsigned char ebyte[6]; + uint8 ebyte[6]; } ether_address_t; - -/* - * info passed to ETHER_INIT - */ - -typedef struct ether_init_params { - short port; - short irq; - unsigned long mem; -} ether_init_params_t; - -/* - * info returned from ETHER_GETLINKSTATE - */ - +/* ETHER_GETLINKSTATE */ typedef struct ether_link_state { - float link_speed; /* In Mbits per second */ - float link_quality; /* Set to zero if not connected */ - char duplex_mode; /* Set to 1 for full duplex, 0 for half */ + uint32 link_media; /* as specified in net/if_media.h */ + uint32 link_quality; /* in one tenth of a percent */ + uint64 link_speed; /* in Kbit/s */ } ether_link_state_t; -#ifdef __cplusplus -} -#endif - - -#endif /* _ETHER_DRIVER_H */ +#endif /* _ETHER_DRIVER_H */ From axeld at mail.berlios.de Tue Apr 3 16:43:16 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Tue, 3 Apr 2007 16:43:16 +0200 Subject: [Haiku-commits] r20536 - haiku/trunk/src/add-ons/kernel/drivers/network/sis900 Message-ID: <200704031443.l33EhGUB003697@sheep.berlios.de> Author: axeld Date: 2007-04-03 16:43:16 +0200 (Tue, 03 Apr 2007) New Revision: 20536 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20536&view=rev Modified: haiku/trunk/src/add-ons/kernel/drivers/network/sis900/device.c haiku/trunk/src/add-ons/kernel/drivers/network/sis900/driver.h haiku/trunk/src/add-ons/kernel/drivers/network/sis900/sis900.c haiku/trunk/src/add-ons/kernel/drivers/network/sis900/sis900.h Log: * Implemented ETHER_GETLINKSTATE; the link state is now tracked and can be reported. * Made header self-containing. * Minor cleanup. Modified: haiku/trunk/src/add-ons/kernel/drivers/network/sis900/device.c =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/network/sis900/device.c 2007-04-03 14:42:07 UTC (rev 20535) +++ haiku/trunk/src/add-ons/kernel/drivers/network/sis900/device.c 2007-04-03 14:43:16 UTC (rev 20536) @@ -1,27 +1,25 @@ -/* Device hooks for SiS 900 networking - * - * Copyright ? 2001-2005 pinc Software. All Rights Reserved. +/* + * Copyright (c) 2001-2007 pinc Software. All Rights Reserved. + * Distributed under the terms of the MIT license. */ +/*! Device hooks for SiS 900 networking */ -#include -#include -#include -#include -#include -#include +#include "device.h" + +#include "driver.h" +#include "interface.h" +#include "sis900.h" + #include #include #include +#ifdef HAIKU_TARGET_PLATFORM_HAIKU +# include +#endif -#include "ether_driver.h" -#include "driver.h" -#include "device.h" -#include "sis900.h" -#include "interface.h" - /* device hooks prototypes */ status_t device_open(const char *, uint32, void **); @@ -362,32 +360,47 @@ case ETHER_GETADDR: TRACE(("ioctl: get MAC address\n")); memcpy(buffer, &info->address, 6); - return B_NO_ERROR; + return B_OK; case ETHER_INIT: TRACE(("ioctl: init\n")); - return B_NO_ERROR; - + return B_OK; + case ETHER_GETFRAMESIZE: TRACE(("ioctl: get frame size\n")); *(uint32*)buffer = MAX_FRAME_SIZE; - return B_NO_ERROR; - + return B_OK; + case ETHER_SETPROMISC: TRACE(("ioctl: set promisc\n")); sis900_setPromiscuous(info, *(uint32 *)buffer != 0); return B_OK; - + case ETHER_NONBLOCK: info->blockFlag = *(int32 *)buffer ? B_TIMEOUT : 0; TRACE(("ioctl: non blocking ? %s\n", info->blockFlag ? "yes" : "no")); - return B_NO_ERROR; - + return B_OK; + case ETHER_ADDMULTI: TRACE(("ioctl: add multicast\n")); /* not yet implemented */ break; - + +#ifdef HAIKU_TARGET_PLATFORM_HAIKU + case ETHER_GETLINKSTATE: + { + ether_link_state_t state; + state.link_media = (info->link ? IFM_ACTIVE : 0) + | (info->full_duplex ? IFM_FULL_DUPLEX : IFM_HALF_DUPLEX) + | (info->speed == LINK_SPEED_100_MBIT ? IFM_100_TX : IFM_10_T); + state.link_speed = info->speed == LINK_SPEED_100_MBIT + ? 100000 : 10000; + state.link_quality = 1000; + + return user_memcpy(buffer, &state, sizeof(ether_link_state_t)); + } +#endif + default: TRACE(("ioctl: unknown message %lu (length = %ld)\n", msg, bufferLength)); break; Modified: haiku/trunk/src/add-ons/kernel/drivers/network/sis900/driver.h =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/network/sis900/driver.h 2007-04-03 14:42:07 UTC (rev 20535) +++ haiku/trunk/src/add-ons/kernel/drivers/network/sis900/driver.h 2007-04-03 14:43:16 UTC (rev 20536) @@ -1,12 +1,14 @@ -/* Kernel driver for SiS 900 networking - * - * Copyright ? 2001-2005 pinc Software. All Rights Reserved. +/* + * Copyright (c) 2001-2007 pinc Software. All Rights Reserved. * Distributed under the terms of the MIT license. */ #ifndef DRIVER_H #define DRIVER_H +#include + + // PCI Communications #define IO_PORT_PCI_ACCESS true Modified: haiku/trunk/src/add-ons/kernel/drivers/network/sis900/sis900.c =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/network/sis900/sis900.c 2007-04-03 14:42:07 UTC (rev 20535) +++ haiku/trunk/src/add-ons/kernel/drivers/network/sis900/sis900.c 2007-04-03 14:43:16 UTC (rev 20536) @@ -434,8 +434,10 @@ uint32 address = info->registers + SiS900_MAC_CONFIG; uint32 txFlags = SiS900_Tx_AUTO_PADDING | SiS900_Tx_FILL_THRES; uint32 rxFlags = 0; - int32 speed = mode & LINK_SPEED_MASK; + info->speed = mode & LINK_SPEED_MASK; + info->full_duplex = (mode & LINK_DUPLEX_MASK) == LINK_FULL_DUPLEX; + if (read32(address) & SiS900_MAC_CONFIG_EDB_MASTER) { TRACE((DEVICE_NAME ": EDB master is set!\n")); txFlags |= 5 << SiS900_DMA_SHIFT; @@ -444,7 +446,7 @@ // link speed FIFO thresholds - if (speed == LINK_SPEED_HOME || speed == LINK_SPEED_10_MBIT) { + if (info->speed == LINK_SPEED_HOME || info->speed == LINK_SPEED_10_MBIT) { rxFlags |= SiS900_Rx_10_MBIT_DRAIN_THRES; txFlags |= SiS900_Tx_10_MBIT_DRAIN_THRES; } else { @@ -454,7 +456,7 @@ // duplex mode - if ((mode & LINK_DUPLEX_MASK) == LINK_FULL_DUPLEX) { + if (info->full_duplex) { txFlags |= SiS900_Tx_CS_IGNORE | SiS900_Tx_HB_IGNORE; rxFlags |= SiS900_Rx_ACCEPT_Tx_PACKETS; } Modified: haiku/trunk/src/add-ons/kernel/drivers/network/sis900/sis900.h =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/network/sis900/sis900.h 2007-04-03 14:42:07 UTC (rev 20535) +++ haiku/trunk/src/add-ons/kernel/drivers/network/sis900/sis900.h 2007-04-03 14:43:16 UTC (rev 20536) @@ -1,15 +1,18 @@ -/* SiS 900 driver/chip specific definitions - * - * Copyright ? 2001-2005 pinc Software. All Rights Reserved. +/* + * Copyright (c) 2001-2007 pinc Software. All Rights Reserved. * Distributed under the terms of the MIT license. */ #ifndef SIS900_H #define SIS900_H +/*! SiS 900 driver/chip specific definitions */ -#include "ether_driver.h" +#include +#include +#include + #define VENDOR_ID_SiS 0x1039 #define DEVICE_ID_SiS900 0x900 @@ -98,6 +101,8 @@ uint16 phy; bool autoNegotiationComplete; bool link; + bool full_duplex; + uint16 speed; uint16 fixedMode; // receive data From axeld at mail.berlios.de Tue Apr 3 16:57:29 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Tue, 3 Apr 2007 16:57:29 +0200 Subject: [Haiku-commits] r20537 - haiku/trunk/src/add-ons/kernel/drivers/network/ipro1000 Message-ID: <200704031457.l33EvTRe004731@sheep.berlios.de> Author: axeld Date: 2007-04-03 16:57:28 +0200 (Tue, 03 Apr 2007) New Revision: 20537 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20537&view=rev Modified: haiku/trunk/src/add-ons/kernel/drivers/network/ipro1000/device.c haiku/trunk/src/add-ons/kernel/drivers/network/ipro1000/if_compat.h haiku/trunk/src/add-ons/kernel/drivers/network/ipro1000/if_em_osdep.h Log: Prepared implementation of ETHER_GETLINKSTATE - it would need a bit more work to get it to work as intended, though. Modified: haiku/trunk/src/add-ons/kernel/drivers/network/ipro1000/device.c =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/network/ipro1000/device.c 2007-04-03 14:43:16 UTC (rev 20536) +++ haiku/trunk/src/add-ons/kernel/drivers/network/ipro1000/device.c 2007-04-03 14:57:28 UTC (rev 20537) @@ -16,14 +16,8 @@ * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ -#include -#include -#include -#include -#include -#include -#include + #include "debug.h" #include "device.h" #include "driver.h" @@ -31,6 +25,17 @@ #include "if_em.h" #include "if_compat.h" +#include +#include + +#include +#include +#include +#include +#ifdef HAIKU_TARGET_PLATFORM_HAIKU +# include +#endif + #undef malloc #undef free @@ -331,11 +336,28 @@ DEVICE_DEBUGOUT2("ipro1000_control() ETHER_GETFRAMESIZE, framesize = %d (MTU = %d)", device->maxframesize, device->maxframesize - ENET_HEADER_SIZE); *(uint32*)arg = device->maxframesize; return B_OK; - + +#ifdef HAIKU_TARGET_PLATFORM_HAIKU +#if 0 + case ETHER_GETLINKSTATE: + { + ether_link_state_t state; + state.link_media = (info->link ? IFM_ACTIVE : 0) + | (info->full_duplex ? IFM_FULL_DUPLEX : IFM_HALF_DUPLEX) + | (info->speed == LINK_SPEED_100_MBIT ? IFM_100_TX : IFM_10_T); + state.link_speed = info->speed == LINK_SPEED_100_MBIT + ? 100000 : 10000; + state.link_quality = 1000; + + return user_memcpy(buffer, &state, sizeof(ether_link_state_t)); + } +#endif +#endif + default: DEVICE_DEBUGOUT("ipro1000_control() Invalid command"); break; } - - return B_ERROR; + + return B_BAD_VALUE; } Modified: haiku/trunk/src/add-ons/kernel/drivers/network/ipro1000/if_compat.h =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/network/ipro1000/if_compat.h 2007-04-03 14:43:16 UTC (rev 20536) +++ haiku/trunk/src/add-ons/kernel/drivers/network/ipro1000/if_compat.h 2007-04-03 14:57:28 UTC (rev 20537) @@ -38,24 +38,31 @@ #define IFCAP_TXCSUM 0x0010 #define IFCAP_RXCSUM 0x0020 -#define IFM_ACTIVE 0x0001 -#define IFM_FDX 0x0002 -#define IFM_HDX 0x0004 -#define IFM_10_T 0x0008 -#define IFM_100_TX 0x0010 -#define IFM_1000_T 0x0020 -#define IFM_1000_TX 0x0040 -#define IFM_1000_SX 0x0080 -#define IFM_ETHER 0x0100 -#define IFM_AUTO 0x0200 -#define IFM_AVALID 0x0400 -#define IFM_GMASK (IFM_FDX | IFM_HDX) -#define IFM_TYPE_MASK (IFM_ETHER) -#define IFM_SUBTYPE_MASK (IFM_AUTO | IFM_1000_SX | IFM_1000_TX | IFM_1000_T | IFM_100_TX | IFM_10_T) +#ifdef HAIKU_TARGET_PLATFORM_HAIKU +# define IFM_FDX IFM_FULL_DUPLEX +# define IFM_HDX IFM_HALF_DUPLEX +# define IFM_1000_TX 17 +# define IFM_1000_SX 18 +#else +# define IFM_ACTIVE 0x0001 +# define IFM_FDX 0x0002 +# define IFM_HDX 0x0004 +# define IFM_10_T 0x0008 +# define IFM_100_TX 0x0010 +# define IFM_1000_T 0x0020 +# define IFM_1000_TX 0x0040 +# define IFM_1000_SX 0x0080 +# define IFM_ETHER 0x0100 +# define IFM_AUTO 0x0200 +# define IFM_AVALID 0x0400 +# define IFM_GMASK (IFM_FDX | IFM_HDX) +# define IFM_TYPE_MASK (IFM_ETHER) +# define IFM_SUBTYPE_MASK \ + (IFM_AUTO | IFM_1000_SX | IFM_1000_TX | IFM_1000_T | IFM_100_TX | IFM_10_T) +# define IFM_TYPE(media) ((media) & IFM_TYPE_MASK) +# define IFM_SUBTYPE(media) ((media) & IFM_SUBTYPE_MASK) +#endif -#define IFM_TYPE(media) ((media) & IFM_TYPE_MASK) -#define IFM_SUBTYPE(media) ((media) & IFM_SUBTYPE_MASK) - #define CSUM_TCP 0x0001 // ifnet::if_hwassist #define CSUM_UDP 0x0002 // ifnet::if_hwassist #define CSUM_IP_CHECKED 0x0004 Modified: haiku/trunk/src/add-ons/kernel/drivers/network/ipro1000/if_em_osdep.h =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/network/ipro1000/if_em_osdep.h 2007-04-03 14:43:16 UTC (rev 20536) +++ haiku/trunk/src/add-ons/kernel/drivers/network/ipro1000/if_em_osdep.h 2007-04-03 14:57:28 UTC (rev 20537) @@ -34,17 +34,19 @@ #ifndef _IF_EM_OSDEP_H_ #define _IF_EM_OSDEP_H_ -#include -#include -#include -#include -#include -#include #include "driver.h" #include "device.h" #include "timer.h" #include "debug.h" +#include +#include +#include + +#include +#include +#include + #define usec_delay(x) snooze(x) #define msec_delay(x) snooze(1000*(x)) From wkornewald at haiku-os.org Tue Apr 3 17:44:30 2007 From: wkornewald at haiku-os.org (Waldemar Kornewald) Date: Tue, 3 Apr 2007 17:44:30 +0200 Subject: [Haiku-commits] r20536 - haiku/trunk/src/add-ons/kernel/drivers/network/sis900 In-Reply-To: <200704031443.l33EhGUB003697@sheep.berlios.de> References: <200704031443.l33EhGUB003697@sheep.berlios.de> Message-ID: Hi Axel, On 4/3/07, axeld at BerliOS wrote: > Author: axeld > Date: 2007-04-03 16:43:16 +0200 (Tue, 03 Apr 2007) > New Revision: 20536 > ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20536&view=rev > > Modified: > haiku/trunk/src/add-ons/kernel/drivers/network/sis900/device.c > haiku/trunk/src/add-ons/kernel/drivers/network/sis900/driver.h > haiku/trunk/src/add-ons/kernel/drivers/network/sis900/sis900.c > haiku/trunk/src/add-ons/kernel/drivers/network/sis900/sis900.h > Log: > * Implemented ETHER_GETLINKSTATE; the link state is now tracked and can be reported. You're my personal hero! :) I've always wished that the system has a way to automatically recognize when it must reconfigure an interface. Now, we need this in every ethernet driver. ;) Do you know if other drivers already support this feature? Or is this a Haiku-only function? Bye, Waldemar Kornewald From wkornewald at haiku-os.org Tue Apr 3 17:45:38 2007 From: wkornewald at haiku-os.org (Waldemar Kornewald) Date: Tue, 3 Apr 2007 17:45:38 +0200 Subject: [Haiku-commits] r20536 - haiku/trunk/src/add-ons/kernel/drivers/network/sis900 In-Reply-To: References: <200704031443.l33EhGUB003697@sheep.berlios.de> Message-ID: On 4/3/07, Waldemar Kornewald wrote: > Do you know if other drivers already support this feature? Or is this > a Haiku-only function? Hmm, I should've taken a look at the source. #ifdef HAIKU_TARGET_PLATFORM_HAIKU... Bye, Waldemar Kornewald From axeld at pinc-software.de Tue Apr 3 17:59:05 2007 From: axeld at pinc-software.de (Axel =?iso-8859-15?q?D=F6rfler?=) Date: Tue, 03 Apr 2007 17:59:05 +0200 CEST Subject: [Haiku-commits] =?iso-8859-15?q?r20536_-_haiku/trunk/src/add-ons/?= =?iso-8859-15?q?kernel/drivers/network/sis900?= In-Reply-To: Message-ID: <20471374357-BeMail@zon> "Waldemar Kornewald" wrote: > > Log: > > * Implemented ETHER_GETLINKSTATE; the link state is now tracked > > and can be reported. > You're my personal hero! :) I've always wished that the system has a > way to automatically recognize when it must reconfigure an interface. > Now, we need this in every ethernet driver. ;) > Do you know if other drivers already support this feature? Or is this > a Haiku-only function? It was supposed to be a BONE extension, but I implemented it differently; AFAICT there are no drivers that support those BONE extensions including BONE itself. Therefore (and because of user_memcpy()) it's implemented as Haiku-only function. Bye, Axel. From axeld at mail.berlios.de Tue Apr 3 18:39:43 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Tue, 3 Apr 2007 18:39:43 +0200 Subject: [Haiku-commits] r20538 - haiku/trunk/src/add-ons/kernel/network/devices/ethernet Message-ID: <200704031639.l33GdhLw029466@sheep.berlios.de> Author: axeld Date: 2007-04-03 18:39:30 +0200 (Tue, 03 Apr 2007) New Revision: 20538 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20538&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/devices/ethernet/ethernet.cpp Log: * Fixed compilation due to removed ether_init_params from ether_driver.h, thanks to Hugo for reporting :-) * Implemented setting promiscuous mode on ethernet device level. * Set net_device::media to something useful. Modified: haiku/trunk/src/add-ons/kernel/network/devices/ethernet/ethernet.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/devices/ethernet/ethernet.cpp 2007-04-03 14:57:28 UTC (rev 20537) +++ haiku/trunk/src/add-ons/kernel/network/devices/ethernet/ethernet.cpp 2007-04-03 16:39:30 UTC (rev 20538) @@ -1,5 +1,5 @@ /* - * Copyright 2006, Haiku, Inc. All Rights Reserved. + * Copyright 2006-2007, Haiku, Inc. All Rights Reserved. * Distributed under the terms of the MIT License. * * Authors: @@ -16,8 +16,9 @@ #include #include +#include +#include #include -#include #include #include #include @@ -28,7 +29,6 @@ uint32 frame_size; }; - struct net_buffer_module_info *gBufferModule; @@ -57,6 +57,7 @@ device->flags = IFF_BROADCAST; device->type = IFT_ETHER; device->mtu = 1500; + device->media = IFM_ACTIVE; device->header_length = ETHER_HEADER_LENGTH; device->fd = -1; @@ -84,11 +85,6 @@ if (device->fd < 0) return errno; - ether_init_params params; - memset(¶ms, 0, sizeof(ether_init_params)); - if (ioctl(device->fd, ETHER_INIT, ¶ms, sizeof(ether_init_params)) < 0) - goto err; - if (ioctl(device->fd, ETHER_GETADDR, device->address.data, ETHER_ADDRESS_LENGTH) < 0) goto err; @@ -243,9 +239,15 @@ status_t -ethernet_set_promiscuous(net_device *device, bool promiscuous) +ethernet_set_promiscuous(net_device *_device, bool promiscuous) { - return EOPNOTSUPP; + ethernet_device *device = (ethernet_device *)_device; + + int32 value = (int32)promiscuous; + if (ioctl(device->fd, ETHER_GETADDR, &value, sizeof(value)) < 0) + return EOPNOTSUPP; + + return B_OK; } From hugosantos at mail.berlios.de Tue Apr 3 18:54:26 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Tue, 3 Apr 2007 18:54:26 +0200 Subject: [Haiku-commits] r20539 - haiku/trunk/src/add-ons/kernel/network/protocols/tcp Message-ID: <200704031654.l33GsQYu014754@sheep.berlios.de> Author: hugosantos Date: 2007-04-03 18:54:07 +0200 (Tue, 03 Apr 2007) New Revision: 20539 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20539&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp Log: some more cleanups to TCP TRACE() facility Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-03 16:39:30 UTC (rev 20538) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-03 16:54:07 UTC (rev 20539) @@ -42,10 +42,12 @@ // Forward RTO-Recovery, RFC 4138 //#define TRACE_TCP + #ifdef TRACE_TCP -# define TRACE(x) dprintf x +// the space after 'this' is important in order for this to work with cpp 2.95 +# define TRACE(format, args...) dprintf("TCP:%p:" format "\n", this , ##args) #else -# define TRACE(x) +# define TRACE(args...) #endif // Initial estimate for packet round trip time (RTT) @@ -139,7 +141,7 @@ status_t TCPEndpoint::Open() { - TRACE(("%p.Open()\n", this)); + TRACE("Open()"); // nothing to do here... return B_OK; } @@ -148,7 +150,7 @@ status_t TCPEndpoint::Close() { - TRACE(("TCP:%p.Close()\n", this)); + TRACE("Close()"); RecursiveLocker lock(fLock); if (fState == LISTEN) @@ -174,7 +176,7 @@ return status; } - TRACE(("TCP: %p.Close(): Entering state %d\n", this, fState)); + TRACE("Close(): Entering state %d", fState); // TODO: do i need to wait until fState returns to CLOSED? return B_OK; } @@ -183,7 +185,7 @@ status_t TCPEndpoint::Free() { - TRACE(("TCP:%p.Free()\n", this)); + TRACE("Free()"); if (fState <= SYNCHRONIZE_SENT || fState == TIME_WAIT) return B_OK; @@ -201,15 +203,15 @@ status_t TCPEndpoint::Connect(const struct sockaddr *address) { - TRACE(("TCP:%p.Connect() on address %s\n", this, - AddressString(gDomain, address, true).Data())); + TRACE("Connect() on address %s", + AddressString(gDomain, address, true).Data()); if (address->sa_family != AF_INET) return EAFNOSUPPORT; RecursiveLocker locker(&fLock); - TRACE((" TCP:%p.Connect(): in state %d\n", this, fState)); + TRACE(" Connect(): in state %d", fState); // Can only call connect() from CLOSED or LISTEN states // otherwise endpoint is considered already connected @@ -223,7 +225,7 @@ // TODO: get a net_route_info instead! if (fRoute == NULL) { fRoute = gDatalinkModule->get_route(gDomain, (sockaddr *)address); - TRACE((" TCP:%p.Connect(): Using Route %p\n", this, fRoute)); + TRACE(" Connect(): Using Route %p", fRoute); if (fRoute == NULL) return ENETUNREACH; } @@ -232,8 +234,7 @@ status_t status = gEndpointManager->SetConnection(this, (sockaddr *)&socket->address, address, fRoute->interface->address); if (status < B_OK) { - TRACE((" TCP:%p.Connect(): could not add connection: %s!\n", - this, strerror(status))); + TRACE(" Connect(): could not add connection: %s!", strerror(status)); return status; } @@ -247,7 +248,7 @@ fReceiveWindowShift++; } - TRACE((" TCP:%p.Connect(): starting 3-way handshake...\n", this)); + TRACE(" Connect(): starting 3-way handshake..."); fState = SYNCHRONIZE_SENT; fInitialSendSequence = system_time() >> 4; @@ -275,8 +276,7 @@ status = acquire_sem_etc(fSendLock, 1, B_RELATIVE_TIMEOUT | B_CAN_INTERRUPT, timeout); - TRACE((" TCP:%p.Connect(): Connection complete: %s\n", - this, strerror(status))); + TRACE(" Connect(): Connection complete: %s", strerror(status)); return status; } @@ -284,7 +284,7 @@ status_t TCPEndpoint::Accept(struct net_socket **_acceptedSocket) { - TRACE(("TCP:%p.Accept()\n", this)); + TRACE("Accept()"); // TODO: test for pending sockets // TODO: test for non-blocking I/O @@ -305,8 +305,8 @@ status_t TCPEndpoint::Bind(sockaddr *address) { - TRACE(("TCP:%p.Bind() on address %s\n", this, - AddressString(gDomain, address, true).Data())); + TRACE("Bind() on address %s", + AddressString(gDomain, address, true).Data()); RecursiveLocker lock(fLock); @@ -330,7 +330,7 @@ status_t TCPEndpoint::Unbind(struct sockaddr *address) { - TRACE(("TCP:%p.Unbind()\n", this)); + TRACE("Unbind()"); RecursiveLocker lock(fLock); return gEndpointManager->Unbind(this); @@ -340,7 +340,7 @@ status_t TCPEndpoint::Listen(int count) { - TRACE(("TCP:%p.Listen()\n", this)); + TRACE("Listen()"); RecursiveLocker lock(fLock); @@ -358,7 +358,7 @@ status_t TCPEndpoint::Shutdown(int direction) { - TRACE(("TCP:%p.Shutdown()\n", this)); + TRACE("Shutdown()"); // TODO: implement shutdown! return B_ERROR; } @@ -370,8 +370,8 @@ status_t TCPEndpoint::SendData(net_buffer *buffer) { - TRACE(("TCP:%p.SendData(buffer %p, size %lu, flags %lx)\n", - this, buffer, buffer->size, buffer->flags)); + TRACE("SendData(buffer %p, size %lu, flags %lx)", + buffer, buffer->size, buffer->flags); size_t bytesLeft = buffer->size; @@ -383,7 +383,8 @@ * fSendMaxSegmentSize; chunk = gBufferModule->split(buffer, chunkSize); -TRACE((" TCP:%p.Send() split buffer at %lu (buffer size %lu, mss %lu) -> %p\n", this, chunkSize, socket->send.buffer_size, fSendMaxSegmentSize, chunk)); + TRACE(" Send() split buffer at %lu (buffer size %lu, mss %lu) -> %p", + chunkSize, socket->send.buffer_size, fSendMaxSegmentSize, chunk); if (chunk == NULL) return B_NO_MEMORY; } else @@ -433,7 +434,7 @@ ssize_t TCPEndpoint::SendAvailable() { - TRACE(("TCP:%p.SendAvailable()\n", this)); + TRACE("SendAvailable()"); RecursiveLocker locker(fLock); return fSendQueue.Free(); @@ -443,7 +444,7 @@ status_t TCPEndpoint::ReadData(size_t numBytes, uint32 flags, net_buffer** _buffer) { - TRACE(("TCP:%p.ReadData(%lu bytes)\n", this, numBytes)); + TRACE("ReadData(%lu bytes)", numBytes); //BenaphoreLocker lock(&fReceiveLock); @@ -478,8 +479,9 @@ RecursiveLocker locker(fLock); - TRACE(("TCP: %p.ReadData(): read %lu bytes, %lu are available\n", - this, numBytes, fReceiveQueue.Available())); + TRACE("ReadData(): read %lu bytes, %lu are available", + numBytes, fReceiveQueue.Available()); + if (numBytes < fReceiveQueue.Available()) release_sem_etc(fReceiveLock, 1, B_DO_NOT_RESCHEDULE); @@ -490,7 +492,7 @@ ssize_t TCPEndpoint::ReadAvailable() { - TRACE(("TCP:%p.ReadAvailable()\n", this)); + TRACE("ReadAvailable()"); RecursiveLocker locker(fLock); return _AvailableBytesOrDisconnect(); @@ -706,8 +708,8 @@ int32 TCPEndpoint::Receive(tcp_segment_header &segment, net_buffer *buffer) { - TRACE(("TCP:%p.Receive(): Connection in state %d received packet %p (%lu bytes) with flags 0x%x, seq %lu, ack %lu!\n", - this, fState, buffer, buffer->size, segment.flags, segment.sequence, segment.acknowledge)); + TRACE("Receive(): Connection in state %d received packet %p (%lu bytes) with flags 0x%x, seq %lu, ack %lu!", + fState, buffer, buffer->size, segment.flags, segment.sequence, segment.acknowledge); // TODO: rethink locking! @@ -726,7 +728,7 @@ // this is a pure acknowledge segment - we're on the sending end if (fSendUnacknowledged < segment.acknowledge && fSendMax >= segment.acknowledge) { - TRACE(("TCP:%p.Receive(): header prediction send!\n", this)); + TRACE("Receive(): header prediction send!"); // and it only acknowledges outstanding data // TODO: update RTT estimators @@ -749,12 +751,11 @@ } else if (segment.acknowledge == fSendUnacknowledged && fReceiveQueue.IsContiguous() && fReceiveQueue.Free() >= buffer->size) { - TRACE(("TCP:%p.Receive(): header prediction receive!\n", this)); + TRACE("Receive(): header prediction receive!"); // we're on the receiving end of the connection, and this segment // is the one we were expecting, in-sequence fReceiveNext += buffer->size; - TRACE(("TCP:%p.Receive(): receive next = %lu!\n", - this, (uint32)fReceiveNext)); + TRACE("Receive(): receive next = %lu", (uint32)fReceiveNext); fReceiveQueue.Add(buffer, segment.sequence); release_sem_etc(fReceiveLock, 1, B_DO_NOT_RESCHEDULE); @@ -810,7 +811,7 @@ } // remove duplicate data at the start - TRACE(("* remove %ld bytes from the start\n", drop)); + TRACE("* remove %ld bytes from the start", drop); gBufferModule->remove_header(buffer, drop); segment.sequence += drop; } @@ -835,7 +836,7 @@ } segment.flags &= ~(TCP_FLAG_FINISH | TCP_FLAG_PUSH); - TRACE(("* remove %ld bytes from the end\n", drop)); + TRACE("* remove %ld bytes from the end", drop); gBufferModule->remove_trailer(buffer, drop); } @@ -864,7 +865,7 @@ // TODO: handle this! if (buffer->size == 0 && advertisedWindow == fSendWindow && (segment.flags & TCP_FLAG_FINISH) == 0) { - TRACE(("TCP:%p.Receive(): duplicate ack!\n", this)); + TRACE("Receive(): duplicate ack!"); fDuplicateAcknowledgeCount++; gStackModule->cancel_timer(&fRetransmitTimer); @@ -881,10 +882,10 @@ // there is no outstanding data to be acknowledged // TODO: if the transmit timer function is already waiting // to acquire this endpoint's lock, we should stop it anyway - TRACE(("TCP:%p.Receive(): all inflight data ack'd!\n", this)); + TRACE("Receive(): all inflight data ack'd!"); gStackModule->cancel_timer(&fRetransmitTimer); } else { - TRACE(("TCP:%p.Receive(): set retransmit timer!\n", this)); + TRACE("Receive(): set retransmit timer!"); // TODO: set retransmit timer correctly if (!gStackModule->is_timer_active(&fRetransmitTimer)) gStackModule->set_timer(&fRetransmitTimer, 1000000LL); @@ -898,7 +899,7 @@ if (segment.acknowledge > fSendQueue.LastSequence() && fState > ESTABLISHED) { // our TCP_FLAG_FINISH has been acknowledged - TRACE(("TCP:%p.Receive(): FIN has been acknowledged!\n", this)); + TRACE("Receive(): FIN has been acknowledged!"); switch (fState) { case FINISH_SENT: @@ -928,7 +929,7 @@ // TODO: ignore data *after* FIN if (segment.flags & TCP_FLAG_FINISH) { - TRACE(("TCP:%p.Receive(): peer is finishing connection!\n", this)); + TRACE("Receive(): peer is finishing connection!"); fReceiveNext++; fFlags |= FLAG_NO_RECEIVE; @@ -963,7 +964,7 @@ if (buffer->size > 0 || (segment.flags & (TCP_FLAG_SYNCHRONIZE | TCP_FLAG_FINISH)) != 0) action |= ACKNOWLEDGE; - TRACE(("TCP %p.Receive():Entering state %d, segment action %ld\n", this, fState, action)); + TRACE("Receive():Entering state %d, segment action %ld", fState, action); // state machine is done switching states and the data is good. // put it in the receive buffer @@ -971,7 +972,7 @@ if (buffer->size > 0) { fReceiveQueue.Add(buffer, segment.sequence); fReceiveNext = fReceiveQueue.NextSequence(); - TRACE(("TCP %p.Receive(): adding data, receive next = %lu!\n", this, (uint32)fReceiveNext)); + TRACE("Receive(): adding data, receive next = %lu!", (uint32)fReceiveNext); release_sem_etc(fReceiveLock, 1, B_DO_NOT_RESCHEDULE); // TODO: real conditional locking needed! @@ -1134,10 +1135,10 @@ gAddressModule->set_to((sockaddr *)&buffer->source, (sockaddr *)&socket->address); gAddressModule->set_to((sockaddr *)&buffer->destination, (sockaddr *)&socket->peer); - TRACE(("TCP:%p.SendQueued() flags %x, buffer %p, size %lu, from address %s to %s\n", this, + TRACE("SendQueued() flags %x, buffer %p, size %lu, from address %s to %s", segment.flags, buffer, buffer->size, AddressString(gDomain, (sockaddr *)&buffer->source, true).Data(), - AddressString(gDomain, (sockaddr *)&buffer->destination, true).Data())); + AddressString(gDomain, (sockaddr *)&buffer->destination, true).Data()); uint32 size = buffer->size; if (length > 0 && fSendNext + segmentLength == fSendQueue.LastSequence()) { From hugosantos at mail.berlios.de Tue Apr 3 19:36:12 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Tue, 3 Apr 2007 19:36:12 +0200 Subject: [Haiku-commits] r20540 - haiku/trunk/src/add-ons/kernel/network/protocols/tcp Message-ID: <200704031736.l33HaCGI029420@sheep.berlios.de> Author: hugosantos Date: 2007-04-03 19:35:56 +0200 (Tue, 03 Apr 2007) New Revision: 20540 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20540&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp Log: implemented SO_LINGER support in TCP Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-03 16:54:07 UTC (rev 20539) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-03 17:35:56 UTC (rev 20540) @@ -1,10 +1,11 @@ /* - * Copyright 2006, Haiku, Inc. All Rights Reserved. + * Copyright 2006-2007, Haiku, Inc. All Rights Reserved. * Distributed under the terms of the MIT License. * * Authors: * Andrew Galante, haiku.galante at gmail.com * Axel D?rfler, axeld at pinc-software.de + * Hugo Santos, hugosantos at gmail.com */ @@ -177,6 +178,28 @@ } TRACE("Close(): Entering state %d", fState); + + if (socket->options & SO_LINGER) { + TRACE("Close(): Lingering for %i secs", socket->linger); + + bigtime_t maximum = system_time() + socket->linger * 1000000LL; + + while (fSendQueue.Used() > 0) { + lock.Unlock(); + status = acquire_sem_etc(fSendLock, 1, B_CAN_INTERRUPT + | B_ABSOLUTE_TIMEOUT, maximum); + if (status == B_TIMED_OUT) { + TRACE("Close(): Lingering made me wait, but not all data was sent."); + return B_OK; + } else if (status < B_OK) + return status; + + lock.Lock(); + } + + TRACE("Close(): Waited for all data to be sent with success"); + } + // TODO: do i need to wait until fState returns to CLOSED? return B_OK; } From korli at mail.berlios.de Tue Apr 3 20:27:25 2007 From: korli at mail.berlios.de (korli at BerliOS) Date: Tue, 3 Apr 2007 20:27:25 +0200 Subject: [Haiku-commits] r20541 - in haiku/trunk/src/add-ons/kernel/drivers/network: bcm440x bcm570x Message-ID: <200704031827.l33IRPPt000590@sheep.berlios.de> Author: korli Date: 2007-04-03 20:27:24 +0200 (Tue, 03 Apr 2007) New Revision: 20541 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20541&view=rev Modified: haiku/trunk/src/add-ons/kernel/drivers/network/bcm440x/b44um.c haiku/trunk/src/add-ons/kernel/drivers/network/bcm570x/b57um.c Log: implemented ETHER_GETLINKSTATE for bcm440x and bcm570x Modified: haiku/trunk/src/add-ons/kernel/drivers/network/bcm440x/b44um.c =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/network/bcm440x/b44um.c 2007-04-03 17:35:56 UTC (rev 20540) +++ haiku/trunk/src/add-ons/kernel/drivers/network/bcm440x/b44um.c 2007-04-03 18:27:24 UTC (rev 20541) @@ -9,6 +9,9 @@ #include "mempool.h" #include +#ifdef HAIKU_TARGET_PLATFORM_HAIKU +# include +#endif #include #include @@ -241,12 +244,36 @@ b44_LM_SetReceiveMask(&pUmDevice->lm_dev, pUmDevice->lm_dev.ReceiveMask & ~LM_PROMISCUOUS_MODE); return B_OK; +#ifndef HAIKU_TARGET_PLATFORM_HAIKU case ETHER_GETLINKSTATE: { ether_link_state_t *state_buffer = (ether_link_state_t *)(data); state_buffer->link_speed = (pUmDevice->lm_dev.LineSpeed == LM_LINE_SPEED_10MBPS) ? 10 : 100; state_buffer->link_quality = (pUmDevice->lm_dev.LinkStatus == LM_STATUS_LINK_DOWN) ? 0.0 : 1.0; state_buffer->duplex_mode = (pUmDevice->lm_dev.DuplexMode == LM_DUPLEX_MODE_FULL); } return B_OK; +#else + case ETHER_GETLINKSTATE: + { + ether_link_state_t state; + state.link_media = (pUmDevice->lm_dev.LinkStatus == LM_STATUS_LINK_DOWN) ? IFM_ACTIVE : 0; + switch (pUmDevice->lm_dev.LineSpeed) { + case LM_LINE_SPEED_10MBPS: + state.link_media |= IFM_10_T; + state.link_speed = 10000; + break; + case LM_LINE_SPEED_100MBPS: + state.link_media |= IFM_100_TX; + state.link_speed = 100000; + break; + default: + state.link_speed = 0; + } + state.link_media |= (pUmDevice->lm_dev.DuplexMode == LM_DUPLEX_MODE_FULL ? IFM_FULL_DUPLEX : IFM_HALF_DUPLEX); + state.link_quality = 1000; + + return user_memcpy(data, &state, sizeof(ether_link_state_t)); + } +#endif } return B_ERROR; } Modified: haiku/trunk/src/add-ons/kernel/drivers/network/bcm570x/b57um.c =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/network/bcm570x/b57um.c 2007-04-03 17:35:56 UTC (rev 20540) +++ haiku/trunk/src/add-ons/kernel/drivers/network/bcm570x/b57um.c 2007-04-03 18:27:24 UTC (rev 20541) @@ -3,6 +3,10 @@ #include #include +#ifdef HAIKU_TARGET_PLATFORM_HAIKU +# include +#endif + #include "mm.h" #include "lm.h" #include "mempool.h" @@ -477,6 +481,7 @@ pUmDevice->lm_dev.ReceiveMask & ~LM_PROMISCUOUS_MODE); } return B_OK; +#ifndef HAIKU_TARGET_PLATFORM_HAIKU case ETHER_GETLINKSTATE: { ether_link_state_t *state_buffer = (ether_link_state_t *)(data); state_buffer->link_speed = pUmDevice->lm_dev.LineSpeed; @@ -484,6 +489,33 @@ state_buffer->duplex_mode = (pUmDevice->lm_dev.DuplexMode == LM_DUPLEX_MODE_FULL); return B_OK; } +#else + case ETHER_GETLINKSTATE: + { + ether_link_state_t state; + state.link_media = (pUmDevice->lm_dev.LinkStatus == LM_STATUS_LINK_DOWN) ? IFM_ACTIVE : 0; + switch (pUmDevice->lm_dev.LineSpeed) { + case LM_LINE_SPEED_10MBPS: + state.link_media |= IFM_10_T; + state.link_speed = 10000; + break; + case LM_LINE_SPEED_100MBPS: + state.link_media |= IFM_100_TX; + state.link_speed = 100000; + break; + case LM_LINE_SPEED_1000MBPS: + state.link_media |= IFM_1000_T; + state.link_speed = 1000000; + break; + default: + state.link_speed = 0; + } + state.link_media |= (pUmDevice->lm_dev.DuplexMode == LM_DUPLEX_MODE_FULL ? IFM_FULL_DUPLEX : IFM_HALF_DUPLEX); + state.link_quality = 1000; + + return user_memcpy(data, &state, sizeof(ether_link_state_t)); + } +#endif } return B_ERROR; } From korli at users.berlios.de Tue Apr 3 20:30:18 2007 From: korli at users.berlios.de (=?ISO-8859-1?Q?J=E9r=F4me_Duval?=) Date: Tue, 3 Apr 2007 20:30:18 +0200 Subject: [Haiku-commits] r20428 - haiku/trunk/src/add-ons/kernel/bus_managers/usb In-Reply-To: <200703261955.l2QJtdLl000810@sheep.berlios.de> References: <200703261955.l2QJtdLl000810@sheep.berlios.de> Message-ID: Hi Michael, 2007/3/26, mmlr at BerliOS : > Author: mmlr > Date: 2007-03-26 21:55:37 +0200 (Mon, 26 Mar 2007) > New Revision: 20428 > ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20428&view=rev > > Modified: > haiku/trunk/src/add-ons/kernel/bus_managers/usb/Transfer.cpp > Log: > Try at fixing build for gcc4 suggested by Axel. Does that work? > Works fine. Bye, J?r?me From hugosantos at mail.berlios.de Tue Apr 3 20:38:53 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Tue, 3 Apr 2007 20:38:53 +0200 Subject: [Haiku-commits] r20542 - haiku/trunk/src/add-ons/kernel/network/protocols/tcp Message-ID: <200704031838.l33IcrXZ001603@sheep.berlios.de> Author: hugosantos Date: 2007-04-03 20:38:42 +0200 (Tue, 03 Apr 2007) New Revision: 20542 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20542&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h Log: TCP: initial shutdown() implementation and some general fixes * set FLAG_NO_RECEIVE/FLAG_NO_SEND on shutdown() and send FIN on SHUT_WR * if a send() is attempted with FLAG_NO_SEND set return EPIPE * proper handling of recv timeout in ReadData(), using absolute timeout instead of relative * if FLAG_NO_RECEIVE is set, don't attached more segments to the receive queue, drop them instead Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-03 18:27:24 UTC (rev 20541) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-03 18:38:42 UTC (rev 20542) @@ -59,6 +59,7 @@ FLAG_OPTION_WINDOW_SHIFT = 0x01, FLAG_OPTION_TIMESTAMP = 0x02, FLAG_NO_RECEIVE = 0x04, + FLAG_NO_SEND = 0x08, }; @@ -162,20 +163,9 @@ return B_OK; } - tcp_state previousState = fState; - - if (fState == SYNCHRONIZE_RECEIVED || fState == ESTABLISHED) - fState = FINISH_SENT; - else if (fState == FINISH_RECEIVED) - fState = WAIT_FOR_FINISH_ACKNOWLEDGE; - else - fState = CLOSED; - - status_t status = _SendQueued(); - if (status != B_OK) { - fState = previousState; + status_t status = _ShutdownEgress(true); + if (status != B_OK) return status; - } TRACE("Close(): Entering state %d", fState); @@ -381,9 +371,18 @@ status_t TCPEndpoint::Shutdown(int direction) { - TRACE("Shutdown()"); - // TODO: implement shutdown! - return B_ERROR; + TRACE("Shutdown(%i)", direction); + + RecursiveLocker lock(fLock); + + if (direction == SHUT_RD || direction == SHUT_RDWR) { + fFlags |= FLAG_NO_RECEIVE; + } + + if (direction == SHUT_WR || direction == SHUT_RDWR) + _ShutdownEgress(false); + + return B_OK; } @@ -396,6 +395,13 @@ TRACE("SendData(buffer %p, size %lu, flags %lx)", buffer, buffer->size, buffer->flags); + RecursiveLocker lock(fLock); + + if (fFlags & FLAG_NO_SEND) { + // TODO: send SIGPIPE signal to app? + return EPIPE; + } + size_t bytesLeft = buffer->size; do { @@ -413,17 +419,15 @@ } else chunk = buffer; - recursive_lock_lock(&fLock); - while (fSendQueue.Free() < chunk->size) { - recursive_lock_unlock(&fLock); + lock.Unlock(); status_t status = acquire_sem_etc(fSendLock, 1, B_RELATIVE_TIMEOUT | B_CAN_INTERRUPT, socket->send.timeout); if (status < B_OK) return status; - recursive_lock_lock(&fLock); + lock.Lock(); } // TODO: check state! @@ -438,8 +442,6 @@ status_t status = _SendQueued(); - recursive_lock_unlock(&fLock); - if (buffer != chunk) { // as long as we didn't eat the buffer, we can still return an error code // (we don't own the buffer if we return an error code) @@ -491,17 +493,23 @@ // read data out of buffer // TODO: add support for urgent data (MSG_OOB) // TODO: wait until enough bytes are available + + bigtime_t timeout = system_time() + socket->receive.timeout; + + RecursiveLocker locker(fLock); + do { - // TODO: we may wait much longer than the time we wanted to... + locker.Unlock(); + status_t status = acquire_sem_etc(fReceiveLock, 1, - B_RELATIVE_TIMEOUT | B_CAN_INTERRUPT, socket->receive.timeout); + B_ABSOLUTE_TIMEOUT | B_CAN_INTERRUPT, timeout); if (status < B_OK) return status; + + locker.Lock(); } while (fReceiveQueue.Available() < socket->receive.low_water_mark - && (fFlags & FLAG_NO_RECEIVE) == 0); + && (fFlags & FLAG_NO_RECEIVE) == 0); - RecursiveLocker locker(fLock); - TRACE("ReadData(): read %lu bytes, %lu are available", numBytes, fReceiveQueue.Available()); @@ -777,15 +785,20 @@ TRACE("Receive(): header prediction receive!"); // we're on the receiving end of the connection, and this segment // is the one we were expecting, in-sequence - fReceiveNext += buffer->size; - TRACE("Receive(): receive next = %lu", (uint32)fReceiveNext); - fReceiveQueue.Add(buffer, segment.sequence); + if (fFlags & FLAG_NO_RECEIVE) { + return DROP; + } else { + fReceiveNext += buffer->size; + TRACE("Receive(): receive next = %lu", (uint32)fReceiveNext); + fReceiveQueue.Add(buffer, segment.sequence); - release_sem_etc(fReceiveLock, 1, B_DO_NOT_RESCHEDULE); - // TODO: real conditional locking needed! - gSocketModule->notify(socket, B_SELECT_READ, fReceiveQueue.Available()); + release_sem_etc(fReceiveLock, 1, B_DO_NOT_RESCHEDULE); + // TODO: real conditional locking needed! + gSocketModule->notify(socket, B_SELECT_READ, + fReceiveQueue.Available()); - return KEEP | ACKNOWLEDGE; + return KEEP | ACKNOWLEDGE; + } } } @@ -1256,6 +1269,32 @@ } +status_t +TCPEndpoint::_ShutdownEgress(bool closing) +{ + tcp_state previousState = fState; + + if (fState == SYNCHRONIZE_RECEIVED || fState == ESTABLISHED) + fState = FINISH_SENT; + else if (fState == FINISH_RECEIVED) + fState = WAIT_FOR_FINISH_ACKNOWLEDGE; + else if (closing) + fState = CLOSED; + else + return B_OK; + + status_t status = _SendQueued(); + if (status != B_OK) { + fState = previousState; + return status; + } + + fFlags |= FLAG_NO_SEND; + + return B_OK; +} + + // #pragma mark - timer Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h 2007-04-03 18:27:24 UTC (rev 20541) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h 2007-04-03 18:38:42 UTC (rev 20542) @@ -67,6 +67,7 @@ status_t _SendQueued(bool force = false); int _GetMSS(const struct sockaddr *) const; ssize_t _AvailableBytesOrDisconnect() const; + status_t _ShutdownEgress(bool closing); static void _TimeWaitTimer(net_timer *timer, void *data); static void _RetransmitTimer(net_timer *timer, void *data); From hugosantos at mail.berlios.de Tue Apr 3 20:50:35 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Tue, 3 Apr 2007 20:50:35 +0200 Subject: [Haiku-commits] r20543 - haiku/trunk/src/bin/strace Message-ID: <200704031850.l33IoZkD002752@sheep.berlios.de> Author: hugosantos Date: 2007-04-03 20:50:27 +0200 (Tue, 03 Apr 2007) New Revision: 20543 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20543&view=rev Modified: haiku/trunk/src/bin/strace/NetworkTypes.cpp haiku/trunk/src/bin/strace/TypeHandler.h Log: gcc 4 compilation fixes. Patch by Jerome Duval. Modified: haiku/trunk/src/bin/strace/NetworkTypes.cpp =================================================================== --- haiku/trunk/src/bin/strace/NetworkTypes.cpp 2007-04-03 18:38:42 UTC (rev 20542) +++ haiku/trunk/src/bin/strace/NetworkTypes.cpp 2007-04-03 18:50:27 UTC (rev 20543) @@ -91,7 +91,7 @@ template<> string -TypeHandlerImpl::GetParameterValue(Context &context, Parameter *, +TypeHandlerImpl::GetParameterValue(Context &context, Parameter *, const void *address) { void *data = *(void **)address; @@ -102,7 +102,7 @@ template<> string -TypeHandlerImpl::GetReturnValue(Context &context, uint64 value) +TypeHandlerImpl::GetReturnValue(Context &context, uint64 value) { return context.FormatPointer((void *)value); } @@ -120,7 +120,7 @@ } static string -get_ipv4_address(struct in_addr *addr) +get_ipv4_address(in_addr *addr) { char tmp[32]; snprintf(tmp, sizeof(tmp), "%u.%u.%u.%u", @@ -196,7 +196,7 @@ { string r; - struct sockaddr_in *sin = (struct sockaddr_in *)saddr; + sockaddr_in *sin = (sockaddr_in *)saddr; r = format_socket_family(context, saddr->sa_family) + ", "; @@ -220,7 +220,7 @@ { string r; - r = "addr = " + format_pointer_value(context, args->address); + r = "addr = " + format_pointer_value(context, args->address); r += ", len = " + context.FormatUnsigned(args->address_length); return r; @@ -234,7 +234,7 @@ r = "data = " + context.FormatPointer(args->data); r += ", len = " + context.FormatUnsigned(args->data_length); r += ", flags = " + context.FormatFlags(args->flags); - r += ", addr = " + format_pointer_value(context, args->address); + r += ", addr = " + format_pointer_value(context, args->address); return r; } @@ -370,7 +370,7 @@ } static string -get_iovec(Context &context, struct iovec *iov, int iovlen) +get_iovec(Context &context, iovec *iov, int iovlen) { string r = "{"; r += context.FormatPointer(iov); @@ -383,7 +383,7 @@ { string r; - r = "name = " + format_pointer_value(context, h->msg_name); + r = "name = " + format_pointer_value(context, h->msg_name); r += ", name_len = " + context.FormatUnsigned(h->msg_namelen); r += ", iov = " + get_iovec(context, h->msg_iov, h->msg_iovlen); r += ", control = " + context.FormatPointer(h->msg_control); @@ -473,11 +473,11 @@ return new SpecializedPointerTypeHandler(); \ } -DEFINE_TYPE(fdset_ptr, struct fd_set *); -POINTER_TYPE(sockaddr_args_ptr, struct sockaddr_args); -POINTER_TYPE(transfer_args_ptr, struct transfer_args); -POINTER_TYPE(sockopt_args_ptr, struct sockopt_args); -POINTER_TYPE(socket_args_ptr, struct socket_args); -POINTER_TYPE(msghdr_ptr, struct msghdr); -POINTER_TYPE(ifreq_ptr, struct ifreq); -POINTER_TYPE(ifconf_ptr, struct ifconf); +DEFINE_TYPE(fdset_ptr, fd_set *); +POINTER_TYPE(sockaddr_args_ptr, sockaddr_args); +POINTER_TYPE(transfer_args_ptr, transfer_args); +POINTER_TYPE(sockopt_args_ptr, sockopt_args); +POINTER_TYPE(socket_args_ptr, socket_args); +POINTER_TYPE(msghdr_ptr, msghdr); +POINTER_TYPE(ifreq_ptr, ifreq); +POINTER_TYPE(ifconf_ptr, ifconf); Modified: haiku/trunk/src/bin/strace/TypeHandler.h =================================================================== --- haiku/trunk/src/bin/strace/TypeHandler.h 2007-04-03 18:38:42 UTC (rev 20542) +++ haiku/trunk/src/bin/strace/TypeHandler.h 2007-04-03 18:50:27 UTC (rev 20543) @@ -97,14 +97,22 @@ } \ } \ -DEFINE_FACTORY(fdset_ptr, struct fd_set *); -DEFINE_FACTORY(sockaddr_args_ptr, struct sockaddr_args *); -DEFINE_FACTORY(transfer_args_ptr, struct transfer_args *); -DEFINE_FACTORY(sockopt_args_ptr, struct sockopt_args *); -DEFINE_FACTORY(socket_args_ptr, struct socket_args *); -DEFINE_FACTORY(ifreq_ptr, struct ifreq *); -DEFINE_FACTORY(ifconf_ptr, struct ifconf *); +struct fd_set; +struct ifconf; +struct ifreq; +struct sockaddr_args; +struct socket_args; +struct sockopt_args; +struct transfer_args; +DEFINE_FACTORY(fdset_ptr, fd_set *); +DEFINE_FACTORY(sockaddr_args_ptr, sockaddr_args *); +DEFINE_FACTORY(transfer_args_ptr, transfer_args *); +DEFINE_FACTORY(sockopt_args_ptr, sockopt_args *); +DEFINE_FACTORY(socket_args_ptr, socket_args *); +DEFINE_FACTORY(ifreq_ptr, ifreq *); +DEFINE_FACTORY(ifconf_ptr, ifconf *); + DEFINE_FACTORY(int_ptr, int *); DEFINE_FACTORY(long_ptr, long *); DEFINE_FACTORY(longlong_ptr, long long *); From marcusoverhagen at arcor.de Tue Apr 3 21:58:56 2007 From: marcusoverhagen at arcor.de (Marcus Overhagen) Date: Tue, 3 Apr 2007 21:58:56 +0200 (CEST) Subject: [Haiku-commits] r20538 - In-Reply-To: <200704031639.l33GdhLw029466@sheep.berlios.de> References: <200704031639.l33GdhLw029466@sheep.berlios.de> Message-ID: <22843158.1175630336674.JavaMail.ngmail@webmail13> axeld at BerliOS wrote: > * Fixed compilation due to removed ether_init_params from ether_driver.h, thanks > to Hugo for reporting :-) what happens to R5 drivers that now no longer have ETHER_INIT called? regards Marcus Viel oder wenig? Schnell oder langsam? Unbegrenzt surfen + telefonieren ohne Zeit- und Volumenbegrenzung? DAS TOP ANGEBOT JETZT bei Arcor: g?nstig und schnell mit DSL - das All-Inclusive-Paket f?r clevere Doppel-Sparer, nur 39,85 ? inkl. DSL- und ISDN-Grundgeb?hr! http://www.arcor.de/rd/emf-dsl-2 From axeld at pinc-software.de Tue Apr 3 22:09:45 2007 From: axeld at pinc-software.de (Axel =?iso-8859-15?q?D=F6rfler?=) Date: Tue, 03 Apr 2007 22:09:45 +0200 CEST Subject: [Haiku-commits] r20538 - In-Reply-To: <22843158.1175630336674.JavaMail.ngmail@webmail13> Message-ID: <35508908676-BeMail@zon> Marcus Overhagen wrote: > axeld at BerliOS wrote: > > * Fixed compilation due to removed ether_init_params from > > ether_driver.h, thanks to Hugo for reporting :-) > what happens to R5 drivers that now no longer have ETHER_INIT called? Probably nothing. I think we should just give it a try; if it fails, we can easily include it again. Bye, Axel. From bonefish at mail.berlios.de Wed Apr 4 03:27:51 2007 From: bonefish at mail.berlios.de (bonefish at BerliOS) Date: Wed, 4 Apr 2007 03:27:51 +0200 Subject: [Haiku-commits] r20544 - in haiku/trunk/docs/user: . drivers Message-ID: <200704040127.l341Rpgx013568@sheep.berlios.de> Author: bonefish Date: 2007-04-04 03:27:50 +0200 (Wed, 04 Apr 2007) New Revision: 20544 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20544&view=rev Added: haiku/trunk/docs/user/drivers/ haiku/trunk/docs/user/drivers/drivers.dox haiku/trunk/docs/user/drivers/fs_interface.dox haiku/trunk/docs/user/drivers/fs_modules.dox Modified: haiku/trunk/docs/user/Doxyfile haiku/trunk/docs/user/book.dox Log: Started documenting the FS API a bit. Modified: haiku/trunk/docs/user/Doxyfile =================================================================== --- haiku/trunk/docs/user/Doxyfile 2007-04-03 18:50:27 UTC (rev 20543) +++ haiku/trunk/docs/user/Doxyfile 2007-04-04 01:27:50 UTC (rev 20544) @@ -460,9 +460,11 @@ # with spaces. INPUT = . \ + drivers \ midi \ midi2 \ support \ + ../../headers/os/drivers/fs_interface.h \ ../../headers/os/midi2 \ ../../headers/os/support \ ../../headers/posix/syslog.h Modified: haiku/trunk/docs/user/book.dox =================================================================== --- haiku/trunk/docs/user/book.dox 2007-04-03 18:50:27 UTC (rev 20543) +++ haiku/trunk/docs/user/book.dox 2007-04-04 01:27:50 UTC (rev 20544) @@ -3,6 +3,7 @@ \section kits Kits and Servers + - \ref drivers - \ref midi1 - \ref midi2 | \link midi2_intro \em Introduction \endlink - \ref support | \link support_intro \em Introduction \endlink @@ -15,6 +16,7 @@ ///// Define main kits ///// /*! + \defgroup drivers Drivers \defgroup midi2 MIDI 2 Kit \brief API for producing and consuming MIDI events. \defgroup libmidi2 (libmidi2.so) @@ -29,4 +31,4 @@ /*! \defgroup support_globals Global functions in the support kit \ingroup support -*/ \ No newline at end of file +*/ Added: haiku/trunk/docs/user/drivers/drivers.dox =================================================================== --- haiku/trunk/docs/user/drivers/drivers.dox 2007-04-03 18:50:27 UTC (rev 20543) +++ haiku/trunk/docs/user/drivers/drivers.dox 2007-04-04 01:27:50 UTC (rev 20544) @@ -0,0 +1,8 @@ +/*! +\page drivers Drivers + +\section topics Topics + +- \ref fs_modules + +*/ Added: haiku/trunk/docs/user/drivers/fs_interface.dox =================================================================== --- haiku/trunk/docs/user/drivers/fs_interface.dox 2007-04-03 18:50:27 UTC (rev 20543) +++ haiku/trunk/docs/user/drivers/fs_interface.dox 2007-04-04 01:27:50 UTC (rev 20544) @@ -0,0 +1,173 @@ +/*! +\file fs_interface.h +\ingroup drivers +*/ + +/*! +\fn status_t new_vnode(mount_id mountID, vnode_id vnodeID, fs_vnode privateNode) +\brief Creates the vnode with ID \a vnodeID and associates it with the private + data handle \a privateNode, but leaves is in an unpublished state. + +The effect of the function is similar to publish_vnode(), but the vnode +remains in an unpublished state, with the effect that a subsequent +remove_vnode() will just delete the vnode and not invoke the file system's +\link file_system_module_info::remove_vnode remove_vnode() \endlink is not +invoked. + +If the vnode shall be kept, publish_vnode() has to be invoked afterwards to +mark the vnode published. The combined effect is the same as only invoking +publish_vnode(). + +The function fails, if the vnode does already exist. + +\param mountID The ID of the volume. +\param vnodeID The ID of the node. +\param privateNode The private data handle to be associated with the node. +\return \c B_OK if everything went fine, another error code otherwise. +*/ + +/*! +\fn status_t publish_vnode(mount_id mountID, vnode_id vnodeID, + fs_vnode privateNode) +\brief Creates the vnode with ID \a vnodeID and associates it with the private + data handle \a privateNode or just marks it published. + +If the vnode does already exist and has been published, the function fails. +If it has not been published yet (i.e. after a successful new_vnode()), the +function just marks the vnode published. If the vnode did not exist at all +before, it is created and published. + +If the function is successful, the caller owns a reference to the vnode. A +sequence of new_vnode() and publish_vnode() results in just one reference as +well. The reference can be surrendered by calling put_vnode(). + +\param mountID The ID of the volume. +\param vnodeID The ID of the node. +\param privateNode The private data handle to be associated with the node. +\return \c B_OK if everything went fine, another error code otherwise. +*/ + +/*! +\fn status_t get_vnode(mount_id mountID, vnode_id vnodeID, + fs_vnode *_privateNode) +\brief Retrieves the private data handle for the node with the given ID. + +If the function is successful, the caller owns a reference to the vnode. The +reference can be surrendered by calling put_vnode(). + +\param mountID The ID of the volume. +\param vnodeID The ID of the node. +\param _privateNode Pointer to a pre-allocated variable the private data + handle shall be written to. +\return \c B_OK if everything went fine, another error code otherwise. +*/ + +/*! +\fn status_t put_vnode(mount_id mountID, vnode_id vnodeID) +\brief Surrenders a reference to the specified vnode. +\param mountID The ID of the volume. +\param vnodeID The ID of the node. +\return \c B_OK if everything went fine, another error code otherwise. +*/ + +/*! +\fn status_t remove_vnode(mount_id mountID, vnode_id vnodeID) +\brief Marks the specified vnode removed. + +The caller must own a reference to the vnode or at least ensure that a +reference to the vnode exists. The function does not surrender a reference, +though. + +As soon as the last reference to the vnode has been surrendered, the VFS +invokes the file system's +\link file_system_module_info::remove_vnode remove_vnode() \endlink +hook. + +\param mountID The ID of the volume. +\param vnodeID The ID of the node. +\return \c B_OK if everything went fine, another error code otherwise. +*/ + +/*! +\fn status_t unremove_vnode(mount_id mountID, vnode_id vnodeID); +\brief Clears the "removed" mark of the specified vnode. + +The caller must own a reference to the vnode or at least ensure that a +reference to the vnode exists. + +The function is usually called when the caller, who has invoked remove_vnode() +before realizes that it is not possible to remove the node (e.g. due to an +error). + +\param mountID The ID of the volume. +\param vnodeID The ID of the node. +\return \c B_OK if everything went fine, another error code otherwise. +*/ + +/*! +\fn status_t get_vnode_removed(mount_id mountID, vnode_id vnodeID, + bool* removed); +\brief Returns whether the specified vnode is marked removed. + +The caller must own a reference to the vnode or at least ensure that a +reference to the vnode exists. + +\param mountID The ID of the volume. +\param vnodeID The ID of the node. +\param removed Pointer to a pre-allocated variable set to \c true, if the + node is marked removed, to \c false otherwise. +\return \c B_OK if everything went fine, another error code otherwise. +*/ + + +/*! +\class file_system_module_info +\brief Kernel module interface for file systems. +*/ + +/*! +\fn status_t (*file_system_module_info::get_vnode)(fs_volume fs, vnode_id id, + fs_vnode *_vnode, bool reenter) +\brief Creates the private data handle to be associated with the node referred + to by \a id. + +Invoked by the VFS when it creates the vnode for the respective node. + +\param fs The volume handle. +\param id The ID of the node. +\param _vnode Pointer to a pre-allocated variable the private data handle + shall be written to. +\param reenter \c true if the hook invocation has been caused by the FS itself, + e.g. by invoking ::get_vnode(). +\return \c B_OK if everything went fine, another error code otherwise. +*/ + +/*! +\fn \fn status_t (*file_system_module_info::put_vnode)(fs_volume fs, + fs_vnode vnode, bool reenter) +\brief Deletes the private data handle associated with the specified node. + +Invoked by the VFS when it deletes the vnode for the respective node and the +node is not marked removed. + +\param fs The volume handle. +\param vnode The private data handle for the node. +\param reenter \c true if the hook invocation has been caused by the FS itself, + e.g. by invoking ::put_vnode(). +\return \c B_OK if everything went fine, another error code otherwise. +*/ + +/*! +\fn status_t (*file_system_module_info::remove_vnode)(fs_volume fs, + fs_vnode vnode, bool reenter); +\brief Deletes the private data handle associated with the specified node. + +Invoked by the VFS when it deletes the vnode for the respective node and the +node is marked removed. + +\param fs The volume handle. +\param vnode The private data handle for the node. +\param reenter \c true if the hook invocation has been caused by the FS itself, + e.g. by invoking ::put_vnode(). +\return \c B_OK if everything went fine, another error code otherwise. +*/ Added: haiku/trunk/docs/user/drivers/fs_modules.dox =================================================================== --- haiku/trunk/docs/user/drivers/fs_modules.dox 2007-04-03 18:50:27 UTC (rev 20543) +++ haiku/trunk/docs/user/drivers/fs_modules.dox 2007-04-04 01:27:50 UTC (rev 20544) @@ -0,0 +1,123 @@ +/*! +\page fs_modules File System Modules + +To support a particular file system (FS), a kernel module implementing a special +interface (\c file_system_module_info defined in \c ) has to be +provided. As for any other module the +\c std_ops() hook is invoked with \c B_MODULE_INIT directly after the FS module +has been loaded by the kernel, and with \c B_MODULE_UNINIT before it is +unloaded, thus providing a simple mechanism for one-time module initializations. +The same module is used for accessing any volume of that FS type. + + +\section objects File System Objects + +There are several types of objects a FS module has to deal with directly or +indirectly: + +- A \em volume is an instance of a file system. For a disk-based file + system it corresponds to a disk, partition, or disk image file. When + mounting a volume the virtual file system layer (VFS) assigns a unique number + (ID, of type \c mount_id aka \c dev_t) to it and a handle (type + \c fs_volume, in fact \c void*) provided by + the file system. Whenever the FS requests a volume-related service from the + kernel, it has to pass the volume ID, and whenever the VFS asks the FS to + perform an operation, it supplies the handle. Normally the handle is a pointer + to a data structure the FS allocates to associate data with the volume. + +- A \em node is contained by a volume. It can be of type file, directory, or + symbolic link (symlink). Just as volumes nodes are associated with an ID + (type \c vnode_id aka ino_t) and, if in use, also with a handle + (type \c fs_vnode, in fact \c void*). + Unlike the volume ID the node ID is defined by the FS. It often + has a meaning to the FS, e.g. file systems using inodes might choose the + inode number corresponding to the node. As long as the volume is mounted and + the node is known to the VFS, its node ID must not change. The node handle is + again a pointer to a data structure allocated by the FS. + +- A \em vnode (VFS node) is the VFS representation of a node. A volume may + contain a great number of nodes, but at a time only a few are represented by + vnodes, usually only those that are currently in use (sometimes a few more). + +- An \em entry (directory entry) belongs to a directory, has a name, and refers + to a node. It is important to understand the difference between entries and + nodes: A node doesn't have a name, only the entries that refer to it have. + If a FS supports to have more than one entry refer to a single node, it is + also said to support "hard links". It is possible that no entry refers + to a node. This happens when a node (e.g. a file) is still open, but the last + entry referring to it has been removed (the node will be deleted when the + it is closed). While entries are to be understood as independent entities, + the FS interface does not use IDs or handles to refer to them; it always uses + directory and entry name pairs to do that. + +- An \em attribute is a named and typed data container belonging to a node. A + node may have any number of attributes; they are organized in a (virtual or + actually existing) attribute directory, through which one can iterate. + +- An \em index is supposed to provide fast searching capabilities for attributes + with a certain name. A volume's index directory allows for iterating through + the indices. + +- A \em query is a fully virtual object for searching for entries via an + expression matching entry name, node size, node modification date, and/or + node attributes. The mechanism of retrieving the entries found by a query + is similar to that for reading a directory contents. A query can be live + in which case the creator of the query is notified by the FS whenever an + entry no longer matches the query expression or starts matching. + + +\section concepts Generic Concepts + +A FS module has to (or can) provide quite a lot of hook functions. There are +a few concepts that apply to several groups of them: + +- Opening, Closing, and Cookies: Many FS objects can be opened and + closed, namely nodes in general, directories, attribute directories, + attributes, the index directory, and queries. In each case there are three + hook functions: open*(), close*(), and + free*_cookie(). The open*() hook is passed all that is + needed to identify the object to be opened and, in some cases, additional + parameters e.g. specifying a particular opening mode. The implementation + is required to return a cookie (type \c fs_cookie, in fact \c void*), usually + a pointer to a data structure the FS allocates. In some cases (e.g. when an + iteration state is associated with the cookie) a new cookie must be allocated + for each instance of opening the object. The cookie is passed to all hooks + that operate on a thusly opened object. The close*() hook is invoked + to signal that the cookie is to be closed. At this point the cookie might + still be in use. Blocking FS hooks (e.g. blocking read/write operations) + using the same cookie have to be unblocked. When the cookie stops being in + use the free*_cookie() hook is called; it has to free the cookie. + +- Entry Iteration: For the FS objects serving as containers for other + objects, i.e. directories, attribute directories, the index directory, + and queries, the cookie mechanism is used for a stateful iteration through + the contained objects. The read_*() hook reads the next one or more + entries into a struct dirent buffer. The rewind_*() hook + resets the iteration state to the first entry. + +- Stat Information: In case of nodes, attributes, and indices + detailed information about an object are requested via a read*_stat() + hook and must be written into a struct stat buffer. + + +\section vnodes VNodes + +A vnode is the VFS representation of a node. As soon as an access to a node +is requested, the VFS creates a corresponding vnode. The requesting entity +gets a reference to the vnode for the time it works with the vnode and +releases the reference when done. When the last reference to a vnode has been +surrendered, the vnode is unused and the VFS can decide to destroy it (usually +it is cached for a while longer). + +When the VFS creates a vnode, it invokes the FS's +\link file_system_module_info::get_vnode get_vnode() \endlink +hook to let it create the respective node handle (unless the FS requests the +creation of the vnode explicitely by calling publish_vnode()). That's the only +hook that specifies a node by ID; to all other node-related hooks the node +handle is passed. When the VFS deletes the vnode, it invokes the FS's +\link file_system_module_info::put_vnode put_vnode() \endlink +hook or, if the node was marked removed, +\link file_system_module_info::remove_vnode remove_vnode() \endlink. + +*/ + From axeld at mail.berlios.de Wed Apr 4 09:34:08 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Wed, 4 Apr 2007 09:34:08 +0200 Subject: [Haiku-commits] r20545 - buildtools/trunk/jam Message-ID: <200704040734.l347Y8aZ010464@sheep.berlios.de> Author: axeld Date: 2007-04-04 09:34:07 +0200 (Wed, 04 Apr 2007) New Revision: 20545 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20545&view=rev Modified: buildtools/trunk/jam/jam.h Log: I couldn't do a full clean build without this any longer using Linux and GCC 2.95.3 (Archive action too long), YMMV. Modified: buildtools/trunk/jam/jam.h =================================================================== --- buildtools/trunk/jam/jam.h 2007-04-04 01:27:50 UTC (rev 20544) +++ buildtools/trunk/jam/jam.h 2007-04-04 07:34:07 UTC (rev 20545) @@ -458,7 +458,7 @@ */ # ifndef MAXLINE -# define MAXLINE 20480 /* longest 'together' actions' */ +# define MAXLINE 40960 /* longest 'together' actions' */ # endif # ifndef EXITOK From axeld at pinc-software.de Wed Apr 4 10:30:41 2007 From: axeld at pinc-software.de (Axel =?iso-8859-15?q?D=F6rfler?=) Date: Wed, 04 Apr 2007 10:30:41 +0200 CEST Subject: [Haiku-commits] r20544 - in haiku/trunk/docs/user: . drivers In-Reply-To: <200704040127.l341Rpgx013568@sheep.berlios.de> Message-ID: <1014603796-BeMail@zon> bonefish at BerliOS wrote: > Log: > Started documenting the FS API a bit. Lovely, thanks! Bye, Axel. From revol at free.fr Wed Apr 4 10:56:21 2007 From: revol at free.fr (=?windows-1252?q?Fran=E7ois?= Revol) Date: Wed, 04 Apr 2007 10:56:21 +0200 CEST Subject: [Haiku-commits] =?windows-1252?q?r20535_-_in_haiku/trunk/headers?= =?windows-1252?q?=3A_posix/net_private/net?= In-Reply-To: <200704031442.l33Eg9LM003562@sheep.berlios.de> Message-ID: <1420941304-BeMail@laptop> > Log: > * Rewrote ether_driver.h, removed some BONE stuff we don't support > at this point; Is it a reason to remove ? While the timestamp stuff is only used for tcpdump things (more precise than stamping outside the driver because of queueing), the iovec one could help improve speed by removing the copy op used to make a contig buffer to pass to write(). The if_type stuff was added by me to distinguish between drivers that do implement the ether_driver.h ioctls and those that don't (yes some do! like the speedtouch usb, which is of atm type), but it doesn't seem to be the best way though, something like naming the device /dev/net/ [atm|.11|...]// would make more sense. But IFNAMSIZ is limited, so it must be done carefully. Maybe using uppercase to distinguish from driver names, but it goes against conventions. We could also use /dev/ net/%02x/ with the numeric if_type. BONE used link-layer protocol modules stacked on top of the device (like ether framing), and making the diff in the interface module could allow stacking a PPPoA on the usbspeedtouch for ex. The other option is to change them to not publish under /dev/net/ but it seems as incorrect. Fran?ois. From revol at free.fr Wed Apr 4 10:58:09 2007 From: revol at free.fr (=?windows-1252?q?Fran=E7ois?= Revol) Date: Wed, 04 Apr 2007 10:58:09 +0200 CEST Subject: [Haiku-commits] r20536 - haiku/trunk/src/add-ons/kernel/drivers/network/sis900 In-Reply-To: <20471374357-BeMail@zon> Message-ID: <1528719004-BeMail@laptop> > "Waldemar Kornewald" wrote: > > > Log: > > > * Implemented ETHER_GETLINKSTATE; the link state is now tracked > > > and can be reported. > > You're my personal hero! :) I've always wished that the system has > > a > > way to automatically recognize when it must reconfigure an > > interface. > > Now, we need this in every ethernet driver. ;) > > Do you know if other drivers already support this feature? Or is > > this > > a Haiku-only function? > > It was supposed to be a BONE extension, but I implemented it It was a NathanWhitehorn extention AFAIK :) Fran?ois. From revol at free.fr Wed Apr 4 11:00:46 2007 From: revol at free.fr (=?windows-1252?q?Fran=E7ois?= Revol) Date: Wed, 04 Apr 2007 11:00:46 +0200 CEST Subject: [Haiku-commits] =?windows-1252?q?r20538_-_haiku/trunk/src/add-ons?= =?windows-1252?q?/kernel/network/devices/ethernet?= In-Reply-To: <200704031639.l33GdhLw029466@sheep.berlios.de> Message-ID: <1686014412-BeMail@laptop> > Author: axeld > Date: 2007-04-03 18:39:30 +0200 (Tue, 03 Apr 2007) > New Revision: 20538 > ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20538&view=rev > > Modified: > haiku/trunk/src/add-ons/kernel/network/devices/ethernet/ > ethernet.cpp > Log: > * Fixed compilation due to removed ether_init_params from > ether_driver.h, > thanks to Hugo for reporting :-) I seem to remember at least one driver using the INIT ioctl to trigger some stuff, so not calling it might actually break it. Probably in BONE though so if we rewrite that... Fran?ois. From axeld at mail.berlios.de Wed Apr 4 11:41:06 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Wed, 4 Apr 2007 11:41:06 +0200 Subject: [Haiku-commits] r20546 - in haiku/trunk: headers/private/net src/add-ons/kernel/drivers/network/bcm440x src/add-ons/kernel/drivers/network/bcm570x src/add-ons/kernel/drivers/network/ipro1000 src/add-ons/kernel/drivers/network/sis900 src/add-ons/kernel/network/devices/ethernet src/add-ons/kernel/network/stack Message-ID: <200704040941.l349f6hY017950@sheep.berlios.de> Author: axeld Date: 2007-04-04 11:41:04 +0200 (Wed, 04 Apr 2007) New Revision: 20546 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20546&view=rev Modified: haiku/trunk/headers/private/net/ether_driver.h haiku/trunk/headers/private/net/net_device.h haiku/trunk/headers/private/net/net_stack.h haiku/trunk/src/add-ons/kernel/drivers/network/bcm440x/b44um.c haiku/trunk/src/add-ons/kernel/drivers/network/bcm570x/b57um.c haiku/trunk/src/add-ons/kernel/drivers/network/ipro1000/device.c haiku/trunk/src/add-ons/kernel/drivers/network/sis900/device.c haiku/trunk/src/add-ons/kernel/network/devices/ethernet/ethernet.cpp haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp haiku/trunk/src/add-ons/kernel/network/stack/domains.cpp haiku/trunk/src/add-ons/kernel/network/stack/domains.h haiku/trunk/src/add-ons/kernel/network/stack/interfaces.cpp haiku/trunk/src/add-ons/kernel/network/stack/interfaces.h haiku/trunk/src/add-ons/kernel/network/stack/stack.cpp Log: * Changed ETHER_GET_LINK_STATE ethernet driver interface, added ETHER_SET_LINK_STATE_SEM. * The device interface list now uses class DoublyLinkedList instead of struct list. * Implemented SIOC[SG]IFMEDIA for setting (not supported by any device yet), and retrieving the device media information. * Fixed a locking bug in list_domain_interfaces(). * Added new stack function device_link_changed() that should be called in case the link state (media) changed. * The ethernet device module now spawns a thread and will periodically check the media state of all ethernet devices that support this (if any). * Minor cleanup. Modified: haiku/trunk/headers/private/net/ether_driver.h =================================================================== --- haiku/trunk/headers/private/net/ether_driver.h 2007-04-04 07:34:07 UTC (rev 20545) +++ haiku/trunk/headers/private/net/ether_driver.h 2007-04-04 09:41:04 UTC (rev 20546) @@ -21,21 +21,23 @@ ETHER_REMMULTI, /* remove multicast address */ ETHER_SETPROMISC, /* set promiscuous mode (int *) */ ETHER_GETFRAMESIZE, /* get frame size (required) (int *) */ - ETHER_GETLINKSTATE + ETHER_SET_LINK_STATE_SEM, + /* pass over a semaphore to release on link state changes (sem_id *) */ + ETHER_GET_LINK_STATE /* get line speed, quality, duplex mode, etc. (ether_link_state_t *) */ }; /* ETHER_GETADDR - MAC address */ -typedef struct { - uint8 ebyte[6]; +typedef struct ether_address { + uint8 ebyte[6]; } ether_address_t; /* ETHER_GETLINKSTATE */ typedef struct ether_link_state { - uint32 link_media; /* as specified in net/if_media.h */ - uint32 link_quality; /* in one tenth of a percent */ - uint64 link_speed; /* in Kbit/s */ + uint32 media; /* as specified in net/if_media.h */ + uint32 quality; /* in one tenth of a percent */ + uint64 speed; /* in Kbit/s */ } ether_link_state_t; #endif /* _ETHER_DRIVER_H */ Modified: haiku/trunk/headers/private/net/net_device.h =================================================================== --- haiku/trunk/headers/private/net/net_device.h 2007-04-04 07:34:07 UTC (rev 20545) +++ haiku/trunk/headers/private/net/net_device.h 2007-04-04 09:41:04 UTC (rev 20546) @@ -1,5 +1,5 @@ /* - * Copyright 2006, Haiku, Inc. All Rights Reserved. + * Copyright 2006-2007, Haiku, Inc. All Rights Reserved. * Distributed under the terms of the MIT License. */ #ifndef NET_DEVICE_H @@ -25,6 +25,8 @@ uint32 type; // IFT_ETHER, ... size_t mtu; uint32 media; + uint64 link_speed; + uint32 link_quality; size_t header_length; struct net_hardware_address address; @@ -44,8 +46,10 @@ status_t (*control)(struct net_device *device, int32 op, void *argument, size_t length); - status_t (*send_data)(struct net_device *device, struct net_buffer *buffer); - status_t (*receive_data)(struct net_device *device, struct net_buffer **_buffer); + status_t (*send_data)(struct net_device *device, + struct net_buffer *buffer); + status_t (*receive_data)(struct net_device *device, + struct net_buffer **_buffer); status_t (*set_mtu)(struct net_device *device, size_t mtu); status_t (*set_promiscuous)(struct net_device *device, bool promiscuous); Modified: haiku/trunk/headers/private/net/net_stack.h =================================================================== --- haiku/trunk/headers/private/net/net_stack.h 2007-04-04 07:34:07 UTC (rev 20545) +++ haiku/trunk/headers/private/net/net_stack.h 2007-04-04 09:41:04 UTC (rev 20546) @@ -1,5 +1,5 @@ /* - * Copyright 2006, Haiku, Inc. All Rights Reserved. + * Copyright 2006-2007, Haiku, Inc. All Rights Reserved. * Distributed under the terms of the MIT License. */ #ifndef NET_STACK_H @@ -72,6 +72,7 @@ status_t (*unregister_device_monitor)(struct net_device *device, net_receive_func receiveFunc, void *cookie); + status_t (*device_link_changed)(struct net_device *device); status_t (*device_removed)(struct net_device *device); // Utility Functions Modified: haiku/trunk/src/add-ons/kernel/drivers/network/bcm440x/b44um.c =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/network/bcm440x/b44um.c 2007-04-04 07:34:07 UTC (rev 20545) +++ haiku/trunk/src/add-ons/kernel/drivers/network/bcm440x/b44um.c 2007-04-04 09:41:04 UTC (rev 20546) @@ -1,5 +1,5 @@ /* - * Copyright 2006, Nathan Whitehorn. + * Copyright 2006-2007, Nathan Whitehorn. * Distributed under the terms of the GPL License. */ @@ -237,40 +237,45 @@ case ETHER_REMMULTI: return (b44_LM_MulticastDel(&pUmDevice->lm_dev,(PLM_UINT8)(data)) == LM_STATUS_SUCCESS) ? B_OK : B_ERROR; case ETHER_SETPROMISC: - if (*((uint8 *)(data))) + if (*((uint8 *)(data))) { b44_LM_SetReceiveMask(&pUmDevice->lm_dev, pUmDevice->lm_dev.ReceiveMask | LM_PROMISCUOUS_MODE); - else + } else { b44_LM_SetReceiveMask(&pUmDevice->lm_dev, pUmDevice->lm_dev.ReceiveMask & ~LM_PROMISCUOUS_MODE); + } return B_OK; #ifndef HAIKU_TARGET_PLATFORM_HAIKU - case ETHER_GETLINKSTATE: { + case ETHER_GETLINKSTATE: + { ether_link_state_t *state_buffer = (ether_link_state_t *)(data); state_buffer->link_speed = (pUmDevice->lm_dev.LineSpeed == LM_LINE_SPEED_10MBPS) ? 10 : 100; state_buffer->link_quality = (pUmDevice->lm_dev.LinkStatus == LM_STATUS_LINK_DOWN) ? 0.0 : 1.0; state_buffer->duplex_mode = (pUmDevice->lm_dev.DuplexMode == LM_DUPLEX_MODE_FULL); - } return B_OK; + return B_OK; + } #else - case ETHER_GETLINKSTATE: + case ETHER_GET_LINK_STATE: { ether_link_state_t state; - state.link_media = (pUmDevice->lm_dev.LinkStatus == LM_STATUS_LINK_DOWN) ? IFM_ACTIVE : 0; + state.media = (pUmDevice->lm_dev.LinkStatus + == LM_STATUS_LINK_DOWN) ? IFM_ACTIVE : 0; switch (pUmDevice->lm_dev.LineSpeed) { case LM_LINE_SPEED_10MBPS: - state.link_media |= IFM_10_T; - state.link_speed = 10000; + state.media |= IFM_10_T; + state.speed = 10000; break; case LM_LINE_SPEED_100MBPS: - state.link_media |= IFM_100_TX; - state.link_speed = 100000; + state.media |= IFM_100_TX; + state.speed = 100000; break; default: - state.link_speed = 0; + state.speed = 0; } - state.link_media |= (pUmDevice->lm_dev.DuplexMode == LM_DUPLEX_MODE_FULL ? IFM_FULL_DUPLEX : IFM_HALF_DUPLEX); - state.link_quality = 1000; - + state.media |= (pUmDevice->lm_dev.DuplexMode + == LM_DUPLEX_MODE_FULL ? IFM_FULL_DUPLEX : IFM_HALF_DUPLEX); + state.quality = 1000; + return user_memcpy(data, &state, sizeof(ether_link_state_t)); } #endif Modified: haiku/trunk/src/add-ons/kernel/drivers/network/bcm570x/b57um.c =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/network/bcm570x/b57um.c 2007-04-04 07:34:07 UTC (rev 20545) +++ haiku/trunk/src/add-ons/kernel/drivers/network/bcm570x/b57um.c 2007-04-04 09:41:04 UTC (rev 20546) @@ -482,7 +482,8 @@ } return B_OK; #ifndef HAIKU_TARGET_PLATFORM_HAIKU - case ETHER_GETLINKSTATE: { + case ETHER_GETLINKSTATE: + { ether_link_state_t *state_buffer = (ether_link_state_t *)(data); state_buffer->link_speed = pUmDevice->lm_dev.LineSpeed; state_buffer->link_quality = (pUmDevice->lm_dev.LinkStatus == LM_STATUS_LINK_DOWN) ? 0.0 : 1.0; @@ -490,28 +491,30 @@ return B_OK; } #else - case ETHER_GETLINKSTATE: + case ETHER_GET_LINK_STATE: { ether_link_state_t state; - state.link_media = (pUmDevice->lm_dev.LinkStatus == LM_STATUS_LINK_DOWN) ? IFM_ACTIVE : 0; + state.media = (pUmDevice->lm_dev.LinkStatus + == LM_STATUS_LINK_DOWN) ? IFM_ACTIVE : 0; switch (pUmDevice->lm_dev.LineSpeed) { case LM_LINE_SPEED_10MBPS: - state.link_media |= IFM_10_T; - state.link_speed = 10000; + state.media |= IFM_10_T; + state.speed = 10000; break; case LM_LINE_SPEED_100MBPS: - state.link_media |= IFM_100_TX; - state.link_speed = 100000; + state.media |= IFM_100_TX; + state.speed = 100000; break; case LM_LINE_SPEED_1000MBPS: - state.link_media |= IFM_1000_T; - state.link_speed = 1000000; + state.media |= IFM_1000_T; + state.speed = 1000000; break; default: - state.link_speed = 0; + state.speed = 0; } - state.link_media |= (pUmDevice->lm_dev.DuplexMode == LM_DUPLEX_MODE_FULL ? IFM_FULL_DUPLEX : IFM_HALF_DUPLEX); - state.link_quality = 1000; + state.media |= (pUmDevice->lm_dev.DuplexMode + == LM_DUPLEX_MODE_FULL ? IFM_FULL_DUPLEX : IFM_HALF_DUPLEX); + state.quality = 1000; return user_memcpy(data, &state, sizeof(ether_link_state_t)); } Modified: haiku/trunk/src/add-ons/kernel/drivers/network/ipro1000/device.c =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/network/ipro1000/device.c 2007-04-04 07:34:07 UTC (rev 20545) +++ haiku/trunk/src/add-ons/kernel/drivers/network/ipro1000/device.c 2007-04-04 09:41:04 UTC (rev 20546) @@ -339,15 +339,15 @@ #ifdef HAIKU_TARGET_PLATFORM_HAIKU #if 0 - case ETHER_GETLINKSTATE: + case ETHER_GET_LINK_STATE: { ether_link_state_t state; - state.link_media = (info->link ? IFM_ACTIVE : 0) + state.media = (info->link ? IFM_ACTIVE : 0) | (info->full_duplex ? IFM_FULL_DUPLEX : IFM_HALF_DUPLEX) | (info->speed == LINK_SPEED_100_MBIT ? IFM_100_TX : IFM_10_T); - state.link_speed = info->speed == LINK_SPEED_100_MBIT + state.speed = info->speed == LINK_SPEED_100_MBIT ? 100000 : 10000; - state.link_quality = 1000; + state.quality = 1000; return user_memcpy(buffer, &state, sizeof(ether_link_state_t)); } Modified: haiku/trunk/src/add-ons/kernel/drivers/network/sis900/device.c =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/network/sis900/device.c 2007-04-04 07:34:07 UTC (rev 20545) +++ haiku/trunk/src/add-ons/kernel/drivers/network/sis900/device.c 2007-04-04 09:41:04 UTC (rev 20546) @@ -387,15 +387,15 @@ break; #ifdef HAIKU_TARGET_PLATFORM_HAIKU - case ETHER_GETLINKSTATE: + case ETHER_GET_LINK_STATE: { ether_link_state_t state; - state.link_media = (info->link ? IFM_ACTIVE : 0) + state.media = (info->link ? IFM_ACTIVE : 0) | (info->full_duplex ? IFM_FULL_DUPLEX : IFM_HALF_DUPLEX) | (info->speed == LINK_SPEED_100_MBIT ? IFM_100_TX : IFM_10_T); - state.link_speed = info->speed == LINK_SPEED_100_MBIT + state.speed = info->speed == LINK_SPEED_100_MBIT ? 100000 : 10000; - state.link_quality = 1000; + state.quality = 1000; return user_memcpy(buffer, &state, sizeof(ether_link_state_t)); } Modified: haiku/trunk/src/add-ons/kernel/network/devices/ethernet/ethernet.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/devices/ethernet/ethernet.cpp 2007-04-04 07:34:07 UTC (rev 20545) +++ haiku/trunk/src/add-ons/kernel/network/devices/ethernet/ethernet.cpp 2007-04-04 09:41:04 UTC (rev 20546) @@ -7,11 +7,17 @@ */ +#include + #include -#include #include #include +#include +#include +#include +#include + #include #include @@ -24,14 +30,78 @@ #include -struct ethernet_device : net_device { +struct ethernet_device : DoublyLinkedListLinkImpl, net_device { int fd; uint32 frame_size; }; -struct net_buffer_module_info *gBufferModule; +static const bigtime_t kLinkCheckInterval = 1000000; + // 1 second +net_buffer_module_info *gBufferModule; +static net_stack_module_info *sStackModule; +static benaphore sListLock; +static DoublyLinkedList sCheckList; +static sem_id sLinkChangeSemaphore; +static thread_id sLinkCheckerThread; + + +static status_t +update_link_state(ethernet_device *device, bool notify = true) +{ + ether_link_state state; + if (ioctl(device->fd, ETHER_GET_LINK_STATE, &state, + sizeof(ether_link_state)) < 0) { + // This device does not support retrieving the link + return EOPNOTSUPP; + } + + if (device->media != state.media + || device->link_quality != state.quality + || device->link_speed != state.speed) { + device->media = state.media; + device->link_quality = state.quality; + device->link_speed = state.speed; + + if (notify) + sStackModule->device_link_changed(device); + } + + return B_OK; +} + + +static status_t +ethernet_link_checker(void *) +{ + while (true) { + status_t status = acquire_sem_etc(sLinkChangeSemaphore, 1, + B_RELATIVE_TIMEOUT, kLinkCheckInterval); + if (status == B_BAD_SEM_ID) + break; + + BenaphoreLocker _(sListLock); + + if (sCheckList.IsEmpty()) + break; + + // check link state of all existing devices + + DoublyLinkedList::Iterator iterator + = sCheckList.GetIterator(); + while (iterator.HasNext()) { + update_link_state(iterator.Next()); + } + } + + return B_OK; +} + + +// #pragma mark - + + status_t ethernet_init(const char *name, net_device **_device) { @@ -93,6 +163,27 @@ device->frame_size = ETHER_MAX_FRAME_SIZE; } + if (update_link_state(device, false) == B_OK) { + // device supports retrieval of the link state + + // Set the change notification semaphore; doesn't matter + // if this is supported by the device or not + ioctl(device->fd, ETHER_SET_LINK_STATE_SEM, &sLinkChangeSemaphore, + sizeof(sem_id *)); + + BenaphoreLocker _(&sListLock); + + if (sCheckList.IsEmpty()) { + // start thread + sLinkCheckerThread = spawn_kernel_thread(ethernet_link_checker, + "ethernet link state checker", B_LOW_PRIORITY, NULL); + if (sLinkCheckerThread >= B_OK) + resume_thread(sLinkCheckerThread); + } + + sCheckList.Add(device); + } + device->address.length = ETHER_ADDRESS_LENGTH; device->mtu = device->frame_size - device->header_length; return B_OK; @@ -108,6 +199,14 @@ ethernet_down(net_device *_device) { ethernet_device *device = (ethernet_device *)_device; + + BenaphoreLocker _(sListLock); + + // if the device is still part of the list, remove it + if (device->GetDoublyLinkedListLink()->next != NULL + || device->GetDoublyLinkedListLink()->previous != NULL) + sCheckList.Remove(device); + close(device->fd); } @@ -262,6 +361,7 @@ ethernet_get_multicast_addrs(struct net_device *device, net_hardware_address **addressArray, uint32 count) { + // TODO: see etherpci driver for details return EOPNOTSUPP; } @@ -270,6 +370,7 @@ ethernet_set_multicast_addrs(struct net_device *device, const net_hardware_address **addressArray, uint32 count) { + // TODO: see etherpci driver for details return EOPNOTSUPP; } @@ -279,8 +380,44 @@ { switch (op) { case B_MODULE_INIT: + { + status_t status = get_module(NET_STACK_MODULE_NAME, + (module_info **)&sStackModule); + if (status < B_OK) + return status; + + new (&sCheckList) DoublyLinkedList; + // static C++ objects are not initialized in the module startup + + sLinkCheckerThread = -1; + + sLinkChangeSemaphore = create_sem(0, "ethernet link change"); + if (sLinkChangeSemaphore < B_OK) { + put_module(NET_STACK_MODULE_NAME); + return sLinkChangeSemaphore; + } + + status = benaphore_init(&sListLock, "ethernet devices"); + if (status < B_OK) { + put_module(NET_STACK_MODULE_NAME); + delete_sem(sLinkChangeSemaphore); + return status; + } + + return B_OK; + } + case B_MODULE_UNINIT: + { + delete_sem(sLinkChangeSemaphore); + + status_t status; + wait_for_thread(sLinkCheckerThread, &status); + + benaphore_destroy(&sListLock); + put_module(NET_STACK_MODULE_NAME); return B_OK; + } default: return B_ERROR; Modified: haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp 2007-04-04 07:34:07 UTC (rev 20545) +++ haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp 2007-04-04 09:41:04 UTC (rev 20546) @@ -18,6 +18,7 @@ #include #include +#include #include #include @@ -54,7 +55,8 @@ // feed device monitors // TODO: locking! - DeviceMonitorList::Iterator iterator = interface->monitor_funcs.GetIterator(); + DeviceMonitorList::Iterator iterator + = interface->monitor_funcs.GetIterator(); while (iterator.HasNext()) { net_device_monitor *monitor = iterator.Next(); monitor->func(monitor->cookie, buffer); @@ -64,7 +66,8 @@ if (type >= 0) { // find handler for this packet // TODO: locking! - DeviceHandlerList::Iterator iterator = interface->receive_funcs.GetIterator(); + DeviceHandlerList::Iterator iterator + = interface->receive_funcs.GetIterator(); status = B_ERROR; while (iterator.HasNext()) { @@ -135,7 +138,8 @@ route.gateway = NULL; route.interface = interface; - if (interface->mask != NULL && (option == SIOCSIFNETMASK || option == SIOCSIFADDR)) { + if (interface->mask != NULL + && (option == SIOCSIFNETMASK || option == SIOCSIFADDR)) { route.mask = interface->mask; route.flags = 0; remove_route(interface->domain, &route); @@ -157,7 +161,8 @@ route.gateway = NULL; route.interface = interface; - if (interface->mask != NULL && (option == SIOCSIFNETMASK || option == SIOCSIFADDR)) { + if (interface->mask != NULL + && (option == SIOCSIFNETMASK || option == SIOCSIFADDR)) { route.mask = interface->mask; route.flags = 0; add_route(interface->domain, &route); @@ -324,16 +329,22 @@ if (interface != NULL) { // filter out bringing the interface up or down if (option == SIOCSIFFLAGS - && ((uint32)request.ifr_flags & IFF_UP) != (interface->flags & IFF_UP)) { + && ((uint32)request.ifr_flags & IFF_UP) + != (interface->flags & IFF_UP)) { if ((interface->flags & IFF_UP) != 0) { // bring the interface down - interface->flags &= ~IFF_UP; - interface->first_info->interface_down(interface->first_protocol); + interface->flags &= ~(IFF_UP | IFF_LINK); + interface->first_info->interface_down( + interface->first_protocol); } else { // bring it up - status = interface->first_info->interface_up(interface->first_protocol); - if (status == B_OK) - interface->flags |= IFF_UP; + status = interface->first_info->interface_up( + interface->first_protocol); + if (status == B_OK) { + interface->flags |= IFF_UP + | (interface->device->media & IFM_ACTIVE + ? IFF_LINK : 0); + } } request.ifr_flags = interface->flags; @@ -341,8 +352,8 @@ if (status == B_OK) { // pass the request into the datalink protocol stack - status = interface->first_info->control(interface->first_protocol, - option, value, *_length); + status = interface->first_info->control( + interface->first_protocol, option, value, *_length); } } else status = B_BAD_VALUE; @@ -704,13 +715,34 @@ return B_BAD_ADDRESS; // check for valid bounds - if (request.ifr_mtu < 100 || (uint32)request.ifr_mtu > interface->device->mtu) + if (request.ifr_mtu < 100 + || (uint32)request.ifr_mtu > interface->device->mtu) return B_BAD_VALUE; interface->mtu = request.ifr_mtu; return B_OK; } + case SIOCSIFMEDIA: + { + // set media + struct ifreq request; + if (user_memcpy(&request, argument, sizeof(struct ifreq)) < B_OK) + return B_BAD_ADDRESS; + + return interface->device_interface->module->set_media( + interface->device, request.ifr_media); + } + case SIOCGIFMEDIA: + { + // get media + struct ifreq request; + request.ifr_media = interface->device->media; + + return user_memcpy(&((struct ifreq *)argument)->ifr_media, + &request.ifr_media, sizeof(request.ifr_media)); + } + case SIOCGIFMETRIC: { // get metric Modified: haiku/trunk/src/add-ons/kernel/network/stack/domains.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/domains.cpp 2007-04-04 07:34:07 UTC (rev 20545) +++ haiku/trunk/src/add-ons/kernel/network/stack/domains.cpp 2007-04-04 09:41:04 UTC (rev 20546) @@ -11,11 +11,14 @@ #include "interfaces.h" #include "utility.h" -#include +#include #include #include +#include + +#include #include #include @@ -112,6 +115,8 @@ if (domain == NULL) break; + BenaphoreLocker locker(domain->lock); + net_interface *interface = NULL; while (true) { interface = (net_interface *)list_get_next_item(&domain->interfaces, @@ -121,17 +126,18 @@ ifreq request; strlcpy(request.ifr_name, interface->name, IF_NAMESIZE); - if (interface->address != NULL) - memcpy(&request.ifr_addr, interface->address, interface->address->sa_len); - else { + if (interface->address != NULL) { + memcpy(&request.ifr_addr, interface->address, + interface->address->sa_len); + } else { // empty address request.ifr_addr.sa_len = 2; request.ifr_addr.sa_family = AF_UNSPEC; } if (buffer.Copy(&request, IF_NAMESIZE - + request.ifr_addr.sa_len) == NULL) - return buffer.Status(); + + request.ifr_addr.sa_len) == NULL) + return buffer.Status(); } } @@ -187,6 +193,38 @@ } +void +domain_interfaces_link_changed(net_device *device) +{ + // TODO: notify listeners about this! + + BenaphoreLocker locker(sDomainLock); + + net_domain_private *domain = NULL; + while (true) { + domain = (net_domain_private *)list_get_next_item(&sDomains, domain); + if (domain == NULL) + break; + + BenaphoreLocker locker(domain->lock); + + net_interface *interface = NULL; + while (true) { + interface = (net_interface *)list_get_next_item(&domain->interfaces, + interface); + if (interface == NULL) + break; + + if (interface->device == device) { + // update IFF_LINK flag + interface->flags = (interface->flags & ~IFF_LINK) + | (device->media & IFM_ACTIVE ? IFF_LINK : 0); + } + } + } +} + + status_t register_domain(int family, const char *name, struct net_protocol_module_info *module, Modified: haiku/trunk/src/add-ons/kernel/network/stack/domains.h =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/domains.h 2007-04-04 07:34:07 UTC (rev 20545) +++ haiku/trunk/src/add-ons/kernel/network/stack/domains.h 2007-04-04 09:41:04 UTC (rev 20546) @@ -33,6 +33,7 @@ status_t list_domain_interfaces(void *buffer, size_t *_bufferSize); status_t add_interface_to_domain(net_domain *domain, struct ifreq& request); status_t remove_interface_from_domain(net_interface *interface); +void domain_interfaces_link_changed(net_device *device); net_domain *get_domain(int family); status_t register_domain(int family, const char *name, Modified: haiku/trunk/src/add-ons/kernel/network/stack/interfaces.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/interfaces.cpp 2007-04-04 07:34:07 UTC (rev 20545) +++ haiku/trunk/src/add-ons/kernel/network/stack/interfaces.cpp 2007-04-04 09:41:04 UTC (rev 20546) @@ -1,5 +1,5 @@ /* - * Copyright 2006, Haiku, Inc. All Rights Reserved. + * Copyright 2006-2007, Haiku, Inc. All Rights Reserved. * Distributed under the terms of the MIT License. * * Authors: @@ -34,7 +34,7 @@ static benaphore sInterfaceLock; -static list sInterfaces; +static DeviceInterfaceList sInterfaces; static uint32 sInterfaceIndex; static uint32 sDeviceIndex; @@ -42,12 +42,10 @@ static net_device_interface * find_device_interface(const char *name) { - net_device_interface *interface = NULL; + DeviceInterfaceList::Iterator iterator = sInterfaces.GetIterator(); - while (true) { - interface = (net_device_interface *)list_get_next_item(&sInterfaces, interface); - if (interface == NULL) - break; + while (iterator.HasNext()) { + net_device_interface *interface = iterator.Next(); if (!strcmp(interface->name, name)) return interface; @@ -237,15 +235,11 @@ { BenaphoreLocker locker(sInterfaceLock); - net_device_interface *interface = NULL; + DeviceInterfaceList::Iterator iterator = sInterfaces.GetIterator(); uint32 count = 0; - while (true) { - interface = (net_device_interface *)list_get_next_item(&sInterfaces, - interface); - if (interface == NULL) - break; - + while (iterator.HasNext()) { + iterator.Next(); count++; } @@ -263,22 +257,19 @@ { BenaphoreLocker locker(sInterfaceLock); + DeviceInterfaceList::Iterator iterator = sInterfaces.GetIterator(); UserBuffer buffer(_buffer, *bufferSize); - net_device_interface *interface = NULL; - while (true) { - interface = (net_device_interface *)list_get_next_item(&sInterfaces, - interface); - if (interface == NULL) - break; + while (iterator.HasNext()) { + net_device_interface *interface = iterator.Next(); ifreq request; strlcpy(request.ifr_name, interface->name, IF_NAMESIZE); get_device_interface_address(interface, &request.ifr_addr); if (buffer.Copy(&request, IF_NAMESIZE - + request.ifr_addr.sa_len) == NULL) - return buffer.Status(); + + request.ifr_addr.sa_len) == NULL) + return buffer.Status(); } *bufferSize = buffer.ConsumedAmount(); @@ -300,7 +291,7 @@ { BenaphoreLocker locker(sInterfaceLock); - list_remove_item(&sInterfaces, interface); + sInterfaces.Remove(interface); } interface->module->uninit_device(interface->device); @@ -315,12 +306,10 @@ get_device_interface(uint32 index) { BenaphoreLocker locker(sInterfaceLock); - net_device_interface *interface = NULL; + DeviceInterfaceList::Iterator iterator = sInterfaces.GetIterator(); - while (true) { - interface = (net_device_interface *)list_get_next_item(&sInterfaces, interface); - if (interface == NULL) - break; + while (iterator.HasNext()) { + net_device_interface *interface = iterator.Next(); if (interface->device->index == index) { if (atomic_add(&interface->ref_count, 1) != 0) @@ -380,7 +369,7 @@ device->index = ++sDeviceIndex; device->module = module; - list_add_item(&sInterfaces, interface); + sInterfaces.Add(interface); return interface; } else module->uninit_device(device); @@ -590,6 +579,19 @@ /*! + This function is called by device modules in case their link + state changed, ie. if an ethernet cable was plugged in or + removed. +*/ +status_t +device_link_changed(net_device *device) +{ + domain_interfaces_link_changed(device); + return B_OK; +} + + +/*! This function is called by device modules once their device got physically removed, ie. a USB networking card is unplugged. It is part of the net_manager_module_info API. @@ -612,7 +614,8 @@ if (benaphore_init(&sInterfaceLock, "net interfaces") < B_OK) return B_ERROR; - list_init(&sInterfaces); + new (&sInterfaces) DeviceInterfaceList; + // static C++ objects are not initialized in the module startup return B_OK; } Modified: haiku/trunk/src/add-ons/kernel/network/stack/interfaces.h =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/interfaces.h 2007-04-04 07:34:07 UTC (rev 20545) +++ haiku/trunk/src/add-ons/kernel/network/stack/interfaces.h 2007-04-04 09:41:04 UTC (rev 20546) @@ -29,8 +29,8 @@ typedef DoublyLinkedList DeviceHandlerList; typedef DoublyLinkedList DeviceMonitorList; -struct net_device_interface { - struct list_link link; +struct net_device_interface : DoublyLinkedListLinkImpl { + //struct list_link link; const char *name; struct net_device_module_info *module; struct net_device *device; @@ -46,6 +46,8 @@ DeviceHandlerList receive_funcs; }; +typedef DoublyLinkedList DeviceInterfaceList; + struct net_interface_private : net_interface { char base_name[IF_NAMESIZE]; net_device_interface *device_interface; @@ -90,6 +92,7 @@ net_receive_func receiveFunc, void *cookie); status_t unregister_device_monitor(struct net_device *device, net_receive_func receiveFunc, void *cookie); +status_t device_link_changed(net_device *device); status_t device_removed(net_device *device); #endif // INTERFACES_H Modified: haiku/trunk/src/add-ons/kernel/network/stack/stack.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/stack.cpp 2007-04-04 07:34:07 UTC (rev 20545) +++ haiku/trunk/src/add-ons/kernel/network/stack/stack.cpp 2007-04-04 09:41:04 UTC (rev 20546) @@ -911,6 +911,7 @@ unregister_device_handler, register_device_monitor, unregister_device_monitor, + device_link_changed, device_removed, notify_socket, From axeld at pinc-software.de Wed Apr 4 11:55:24 2007 From: axeld at pinc-software.de (Axel =?iso-8859-15?q?D=F6rfler?=) Date: Wed, 04 Apr 2007 11:55:24 +0200 CEST Subject: [Haiku-commits] r20536 - haiku/trunk/src/add-ons/kernel/drivers/network/sis900 In-Reply-To: <1528719004-BeMail@laptop> Message-ID: <6097949812-BeMail@zon> "Fran?ois Revol" wrote: > > It was supposed to be a BONE extension, but I implemented it > It was a NathanWhitehorn extention AFAIK :) Ah, great thanks, nice to know - that explains why there were floating point values, and also means there is no point in being backwards compatible with it :-) Bye, Axel. From axeld at pinc-software.de Wed Apr 4 12:00:28 2007 From: axeld at pinc-software.de (Axel =?iso-8859-15?q?D=F6rfler?=) Date: Wed, 04 Apr 2007 12:00:28 +0200 CEST Subject: [Haiku-commits] r20535 - in haiku/trunk/headers: posix/net private/net In-Reply-To: <1420941304-BeMail@laptop> Message-ID: <6401149891-BeMail@zon> "Fran?ois Revol" wrote: > > Log: > > * Rewrote ether_driver.h, removed some BONE stuff we don't support > > at this point; > Is it a reason to remove ? Not necessarily, but we can put it back in if we want to (and need it) any time. > The if_type stuff was added by me to distinguish between drivers that > do implement the ether_driver.h ioctls and those that don't (yes some > do! like the speedtouch usb, which is of atm type), but it doesn't > seem > to be the best way though, something like naming the device /dev/net/ > [atm|.11|...]// would make more sense. But IFNAMSIZ is > limited, > so it must be done carefully. Maybe using uppercase to distinguish > from > driver names, but it goes against conventions. We could also use /dev > / > net/%02x/ with the numeric if_type. That's what I would call abuse :-) If a driver doesn't use the ether_driver.h protocol, it should be put into a different directory, like /dev/net/atm/... Likewise, it would be nice if we could move all existing ethernet devices to /dev/net/ether/... - but it seems to be too late for that. BTW it's not necessary that the name of the interface matches the one of the device driver. That's just how ifconfig does it. > BONE used link-layer protocol modules stacked on top of the device > (like ether framing), and making the diff in the interface module > could > allow stacking a PPPoA on the usbspeedtouch for ex. I'm not sure I understand what you're telling me here :-) Bye, Axel. From axeld at mail.berlios.de Wed Apr 4 12:25:36 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Wed, 4 Apr 2007 12:25:36 +0200 Subject: [Haiku-commits] r20547 - haiku/trunk/src/add-ons/kernel/network/devices/ethernet Message-ID: <200704041025.l34APabF021279@sheep.berlios.de> Author: axeld Date: 2007-04-04 12:25:35 +0200 (Wed, 04 Apr 2007) New Revision: 20547 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20547&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/devices/ethernet/ethernet.cpp Log: net_device should come first in order to guaranty it will work together nicely with C only code. Thanks Hugo! Modified: haiku/trunk/src/add-ons/kernel/network/devices/ethernet/ethernet.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/devices/ethernet/ethernet.cpp 2007-04-04 09:41:04 UTC (rev 20546) +++ haiku/trunk/src/add-ons/kernel/network/devices/ethernet/ethernet.cpp 2007-04-04 10:25:35 UTC (rev 20547) @@ -30,7 +30,7 @@ #include -struct ethernet_device : DoublyLinkedListLinkImpl, net_device { +struct ethernet_device : net_device, DoublyLinkedListLinkImpl { int fd; uint32 frame_size; }; From axeld at mail.berlios.de Wed Apr 4 13:57:34 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Wed, 4 Apr 2007 13:57:34 +0200 Subject: [Haiku-commits] r20548 - haiku/trunk/src/add-ons/translators/raw Message-ID: <200704041157.l34BvYM7007023@sheep.berlios.de> Author: axeld Date: 2007-04-04 13:57:33 +0200 (Wed, 04 Apr 2007) New Revision: 20548 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20548&view=rev Modified: haiku/trunk/src/add-ons/translators/raw/ConfigView.cpp haiku/trunk/src/add-ons/translators/raw/RAW.cpp haiku/trunk/src/add-ons/translators/raw/main.cpp Log: * Rotated images did not work correctly. * Removed ICO specific configuration, added copyright note about the source of this translator. * Disabled test mode for the build. Modified: haiku/trunk/src/add-ons/translators/raw/ConfigView.cpp =================================================================== --- haiku/trunk/src/add-ons/translators/raw/ConfigView.cpp 2007-04-04 10:25:35 UTC (rev 20547) +++ haiku/trunk/src/add-ons/translators/raw/ConfigView.cpp 2007-04-04 11:57:33 UTC (rev 20548) @@ -47,25 +47,14 @@ stringView = new BStringView(rect, "copyright", B_UTF8_COPYRIGHT "2007 Haiku Inc."); stringView->ResizeToPreferred(); AddChild(stringView); - - rect.OffsetBy(0, height + 20); - BCheckBox *checkBox = new BCheckBox(rect, "color", "Write 32 bit images on true color input", NULL); - checkBox->ResizeToPreferred(); - AddChild(checkBox); rect.OffsetBy(0, height + 10); - checkBox = new BCheckBox(rect, "size", "Enforce valid icon sizes", NULL); - checkBox->ResizeToPreferred(); - checkBox->SetValue(1); - AddChild(checkBox); - - rect.OffsetBy(0, height + 15); - stringView = new BStringView(rect, "valid1", "Valid icon sizes are 16, 32, or 48"); + stringView = new BStringView(rect, "copyright2", "Based on Dave Coffin's dcraw 8.63"); stringView->ResizeToPreferred(); AddChild(stringView); rect.OffsetBy(0, height + 5); - stringView = new BStringView(rect, "valid2", "pixel in either direction."); + stringView = new BStringView(rect, "copyright3", B_UTF8_COPYRIGHT "1997-2007 Dave Coffin"); stringView->ResizeToPreferred(); AddChild(stringView); } Modified: haiku/trunk/src/add-ons/translators/raw/RAW.cpp =================================================================== --- haiku/trunk/src/add-ons/translators/raw/RAW.cpp 2007-04-04 10:25:35 UTC (rev 20547) +++ haiku/trunk/src/add-ons/translators/raw/RAW.cpp 2007-04-04 11:57:33 UTC (rev 20548) @@ -2376,12 +2376,6 @@ void DCRaw::_WriteRGB32(image_data_info& image, uint8* outputBuffer) { - fOutputWidth = fInputWidth; - fOutputHeight = fInputHeight; - - if (image.flip & 4) - SWAP(fOutputHeight, fOutputWidth); - uint8* line, lookUpTable[0x10000]; uint32 outputRow = (4 * fOutputBitsPerSample / 8) * fOutputWidth; @@ -2398,10 +2392,13 @@ int32 sourceOffset = _FlipIndex(0, 0, image.flip); int32 colStep = _FlipIndex(0, 1, image.flip) - sourceOffset; - int32 rowStep = _FlipIndex(1, 0, image.flip) - _FlipIndex(0, fOutputWidth, image.flip); + int32 rowStep = _FlipIndex(1, 0, image.flip) + - _FlipIndex(0, fOutputWidth, image.flip); - TRACE(("flip = %ld, sourceOffset = %ld, colStep = %ld, rowStep = %ld, input: %lu x %lu, output: %lu x %lu\n", - image.flip, sourceOffset, colStep, rowStep, fInputWidth, fInputHeight, fOutputWidth, fOutputHeight)); + TRACE(("flip = %ld, sourceOffset = %ld, colStep = %ld, rowStep = %ld, " + "input: %lu x %lu, output: %lu x %lu\n", image.flip, sourceOffset, + colStep, rowStep, fInputWidth, fInputHeight, fOutputWidth, + fOutputHeight)); if (fOutputBitsPerSample == 8) { for (uint32 row = 0; row < fOutputHeight; row++, sourceOffset += rowStep) { @@ -3257,6 +3254,9 @@ fShrink = (fHalfSize || fThreshold) && fFilters; fOutputWidth = (fInputWidth + fShrink) >> fShrink; fOutputHeight = (fInputHeight + fShrink) >> fShrink; + if (image.flip & 4) + SWAP(fOutputHeight, fOutputWidth); + image.output_width = fOutputWidth; image.output_height = fOutputHeight; Modified: haiku/trunk/src/add-ons/translators/raw/main.cpp =================================================================== --- haiku/trunk/src/add-ons/translators/raw/main.cpp 2007-04-04 10:25:35 UTC (rev 20547) +++ haiku/trunk/src/add-ons/translators/raw/main.cpp 2007-04-04 11:57:33 UTC (rev 20548) @@ -10,9 +10,9 @@ #include -#define TEST_MODE 1 +#define TEST_MODE 0 #define SHOW_MODE 1 -#if SHOW_MODE +#if SHOW_MODE && TEST_MODE # include # include # include @@ -86,7 +86,7 @@ i, data.is_raw ? "RAW " : "JPEG", data.width, data.height, data.bits_per_sample, data.compression); -#if SHOW_MODE +# if SHOW_MODE if (!data.is_raw) { // write data to file uint8* buffer; @@ -132,7 +132,7 @@ wait_for_thread(window->Thread(), &status); } } -#endif +# endif } } return 0; From axeld at mail.berlios.de Wed Apr 4 14:31:50 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Wed, 4 Apr 2007 14:31:50 +0200 Subject: [Haiku-commits] r20549 - haiku/trunk/src/add-ons/translators/raw Message-ID: <200704041231.l34CVocl010434@sheep.berlios.de> Author: axeld Date: 2007-04-04 14:31:50 +0200 (Wed, 04 Apr 2007) New Revision: 20549 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20549&view=rev Modified: haiku/trunk/src/add-ons/translators/raw/RAW.cpp Log: Rotated images still didn't work correctly; they were offseted. Modified: haiku/trunk/src/add-ons/translators/raw/RAW.cpp =================================================================== --- haiku/trunk/src/add-ons/translators/raw/RAW.cpp 2007-04-04 11:57:33 UTC (rev 20548) +++ haiku/trunk/src/add-ons/translators/raw/RAW.cpp 2007-04-04 12:31:50 UTC (rev 20549) @@ -21,9 +21,9 @@ #include -//#define TRACE(x) dprintf x +//#define TRACE(x) printf x #define TRACE(x) -//#define TAG(x) dprintf x +//#define TAG(x) printf x #define TAG(x) #define ABS(x) (((int)(x) ^ ((int)(x) >> 31)) - ((int)(x) >> 31)) @@ -232,11 +232,11 @@ if (flip & 4) SWAP(row, col); if (flip & 2) - row = fOutputHeight - 1 - row; + row = fInputHeight - 1 - row; if (flip & 1) - col = fOutputWidth - 1 - col; + col = fInputWidth - 1 - col; - return row * fOutputWidth + col; + return row * fInputWidth + col; } @@ -2378,7 +2378,9 @@ { uint8* line, lookUpTable[0x10000]; - uint32 outputRow = (4 * fOutputBitsPerSample / 8) * fOutputWidth; + uint32 width = image.flip & 4 ? fOutputHeight : fOutputWidth; + uint32 height = image.flip & 4 ? fOutputWidth : fOutputHeight; + uint32 outputRow = (4 * fOutputBitsPerSample / 8) * width; uint32 outputOffset = 0; line = (uint8 *)malloc(outputRow); @@ -2393,16 +2395,16 @@ int32 sourceOffset = _FlipIndex(0, 0, image.flip); int32 colStep = _FlipIndex(0, 1, image.flip) - sourceOffset; int32 rowStep = _FlipIndex(1, 0, image.flip) - - _FlipIndex(0, fOutputWidth, image.flip); + - _FlipIndex(0, width, image.flip); TRACE(("flip = %ld, sourceOffset = %ld, colStep = %ld, rowStep = %ld, " "input: %lu x %lu, output: %lu x %lu\n", image.flip, sourceOffset, - colStep, rowStep, fInputWidth, fInputHeight, fOutputWidth, - fOutputHeight)); + colStep, rowStep, fInputWidth, fInputHeight, width, + height)); if (fOutputBitsPerSample == 8) { - for (uint32 row = 0; row < fOutputHeight; row++, sourceOffset += rowStep) { - for (uint32 col = 0; col < fOutputWidth; col++, sourceOffset += colStep) { + for (uint32 row = 0; row < height; row++, sourceOffset += rowStep) { + for (uint32 col = 0; col < width; col++, sourceOffset += colStep) { line[col * 4 + 2] = lookUpTable[fImageData[sourceOffset][0]]; line[col * 4 + 1] = lookUpTable[fImageData[sourceOffset][1]]; line[col * 4 + 0] = lookUpTable[fImageData[sourceOffset][2]]; @@ -3252,13 +3254,17 @@ image_data_info& image = fImages[index]; fShrink = (fHalfSize || fThreshold) && fFilters; - fOutputWidth = (fInputWidth + fShrink) >> fShrink; + fOutputWidth = (fInputWidth + fShrink) >> fShrink; fOutputHeight = (fInputHeight + fShrink) >> fShrink; - if (image.flip & 4) - SWAP(fOutputHeight, fOutputWidth); - image.output_width = fOutputWidth; - image.output_height = fOutputHeight; + if (image.flip & 4) { + // image is rotated + image.output_width = fOutputHeight; + image.output_height = fOutputWidth; + } else { + image.output_width = fOutputWidth; + image.output_height = fOutputHeight; + } if (image.is_raw) { bufferSize = fOutputWidth * 4 * fOutputHeight; From mmlr at mlotz.ch Wed Apr 4 14:01:09 2007 From: mmlr at mlotz.ch (Michael Lotz) Date: Wed, 04 Apr 2007 14:01:09 +0200 CEST Subject: [Haiku-commits] r20538 - haiku/trunk/src/add-ons/kernel/network/devices/ethernet In-Reply-To: <1686014412-BeMail@laptop> Message-ID: <2393772615-BeMail@primary> > > Author: axeld > > Date: 2007-04-03 18:39:30 +0200 (Tue, 03 Apr 2007) > > New Revision: 20538 > > ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20538&view=rev > > > > Modified: > > haiku/trunk/src/add-ons/kernel/network/devices/ethernet/ > > ethernet.cpp > > Log: > > * Fixed compilation due to removed ether_init_params from > > ether_driver.h, > > thanks to Hugo for reporting :-) > > I seem to remember at least one driver using the INIT ioctl to > trigger > some stuff, so not calling it might actually break it. Probably in > BONE > though so if we rewrite that... I used it in the ipw2100 driver to set the card up and start scanning for networks. It somehow made sense to trigger it there as it actually inits the interface, so I find "ETHER_INIT" fits pretty well. Can be rewritten of course, just to mention it. Regards Michael From hugosantos at mail.berlios.de Wed Apr 4 14:50:53 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Wed, 4 Apr 2007 14:50:53 +0200 Subject: [Haiku-commits] r20550 - haiku/trunk/src/bin/network/ifconfig Message-ID: <200704041250.l34CorxF012308@sheep.berlios.de> Author: hugosantos Date: 2007-04-04 14:50:44 +0200 (Wed, 04 Apr 2007) New Revision: 20550 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20550&view=rev Modified: haiku/trunk/src/bin/network/ifconfig/ifconfig.cpp Log: output IFF_LINK, IFF_AUTO_CONFIGURED and IFF_CONFIGURING flags Modified: haiku/trunk/src/bin/network/ifconfig/ifconfig.cpp =================================================================== --- haiku/trunk/src/bin/network/ifconfig/ifconfig.cpp 2007-04-04 12:31:50 UTC (rev 20549) +++ haiku/trunk/src/bin/network/ifconfig/ifconfig.cpp 2007-04-04 12:50:44 UTC (rev 20550) @@ -269,6 +269,9 @@ {IFF_PROMISC, "promiscuous"}, {IFF_ALLMULTI, "allmulti"}, {IFF_AUTOUP, "autoup"}, + {IFF_LINK, "link"}, + {IFF_AUTO_CONFIGURED, "auto-configure"}, + {IFF_CONFIGURING, "configuring"}, }; bool first = true; From hugosantos at mail.berlios.de Wed Apr 4 14:51:09 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Wed, 4 Apr 2007 14:51:09 +0200 Subject: [Haiku-commits] r20551 - in haiku/trunk: headers/posix/net src/add-ons/kernel/drivers/network/ipro1000 Message-ID: <200704041251.l34Cp9w2012390@sheep.berlios.de> Author: hugosantos Date: 2007-04-04 14:50:54 +0200 (Wed, 04 Apr 2007) New Revision: 20551 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20551&view=rev Modified: haiku/trunk/headers/posix/net/if_media.h haiku/trunk/src/add-ons/kernel/drivers/network/ipro1000/device.c haiku/trunk/src/add-ons/kernel/drivers/network/ipro1000/if_compat.h haiku/trunk/src/add-ons/kernel/drivers/network/ipro1000/if_em.c Log: ipro1000: added ETHER_GET_LINK_STATE support * use em_media_status to get link status * added IFM_1000_SX (Fiber Optic) to net/if_media.h Modified: haiku/trunk/headers/posix/net/if_media.h =================================================================== --- haiku/trunk/headers/posix/net/if_media.h 2007-04-04 12:50:44 UTC (rev 20550) +++ haiku/trunk/headers/posix/net/if_media.h 2007-04-04 12:50:54 UTC (rev 20551) @@ -29,6 +29,7 @@ #define IFM_10_T 3 /* 10Base-T - RJ45 */ #define IFM_100_TX 6 /* 100Base-TX - RJ45 */ #define IFM_1000_T 16 /* 1000Base-T - RJ45 */ +#define IFM_1000_SX 18 /* 1000Base-SX - Fiber Optic */ /* General options */ Modified: haiku/trunk/src/add-ons/kernel/drivers/network/ipro1000/device.c =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/network/ipro1000/device.c 2007-04-04 12:50:44 UTC (rev 20550) +++ haiku/trunk/src/add-ons/kernel/drivers/network/ipro1000/device.c 2007-04-04 12:50:54 UTC (rev 20551) @@ -43,6 +43,7 @@ int em_attach(device_t); int em_detach(device_t); +void em_media_status(struct ifnet *, struct ifmediareq *); static void @@ -338,21 +339,29 @@ return B_OK; #ifdef HAIKU_TARGET_PLATFORM_HAIKU -#if 0 case ETHER_GET_LINK_STATE: { + struct ifnet ifp = { .if_softc = device->adapter }; + struct ifmediareq mediareq; ether_link_state_t state; - state.media = (info->link ? IFM_ACTIVE : 0) - | (info->full_duplex ? IFM_FULL_DUPLEX : IFM_HALF_DUPLEX) - | (info->speed == LINK_SPEED_100_MBIT ? IFM_100_TX : IFM_10_T); - state.speed = info->speed == LINK_SPEED_100_MBIT - ? 100000 : 10000; + + if (len < sizeof(ether_link_state_t)) + return ENOBUFS; + + em_media_status(&ifp, &mediareq); + + state.media = mediareq.ifm_active; + if (mediareq.ifm_active & IFM_10_T) + state.speed = 10000; + else if (mediareq.ifm_active & IFM_100_TX) + state.speed = 100000; + else + state.speed = 1000000; state.quality = 1000; - return user_memcpy(buffer, &state, sizeof(ether_link_state_t)); + return user_memcpy(arg, &state, sizeof(ether_link_state_t)); } #endif -#endif default: DEVICE_DEBUGOUT("ipro1000_control() Invalid command"); Modified: haiku/trunk/src/add-ons/kernel/drivers/network/ipro1000/if_compat.h =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/network/ipro1000/if_compat.h 2007-04-04 12:50:44 UTC (rev 20550) +++ haiku/trunk/src/add-ons/kernel/drivers/network/ipro1000/if_compat.h 2007-04-04 12:50:54 UTC (rev 20551) @@ -20,6 +20,7 @@ #define __IF_COMPAT_H #include +#include #define __FreeBSD_version 500001 @@ -39,10 +40,10 @@ #define IFCAP_RXCSUM 0x0020 #ifdef HAIKU_TARGET_PLATFORM_HAIKU +# define IFM_AVALID 0 # define IFM_FDX IFM_FULL_DUPLEX # define IFM_HDX IFM_HALF_DUPLEX -# define IFM_1000_TX 17 -# define IFM_1000_SX 18 +# define IFM_1000_TX IFM_1000_T #else # define IFM_ACTIVE 0x0001 # define IFM_FDX 0x0002 Modified: haiku/trunk/src/add-ons/kernel/drivers/network/ipro1000/if_em.c =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/network/ipro1000/if_em.c 2007-04-04 12:50:44 UTC (rev 20550) +++ haiku/trunk/src/add-ons/kernel/drivers/network/ipro1000/if_em.c 2007-04-04 12:50:54 UTC (rev 20551) @@ -814,7 +814,6 @@ } -#if 0 /********************************************************************* * * Media Ioctl callback @@ -823,7 +822,7 @@ * the interface using ifconfig. * **********************************************************************/ -static void +void em_media_status(struct ifnet *ifp, struct ifmediareq *ifmr) { struct adapter * adapter = ifp->if_softc; @@ -880,6 +879,7 @@ return; } +#if 0 /********************************************************************* * * Media Ioctl callback From hugosantos at mail.berlios.de Wed Apr 4 14:51:23 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Wed, 4 Apr 2007 14:51:23 +0200 Subject: [Haiku-commits] r20552 - in haiku/trunk/src/add-ons/kernel: drivers/network/ipro1000 network/devices/ethernet Message-ID: <200704041251.l34CpNN4012407@sheep.berlios.de> Author: hugosantos Date: 2007-04-04 14:51:09 +0200 (Wed, 04 Apr 2007) New Revision: 20552 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20552&view=rev Modified: haiku/trunk/src/add-ons/kernel/drivers/network/ipro1000/device.c haiku/trunk/src/add-ons/kernel/network/devices/ethernet/ethernet.cpp Log: set IFM_ACTIVE if ipro1000 has link and output media changes on update_link_state() Modified: haiku/trunk/src/add-ons/kernel/drivers/network/ipro1000/device.c =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/network/ipro1000/device.c 2007-04-04 12:50:54 UTC (rev 20551) +++ haiku/trunk/src/add-ons/kernel/drivers/network/ipro1000/device.c 2007-04-04 12:51:09 UTC (rev 20552) @@ -351,6 +351,8 @@ em_media_status(&ifp, &mediareq); state.media = mediareq.ifm_active; + if (mediareq.ifm_status & IFM_ACTIVE) + state.media |= IFM_ACTIVE; if (mediareq.ifm_active & IFM_10_T) state.speed = 10000; else if (mediareq.ifm_active & IFM_100_TX) Modified: haiku/trunk/src/add-ons/kernel/network/devices/ethernet/ethernet.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/devices/ethernet/ethernet.cpp 2007-04-04 12:50:54 UTC (rev 20551) +++ haiku/trunk/src/add-ons/kernel/network/devices/ethernet/ethernet.cpp 2007-04-04 12:51:09 UTC (rev 20552) @@ -64,6 +64,11 @@ device->link_quality = state.quality; device->link_speed = state.speed; + dprintf("%s: media change, media 0x%0x quality %u speed %u\n", + device->name, (unsigned int)device->media, + (unsigned int)device->link_quality, + (unsigned int)device->link_speed); + if (notify) sStackModule->device_link_changed(device); } From hugosantos at mail.berlios.de Wed Apr 4 14:51:36 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Wed, 4 Apr 2007 14:51:36 +0200 Subject: [Haiku-commits] r20553 - haiku/trunk/src/add-ons/kernel/network/stack Message-ID: <200704041251.l34CpaVq012454@sheep.berlios.de> Author: hugosantos Date: 2007-04-04 14:51:23 +0200 (Wed, 04 Apr 2007) New Revision: 20553 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20553&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp Log: don't overwrite the flags we set when the interface goes up or down, instead just update the flags in the same place. Modified: haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp 2007-04-04 12:51:09 UTC (rev 20552) +++ haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp 2007-04-04 12:51:23 UTC (rev 20553) @@ -347,10 +347,8 @@ } } - request.ifr_flags = interface->flags; - } - - if (status == B_OK) { + interface->flags |= (request.ifr_flags & ~(IFF_UP | IFF_LINK)); + } else { // pass the request into the datalink protocol stack status = interface->first_info->control( interface->first_protocol, option, value, *_length); @@ -654,18 +652,7 @@ return user_memcpy(&((struct ifreq *)argument)->ifr_flags, &request.ifr_flags, sizeof(request.ifr_flags)); } - case SIOCSIFFLAGS: - { - // set flags - struct ifreq request; - if (user_memcpy(&request, argument, sizeof(struct ifreq)) < B_OK) - return B_BAD_ADDRESS; - // TODO: check flags! - interface->flags = request.ifr_flags; - return B_OK; - } - case SIOCGIFPARAM: { // get interface parameter From hugosantos at mail.berlios.de Wed Apr 4 14:53:35 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Wed, 4 Apr 2007 14:53:35 +0200 Subject: [Haiku-commits] r20554 - haiku/trunk/src/add-ons/kernel/network/stack Message-ID: <200704041253.l34CrZgi012670@sheep.berlios.de> Author: hugosantos Date: 2007-04-04 14:53:27 +0200 (Wed, 04 Apr 2007) New Revision: 20554 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20554&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp Log: handle all cases of SIOCSIFFLAGS in the same place Modified: haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp 2007-04-04 12:51:23 UTC (rev 20553) +++ haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp 2007-04-04 12:53:27 UTC (rev 20554) @@ -328,26 +328,28 @@ request.ifr_name); if (interface != NULL) { // filter out bringing the interface up or down - if (option == SIOCSIFFLAGS - && ((uint32)request.ifr_flags & IFF_UP) - != (interface->flags & IFF_UP)) { - if ((interface->flags & IFF_UP) != 0) { - // bring the interface down - interface->flags &= ~(IFF_UP | IFF_LINK); - interface->first_info->interface_down( - interface->first_protocol); - } else { - // bring it up - status = interface->first_info->interface_up( - interface->first_protocol); - if (status == B_OK) { - interface->flags |= IFF_UP - | (interface->device->media & IFM_ACTIVE - ? IFF_LINK : 0); + if (option == SIOCSIFFLAGS) { + if (((uint32)request.ifr_flags & IFF_UP) + != (interface->flags & IFF_UP)) { + if ((interface->flags & IFF_UP) != 0) { + // bring the interface down + interface->flags &= ~(IFF_UP | IFF_LINK); + interface->first_info->interface_down( + interface->first_protocol); + } else { + // bring it up + status = interface->first_info->interface_up( + interface->first_protocol); + if (status == B_OK) { + interface->flags |= IFF_UP + | (interface->device->media & IFM_ACTIVE + ? IFF_LINK : 0); + } } } - interface->flags |= (request.ifr_flags & ~(IFF_UP | IFF_LINK)); + if (status == B_OK) + interface->flags |= request.ifr_flags & ~(IFF_UP | IFF_LINK); } else { // pass the request into the datalink protocol stack status = interface->first_info->control( From axeld at mail.berlios.de Wed Apr 4 15:32:19 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Wed, 4 Apr 2007 15:32:19 +0200 Subject: [Haiku-commits] r20555 - haiku/trunk/src/bin/network/ifconfig Message-ID: <200704041332.l34DWJYU015200@sheep.berlios.de> Author: axeld Date: 2007-04-04 15:32:18 +0200 (Wed, 04 Apr 2007) New Revision: 20555 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20555&view=rev Modified: haiku/trunk/src/bin/network/ifconfig/ifconfig.cpp Log: Added support for printing the media type. Modified: haiku/trunk/src/bin/network/ifconfig/ifconfig.cpp =================================================================== --- haiku/trunk/src/bin/network/ifconfig/ifconfig.cpp 2007-04-04 12:53:27 UTC (rev 20554) +++ haiku/trunk/src/bin/network/ifconfig/ifconfig.cpp 2007-04-04 13:32:18 UTC (rev 20555) @@ -1,5 +1,5 @@ /* - * Copyright 2006, Haiku, Inc. All Rights Reserved. + * Copyright 2006-2007, Haiku, Inc. All Rights Reserved. * Distributed under the terms of the MIT License. * * Authors: @@ -13,6 +13,7 @@ #include #include #include +#include #include #include #include @@ -172,7 +173,7 @@ printf("\n\t"); // get link level interface for this interface - + int linkSocket = ::socket(AF_LINK, SOCK_DGRAM, 0); if (linkSocket < 0) { printf("No link level: %s\n", strerror(errno)); @@ -213,6 +214,35 @@ close(linkSocket); } + if (ioctl(socket, SIOCGIFMEDIA, &request, sizeof(struct ifreq)) == 0) { + const char* type = "unknown"; + bool show = true; + + switch (IFM_TYPE(request.ifr_media)) { + case IFM_ETHER: + switch (IFM_SUBTYPE(request.ifr_media)) { + case IFM_10_T: + type = "10 MBit, 10BASE-T"; + break; + case IFM_100_TX: + type = "100 MBit, 100BASE-TX"; + break; + case IFM_1000_T: + case IFM_1000_SX: + type = "1 GBit, 1000BASE-T"; + break; + } + break; + + default: + show = false; + break; + } + + if (show) + printf("\tMedia Type: %s\n", type); + } + uint32 flags = 0; if (ioctl(socket, SIOCGIFFLAGS, &request, sizeof(struct ifreq)) == 0) flags = request.ifr_flags; @@ -270,7 +300,7 @@ {IFF_ALLMULTI, "allmulti"}, {IFF_AUTOUP, "autoup"}, {IFF_LINK, "link"}, - {IFF_AUTO_CONFIGURED, "auto-configure"}, + {IFF_AUTO_CONFIGURED, "auto-configured"}, {IFF_CONFIGURING, "configuring"}, }; bool first = true; From axeld at pinc-software.de Wed Apr 4 15:38:40 2007 From: axeld at pinc-software.de (Axel =?iso-8859-15?q?D=F6rfler?=) Date: Wed, 04 Apr 2007 15:38:40 +0200 CEST Subject: [Haiku-commits] r20538 - haiku/trunk/src/add-ons/kernel/network/devices/ethernet In-Reply-To: <2393772615-BeMail@primary> Message-ID: <19493111511-BeMail@zon> "Michael Lotz" wrote: > I used it in the ipw2100 driver to set the card up and start scanning > for networks. It somehow made sense to trigger it there as it > actually > inits the interface, so I find "ETHER_INIT" fits pretty well. Can be > rewritten of course, just to mention it. Since ETHER_INIT is called directly after open(), I guess it would make more sense to move that code there :-) Anyway, that's at least one reason to put it back in: you might not be the only who used that logic :-) Bye, Axel. From axeld at mail.berlios.de Wed Apr 4 15:42:46 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Wed, 4 Apr 2007 15:42:46 +0200 Subject: [Haiku-commits] r20556 - haiku/trunk/src/add-ons/kernel/network/devices/ethernet Message-ID: <200704041342.l34DgkbK015886@sheep.berlios.de> Author: axeld Date: 2007-04-04 15:42:45 +0200 (Wed, 04 Apr 2007) New Revision: 20556 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20556&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/devices/ethernet/ethernet.cpp Log: * Set default media type to IFM_ETHER. * Added ETHER_INIT back in; we even have a driver in our repository that uses it, thanks to Michael for pointing that out. Modified: haiku/trunk/src/add-ons/kernel/network/devices/ethernet/ethernet.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/devices/ethernet/ethernet.cpp 2007-04-04 13:32:18 UTC (rev 20555) +++ haiku/trunk/src/add-ons/kernel/network/devices/ethernet/ethernet.cpp 2007-04-04 13:42:45 UTC (rev 20556) @@ -132,7 +132,7 @@ device->flags = IFF_BROADCAST; device->type = IFT_ETHER; device->mtu = 1500; - device->media = IFM_ACTIVE; + device->media = IFM_ACTIVE | IFM_ETHER; device->header_length = ETHER_HEADER_LENGTH; device->fd = -1; @@ -160,6 +160,10 @@ if (device->fd < 0) return errno; + uint64 dummy; + if (ioctl(device->fd, ETHER_INIT, &dummy, sizeof(dummy)) < 0) + goto err; + if (ioctl(device->fd, ETHER_GETADDR, device->address.data, ETHER_ADDRESS_LENGTH) < 0) goto err; From bonefish at cs.tu-berlin.de Wed Apr 4 15:50:50 2007 From: bonefish at cs.tu-berlin.de (Ingo Weinhold) Date: Wed, 04 Apr 2007 15:50:50 +0200 Subject: [Haiku-commits] r20545 - buildtools/trunk/jam In-Reply-To: <200704040734.l347Y8aZ010464@sheep.berlios.de> References: <200704040734.l347Y8aZ010464@sheep.berlios.de> Message-ID: <20070404155050.756.1@cs.tu-berlin.de> On 2007-04-04 at 09:34:08 [+0200], axeld at BerliOS wrote: > Author: axeld > Date: 2007-04-04 09:34:07 +0200 (Wed, 04 Apr 2007) > New Revision: 20545 > ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20545&view=rev > > Modified: > buildtools/trunk/jam/jam.h > Log: > I couldn't do a full clean build without this any longer using Linux and > GCC 2.95.3 (Archive action too > long), YMMV. Yeah, since Archive is no longer "piecemeal" this can be a problem. We could split up those archives, though. Otherwise we might hit the hard shell line length at some point. CU, Ingo From axeld at pinc-software.de Wed Apr 4 15:51:27 2007 From: axeld at pinc-software.de (Axel =?iso-8859-15?q?D=F6rfler?=) Date: Wed, 04 Apr 2007 15:51:27 +0200 CEST Subject: [Haiku-commits] =?iso-8859-15?q?r20553_-_haiku/trunk/src/add-ons/?= =?iso-8859-15?q?kernel/network/stack?= In-Reply-To: <200704041251.l34CpaVq012454@sheep.berlios.de> Message-ID: <20260822602-BeMail@zon> hugosantos at mail.berlios.de wrote: > Log: > don't overwrite the flags we set when the interface goes up or down, > instead just update the flags in the same place. There was actually a reason to divide it in two parts, even if it's just a theoretical one: the datalink layer is not responsible for the interface, but the interface layer is - the datalink only brought the interface up and down to keep the interface layer independent from a specific module order :-) Bye, Axel. From axeld at pinc-software.de Wed Apr 4 16:05:11 2007 From: axeld at pinc-software.de (Axel =?iso-8859-15?q?D=F6rfler?=) Date: Wed, 04 Apr 2007 16:05:11 +0200 CEST Subject: [Haiku-commits] r20545 - buildtools/trunk/jam In-Reply-To: <20070404155050.756.1@cs.tu-berlin.de> Message-ID: <21084876101-BeMail@zon> Ingo Weinhold wrote: > On 2007-04-04 at 09:34:08 [+0200], axeld at BerliOS < > axeld at mail.berlios.de> > wrote: > > I couldn't do a full clean build without this any longer using > > Linux and > > GCC 2.95.3 (Archive action too > > long), YMMV. > Yeah, since Archive is no longer "piecemeal" this can be a problem. > We > could split up those archives, though. Otherwise we might hit the > hard > shell line length at some point. I already hit that when I build on OpenSUSE 10.2 with all the command line tools that were added recently. I've removed some of them (we don't need many of them, anyway, do we?), and then the build worked fine again. We probably need to split up the binaries into more than one part :-/ Bye, Axel. From axeld at mail.berlios.de Wed Apr 4 16:20:32 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Wed, 4 Apr 2007 16:20:32 +0200 Subject: [Haiku-commits] r20557 - haiku/trunk/src/bin/network/ifconfig Message-ID: <200704041420.l34EKWSa018219@sheep.berlios.de> Author: axeld Date: 2007-04-04 16:20:32 +0200 (Wed, 04 Apr 2007) New Revision: 20557 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20557&view=rev Modified: haiku/trunk/src/bin/network/ifconfig/ifconfig.cpp Log: Only print the media state in case we're linked. Modified: haiku/trunk/src/bin/network/ifconfig/ifconfig.cpp =================================================================== --- haiku/trunk/src/bin/network/ifconfig/ifconfig.cpp 2007-04-04 13:42:45 UTC (rev 20556) +++ haiku/trunk/src/bin/network/ifconfig/ifconfig.cpp 2007-04-04 14:20:32 UTC (rev 20557) @@ -214,7 +214,9 @@ close(linkSocket); } - if (ioctl(socket, SIOCGIFMEDIA, &request, sizeof(struct ifreq)) == 0) { + if (ioctl(socket, SIOCGIFMEDIA, &request, sizeof(struct ifreq)) == 0 + && (request.ifr_media & IFM_ACTIVE) != 0) { + // dump media state in case we're linked const char* type = "unknown"; bool show = true; From bonefish at cs.tu-berlin.de Wed Apr 4 17:09:19 2007 From: bonefish at cs.tu-berlin.de (Ingo Weinhold) Date: Wed, 04 Apr 2007 17:09:19 +0200 Subject: [Haiku-commits] r20545 - buildtools/trunk/jam In-Reply-To: <21084876101-BeMail@zon> References: <21084876101-BeMail@zon> Message-ID: <20070404170919.1457.6@cs.tu-berlin.de> On 2007-04-04 at 16:05:11 [+0200], Axel D?rfler wrote: > Ingo Weinhold wrote: > > On 2007-04-04 at 09:34:08 [+0200], axeld at BerliOS < > > axeld at mail.berlios.de> > > wrote: > > > I couldn't do a full clean build without this any longer using > > > Linux and > > > GCC 2.95.3 (Archive action too > > > long), YMMV. > > Yeah, since Archive is no longer "piecemeal" this can be a problem. > > We > > could split up those archives, though. Otherwise we might hit the > > hard > > shell line length at some point. > > I already hit that when I build on OpenSUSE 10.2 with all the command > line tools that were added recently. I've removed some of them (we > don't need many of them, anyway, do we?), and then the build worked > fine again. > We probably need to split up the binaries into more than one part :-/ Mmh, weird, the AppendToHaikuImageCopyFilesScript rule that is responsible in this case is already "piecemeal", so that shouldn't happen. CU, Ingo From hugosantos at mail.berlios.de Wed Apr 4 17:36:20 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Wed, 4 Apr 2007 17:36:20 +0200 Subject: [Haiku-commits] r20558 - haiku/trunk/src/bin/network/ifconfig Message-ID: <200704041536.l34FaKkT024481@sheep.berlios.de> Author: hugosantos Date: 2007-04-04 17:36:10 +0200 (Wed, 04 Apr 2007) New Revision: 20558 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20558&view=rev Modified: haiku/trunk/src/bin/network/ifconfig/ifconfig.cpp Log: tiny case but T/TX is copper, SX is fiber Modified: haiku/trunk/src/bin/network/ifconfig/ifconfig.cpp =================================================================== --- haiku/trunk/src/bin/network/ifconfig/ifconfig.cpp 2007-04-04 14:20:32 UTC (rev 20557) +++ haiku/trunk/src/bin/network/ifconfig/ifconfig.cpp 2007-04-04 15:36:10 UTC (rev 20558) @@ -230,9 +230,11 @@ type = "100 MBit, 100BASE-TX"; break; case IFM_1000_T: - case IFM_1000_SX: type = "1 GBit, 1000BASE-T"; break; + case IFM_1000_SX: + type = "1 GBit, 1000BASE-SX"; + break; } break; From hugosantos at mail.berlios.de Wed Apr 4 17:55:02 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Wed, 4 Apr 2007 17:55:02 +0200 Subject: [Haiku-commits] r20559 - haiku/trunk/src/add-ons/kernel/drivers/network/ipro1000 Message-ID: <200704041555.l34Ft2rT026694@sheep.berlios.de> Author: hugosantos Date: 2007-04-04 17:54:50 +0200 (Wed, 04 Apr 2007) New Revision: 20559 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20559&view=rev Modified: haiku/trunk/src/add-ons/kernel/drivers/network/ipro1000/device.c haiku/trunk/src/add-ons/kernel/drivers/network/ipro1000/device.h haiku/trunk/src/add-ons/kernel/drivers/network/ipro1000/if_em.c Log: ipro1000 knows when its link state changes (notified by interrupt). Use ETHER_SET_LINK_STATE_SEM to wake the ethernet device link state notifier sooner. Modified: haiku/trunk/src/add-ons/kernel/drivers/network/ipro1000/device.c =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/network/ipro1000/device.c 2007-04-04 15:36:10 UTC (rev 20558) +++ haiku/trunk/src/add-ons/kernel/drivers/network/ipro1000/device.c 2007-04-04 15:54:50 UTC (rev 20559) @@ -110,6 +110,10 @@ device->pciFunc = device->pciInfo->function; device->adapter = 0; device->maxframesize = 1514; // XXX is MAXIMUM_ETHERNET_FRAME_SIZE = 1518 too much? + +#ifdef HAIKU_TARGET_PLATFORM_HAIKU + device->linkChangeSem = -1; +#endif ipro1000_read_settings(device); @@ -363,6 +367,15 @@ return user_memcpy(arg, &state, sizeof(ether_link_state_t)); } + + case ETHER_SET_LINK_STATE_SEM: + { + if (user_memcpy(&device->linkChangeSem, arg, sizeof(sem_id *)) < B_OK) { + device->linkChangeSem = -1; + return B_BAD_ADDRESS; + } + return B_OK; + } #endif default: Modified: haiku/trunk/src/add-ons/kernel/drivers/network/ipro1000/device.h =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/network/ipro1000/device.h 2007-04-04 15:36:10 UTC (rev 20558) +++ haiku/trunk/src/add-ons/kernel/drivers/network/ipro1000/device.h 2007-04-04 15:54:50 UTC (rev 20559) @@ -48,6 +48,10 @@ uint32 maxframesize; // 14 bytes header + MTU uint8 macaddr[6]; + +#ifdef HAIKU_TARGET_PLATFORM_HAIKU + sem_id linkChangeSem; +#endif } ipro1000_device; #endif Modified: haiku/trunk/src/add-ons/kernel/drivers/network/ipro1000/if_em.c =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/network/ipro1000/if_em.c 2007-04-04 15:36:10 UTC (rev 20558) +++ haiku/trunk/src/add-ons/kernel/drivers/network/ipro1000/if_em.c 2007-04-04 15:54:50 UTC (rev 20559) @@ -52,7 +52,7 @@ static void em_watchdog(struct ifnet *); static void em_init(void *); static void em_stop(void *); -//static void em_media_status(struct ifnet *, struct ifmediareq *); +void em_media_status(struct ifnet *, struct ifmediareq *); //static int em_media_change(struct ifnet *); static void em_identify_hardware(struct adapter *); static int em_allocate_pci_resources(struct adapter *); @@ -808,6 +808,12 @@ em_check_for_link(&adapter->hw); em_print_link_status(adapter); adapter->timer_handle = timeout(em_local_timer, adapter, 2*hz); + +#ifdef HAIKU_TARGET_PLATFORM_HAIKU + if (adapter->osdep.dev->linkChangeSem != -1) + release_sem_etc(adapter->osdep.dev->linkChangeSem, 1, + B_DO_NOT_RESCHEDULE); +#endif } } From hugosantos at mail.berlios.de Wed Apr 4 17:59:27 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Wed, 4 Apr 2007 17:59:27 +0200 Subject: [Haiku-commits] r20560 - in haiku/trunk/src/add-ons/kernel: drivers/network/ipro1000 network/devices/ethernet Message-ID: <200704041559.l34FxRYg027112@sheep.berlios.de> Author: hugosantos Date: 2007-04-04 17:59:13 +0200 (Wed, 04 Apr 2007) New Revision: 20560 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20560&view=rev Modified: haiku/trunk/src/add-ons/kernel/drivers/network/ipro1000/device.c haiku/trunk/src/add-ons/kernel/network/devices/ethernet/ethernet.cpp Log: we want the argument's contents, don't use the size of the pointer (this would even be 8 bytes in a 64 bits platform). Modified: haiku/trunk/src/add-ons/kernel/drivers/network/ipro1000/device.c =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/network/ipro1000/device.c 2007-04-04 15:54:50 UTC (rev 20559) +++ haiku/trunk/src/add-ons/kernel/drivers/network/ipro1000/device.c 2007-04-04 15:59:13 UTC (rev 20560) @@ -370,7 +370,7 @@ case ETHER_SET_LINK_STATE_SEM: { - if (user_memcpy(&device->linkChangeSem, arg, sizeof(sem_id *)) < B_OK) { + if (user_memcpy(&device->linkChangeSem, arg, sizeof(sem_id)) < B_OK) { device->linkChangeSem = -1; return B_BAD_ADDRESS; } Modified: haiku/trunk/src/add-ons/kernel/network/devices/ethernet/ethernet.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/devices/ethernet/ethernet.cpp 2007-04-04 15:54:50 UTC (rev 20559) +++ haiku/trunk/src/add-ons/kernel/network/devices/ethernet/ethernet.cpp 2007-04-04 15:59:13 UTC (rev 20560) @@ -178,7 +178,7 @@ // Set the change notification semaphore; doesn't matter // if this is supported by the device or not ioctl(device->fd, ETHER_SET_LINK_STATE_SEM, &sLinkChangeSemaphore, - sizeof(sem_id *)); + sizeof(sem_id)); BenaphoreLocker _(&sListLock); From axeld at pinc-software.de Wed Apr 4 18:15:27 2007 From: axeld at pinc-software.de (Axel =?iso-8859-15?q?D=F6rfler?=) Date: Wed, 04 Apr 2007 18:15:27 +0200 CEST Subject: [Haiku-commits] r20545 - buildtools/trunk/jam In-Reply-To: <20070404170919.1457.6@cs.tu-berlin.de> Message-ID: <28900417945-BeMail@zon> Ingo Weinhold wrote: > > I already hit that when I build on OpenSUSE 10.2 with all the > > command > > line tools that were added recently. I've removed some of them (we > > don't need many of them, anyway, do we?), and then the build worked > > fine again. > > We probably need to split up the binaries into more than one part : > > -/ > Mmh, weird, the AppendToHaikuImageCopyFilesScript rule that is > responsible > in this case is already "piecemeal", so that shouldn't happen. Maybe the limit is still too large? I can only report that I had this error :-) I could try to reproduce it again by reverting my local changes to HaikuImage, and eventually find out which command triggers it. Bye, Axel. From bonefish at cs.tu-berlin.de Wed Apr 4 19:01:26 2007 From: bonefish at cs.tu-berlin.de (Ingo Weinhold) Date: Wed, 04 Apr 2007 19:01:26 +0200 Subject: [Haiku-commits] r20545 - buildtools/trunk/jam In-Reply-To: <28900417945-BeMail@zon> References: <28900417945-BeMail@zon> Message-ID: <20070404190126.3198.9@cs.tu-berlin.de> On 2007-04-04 at 18:15:27 [+0200], Axel D?rfler wrote: > Ingo Weinhold wrote: > > > I already hit that when I build on OpenSUSE 10.2 with all the > > > command > > > line tools that were added recently. I've removed some of them (we > > > don't need many of them, anyway, do we?), and then the build worked > > > fine again. > > > We probably need to split up the binaries into more than one part : > > > -/ > > Mmh, weird, the AppendToHaikuImageCopyFilesScript rule that is > > responsible > > in this case is already "piecemeal", so that shouldn't happen. > > Maybe the limit is still too large? That's what "piecemeal" is all about. If the command line for the actions would exceed the limit, several command lines are generated for subsets of the dependencies, so that neither of them exceeds the limit. This should only fail, if the command line for a single dependency was still too long. > I can only report that I had this > error :-) > I could try to reproduce it again by reverting my local changes to > HaikuImage, and eventually find out which command triggers it. Don't worry. I'm not really in the mood for hunting obscure Jam bugs, as long as we can work around so easily. :-) CU, Ingo From axeld at mail.berlios.de Wed Apr 4 19:04:56 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Wed, 4 Apr 2007 19:04:56 +0200 Subject: [Haiku-commits] r20561 - in haiku/trunk/src/add-ons/kernel: drivers/network/bcm440x drivers/network/bcm570x drivers/network/sis900 network/devices/ethernet Message-ID: <200704041704.l34H4uvo009047@sheep.berlios.de> Author: axeld Date: 2007-04-04 19:04:54 +0200 (Wed, 04 Apr 2007) New Revision: 20561 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20561&view=rev Modified: haiku/trunk/src/add-ons/kernel/drivers/network/bcm440x/b44um.c haiku/trunk/src/add-ons/kernel/drivers/network/bcm570x/b57um.c haiku/trunk/src/add-ons/kernel/drivers/network/sis900/device.c haiku/trunk/src/add-ons/kernel/network/devices/ethernet/ethernet.cpp Log: Forgot to set IFM_ETHER in all drivers; "ethernet" now also sets it just in case. Modified: haiku/trunk/src/add-ons/kernel/drivers/network/bcm440x/b44um.c =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/network/bcm440x/b44um.c 2007-04-04 15:59:13 UTC (rev 20560) +++ haiku/trunk/src/add-ons/kernel/drivers/network/bcm440x/b44um.c 2007-04-04 17:04:54 UTC (rev 20561) @@ -259,7 +259,7 @@ { ether_link_state_t state; state.media = (pUmDevice->lm_dev.LinkStatus - == LM_STATUS_LINK_DOWN) ? IFM_ACTIVE : 0; + == LM_STATUS_LINK_DOWN ? IFM_ACTIVE : 0) | IFM_ETHER; switch (pUmDevice->lm_dev.LineSpeed) { case LM_LINE_SPEED_10MBPS: state.media |= IFM_10_T; Modified: haiku/trunk/src/add-ons/kernel/drivers/network/bcm570x/b57um.c =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/network/bcm570x/b57um.c 2007-04-04 15:59:13 UTC (rev 20560) +++ haiku/trunk/src/add-ons/kernel/drivers/network/bcm570x/b57um.c 2007-04-04 17:04:54 UTC (rev 20561) @@ -495,7 +495,7 @@ { ether_link_state_t state; state.media = (pUmDevice->lm_dev.LinkStatus - == LM_STATUS_LINK_DOWN) ? IFM_ACTIVE : 0; + == LM_STATUS_LINK_DOWN ? IFM_ACTIVE : 0) | IFM_ETHER; switch (pUmDevice->lm_dev.LineSpeed) { case LM_LINE_SPEED_10MBPS: state.media |= IFM_10_T; Modified: haiku/trunk/src/add-ons/kernel/drivers/network/sis900/device.c =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/network/sis900/device.c 2007-04-04 15:59:13 UTC (rev 20560) +++ haiku/trunk/src/add-ons/kernel/drivers/network/sis900/device.c 2007-04-04 17:04:54 UTC (rev 20561) @@ -390,7 +390,7 @@ case ETHER_GET_LINK_STATE: { ether_link_state_t state; - state.media = (info->link ? IFM_ACTIVE : 0) + state.media = (info->link ? IFM_ACTIVE : 0) | IFM_ETHER | (info->full_duplex ? IFM_FULL_DUPLEX : IFM_HALF_DUPLEX) | (info->speed == LINK_SPEED_100_MBIT ? IFM_100_TX : IFM_10_T); state.speed = info->speed == LINK_SPEED_100_MBIT Modified: haiku/trunk/src/add-ons/kernel/network/devices/ethernet/ethernet.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/devices/ethernet/ethernet.cpp 2007-04-04 15:59:13 UTC (rev 20560) +++ haiku/trunk/src/add-ons/kernel/network/devices/ethernet/ethernet.cpp 2007-04-04 17:04:54 UTC (rev 20561) @@ -57,6 +57,9 @@ return EOPNOTSUPP; } + state.media |= IFM_ETHER; + // make sure the media type is returned correctly + if (device->media != state.media || device->link_quality != state.quality || device->link_speed != state.speed) { From hugosantos at mail.berlios.de Wed Apr 4 19:40:03 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Wed, 4 Apr 2007 19:40:03 +0200 Subject: [Haiku-commits] r20562 - in haiku/trunk: headers/private/net src/add-ons/kernel/drivers/network/stack src/add-ons/kernel/network/socket src/add-ons/kernel/network/stack src/kits/network Message-ID: <200704041740.l34He3xt013513@sheep.berlios.de> Author: hugosantos Date: 2007-04-04 19:39:43 +0200 (Wed, 04 Apr 2007) New Revision: 20562 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20562&view=rev Modified: haiku/trunk/headers/private/net/net_socket.h haiku/trunk/headers/private/net/net_stack_driver.h haiku/trunk/src/add-ons/kernel/drivers/network/stack/kernel_stack.cpp haiku/trunk/src/add-ons/kernel/network/socket/socket.cpp haiku/trunk/src/add-ons/kernel/network/stack/net_socket.cpp haiku/trunk/src/kits/network/socket.cpp Log: initial recvmsg and sendmsg implementations Modified: haiku/trunk/headers/private/net/net_socket.h =================================================================== --- haiku/trunk/headers/private/net/net_socket.h 2007-04-04 17:04:54 UTC (rev 20561) +++ haiku/trunk/headers/private/net/net_socket.h 2007-04-04 17:39:43 UTC (rev 20562) @@ -92,9 +92,11 @@ ssize_t (*recv)(net_socket *socket, void *data, size_t length, int flags); ssize_t (*recvfrom)(net_socket *socket, void *data, size_t length, int flags, struct sockaddr *address, socklen_t *_addressLength); + ssize_t (*recvmsg)(net_socket *socket, msghdr *header, int flags); ssize_t (*send)(net_socket *socket, const void *data, size_t length, int flags); ssize_t (*sendto)(net_socket *socket, const void *data, size_t length, int flags, const struct sockaddr *address, socklen_t addressLength); + ssize_t (*sendmsg)(net_socket *socket, msghdr *header, int flags); int (*setsockopt)(net_socket *socket, int level, int option, const void *optionValue, int optionLength); int (*shutdown)(net_socket *socket, int direction); Modified: haiku/trunk/headers/private/net/net_stack_driver.h =================================================================== --- haiku/trunk/headers/private/net/net_stack_driver.h 2007-04-04 17:04:54 UTC (rev 20561) +++ haiku/trunk/headers/private/net/net_stack_driver.h 2007-04-04 17:39:43 UTC (rev 20562) @@ -31,8 +31,10 @@ NET_STACK_BIND, // sockaddr_args * NET_STACK_RECVFROM, // struct msghdr * NET_STACK_RECV, // transfer_args * + NET_STACK_RECVMSG, // msghdr_args * NET_STACK_SENDTO, // struct msghdr * NET_STACK_SEND, // transfer_args * + NET_STACK_SENDMSG, // msghdr_args * NET_STACK_LISTEN, // int_args * (value = backlog) NET_STACK_ACCEPT, // sockaddr_args * NET_STACK_CONNECT, // sockaddr_args * @@ -68,6 +70,11 @@ socklen_t address_length; // "" }; +struct msghdr_args { + struct msghdr *header; + int flags; +}; + struct socket_args { // used by NET_STACK_SOCKET int family; int type; Modified: haiku/trunk/src/add-ons/kernel/drivers/network/stack/kernel_stack.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/network/stack/kernel_stack.cpp 2007-04-04 17:04:54 UTC (rev 20561) +++ haiku/trunk/src/add-ons/kernel/drivers/network/stack/kernel_stack.cpp 2007-04-04 17:39:43 UTC (rev 20562) @@ -89,6 +89,39 @@ } +static status_t +check_msghdr_args(msghdr_args &args, msghdr &header, sockaddr_storage &address, + void *data, size_t length, sockaddr **originalAddress) +{ + if (length < sizeof(msghdr_args)) + return B_BAD_VALUE; + + status_t status = user_memcpy(&args, data, sizeof(msghdr_args)); + if (status < B_OK) + return status; + + status = user_memcpy(&header, args.header, sizeof(msghdr)); + if (status < B_OK) + return status; + + if (originalAddress == NULL) { + if (header.msg_namelen > sizeof(address)) + return B_BAD_VALUE; + + if (header.msg_name != NULL) { + status = user_memcpy(&address, header.msg_name, header.msg_namelen); + if (status < B_OK) + return B_BAD_ADDRESS; + } + } else { + originalAddress = (sockaddr **)&header.msg_name; + } + + if (header.msg_name != NULL) + header.msg_name = (char *)&address; + return B_OK; +} + template status_t check_args(ArgType &args, void *data, size_t length) { @@ -116,8 +149,10 @@ C2N(NET_STACK_BIND), C2N(NET_STACK_RECVFROM), C2N(NET_STACK_RECV), + C2N(NET_STACK_RECVMSG), C2N(NET_STACK_SENDTO), C2N(NET_STACK_SEND), + C2N(NET_STACK_SENDMSG), C2N(NET_STACK_LISTEN), C2N(NET_STACK_ACCEPT), C2N(NET_STACK_CONNECT), @@ -353,6 +388,20 @@ args.flags, args.address, args.address_length); } + case NET_STACK_SENDMSG: + { + sockaddr_storage address; + msghdr_args args; + msghdr header; + + status = check_msghdr_args(args, header, address, data, + length, NULL); + if (status < B_OK) + return status; + + return sSocket->sendmsg(cookie->socket, &header, args.flags); + } + case NET_STACK_RECV: { transfer_args args; @@ -382,6 +431,32 @@ return bytesRead; } + case NET_STACK_RECVMSG: + { + sockaddr *originalAddress; + sockaddr_storage address; + msghdr_args args; + msghdr header; + + status = check_msghdr_args(args, header, address, data, + length, &originalAddress); + if (status < B_OK) + return status; + + ssize_t bytesRead = sSocket->recvmsg(cookie->socket, &header, + args.flags); + if (bytesRead < B_OK) + return bytesRead; + + if (header.msg_name != NULL) { + if (user_memcpy(originalAddress, header.msg_name, + header.msg_namelen) < B_OK) + return B_BAD_ADDRESS; + } + + return bytesRead; + } + case NET_STACK_GETSOCKOPT: { sockopt_args args; Modified: haiku/trunk/src/add-ons/kernel/network/socket/socket.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/socket/socket.cpp 2007-04-04 17:04:54 UTC (rev 20561) +++ haiku/trunk/src/add-ons/kernel/network/socket/socket.cpp 2007-04-04 17:39:43 UTC (rev 20562) @@ -149,8 +149,8 @@ ssize_t recvmsg(int socket, struct msghdr *message, int flags) { - // TODO: implement me! - return -1; + msghdr_args args = { message, flags }; + return ioctl(socket, NET_STACK_RECVMSG, &args, sizeof(args)); } @@ -186,8 +186,8 @@ ssize_t sendmsg(int socket, const struct msghdr *message, int flags) { - // TODO: implement me! - return -1; + msghdr_args args = { (msghdr *)message, flags }; + return ioctl(socket, NET_STACK_SENDMSG, &args, sizeof(args)); } Modified: haiku/trunk/src/add-ons/kernel/network/stack/net_socket.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/net_socket.cpp 2007-04-04 17:04:54 UTC (rev 20561) +++ haiku/trunk/src/add-ons/kernel/network/stack/net_socket.cpp 2007-04-04 17:39:43 UTC (rev 20562) @@ -783,6 +783,70 @@ ssize_t +socket_recvmsg(net_socket *socket, msghdr *header, int flags) +{ + net_buffer *buffer; + iovec tmp; + int i; + + size_t length = 0; + for (i = 0; i < header->msg_iovlen; i++) { + if (user_memcpy(&tmp, header->msg_iov + i, sizeof(iovec)) < B_OK) + return B_BAD_ADDRESS; + if (tmp.iov_len > 0 && tmp.iov_base == NULL) + return B_BAD_ADDRESS; + length += tmp.iov_len; + } + + status_t status = socket->first_info->read_data( + socket->first_protocol, length, flags, &buffer); + if (status < B_OK) + return status; + + // TODO: - consider the control buffer options + // - datagram based protocols should return the + // full datagram so we can cut it here with MSG_TRUNC + // - returning a NULL buffer when received 0 bytes + // may not make much sense as we still need the address + + header->msg_namelen = 0; + header->msg_flags = 0; + + if (buffer == NULL) + return 0; + + size_t bytesReceived = 0; + for (i = 0; i < header->msg_iovlen && bytesReceived < buffer->size; i++) { + if (user_memcpy(&tmp, header->msg_iov + i, sizeof(iovec)) != B_OK) + break; + + size_t toRead = min_c(buffer->size - bytesReceived, tmp.iov_len); + + if (gNetBufferModule.read(buffer, bytesReceived, tmp.iov_base, + toRead) < B_OK) + break; + + bytesReceived += toRead; + } + + if (bytesReceived == buffer->size) { + if (header->msg_namelen >= buffer->source.ss_len) { + memcpy(header->msg_name, &buffer->source, buffer->source.ss_len); + header->msg_namelen = buffer->source.ss_len; + } + } + + size_t bufferSize = buffer->size; + gNetBufferModule.free(buffer); + + if (bytesReceived < bufferSize) + return ENOBUFS; + + return bytesReceived; +} + + +ssize_t socket_send(net_socket *socket, const void *data, size_t length, int flags) { if (socket->peer.ss_len == 0) @@ -885,6 +949,72 @@ } +status_t +socket_sendmsg(net_socket *socket, msghdr *header, int flags) +{ + const sockaddr *address = (const sockaddr *)header->msg_name; + socklen_t addressLength = header->msg_namelen; + + if ((address == NULL || addressLength == 0) && socket->peer.ss_len != 0) { + // socket is connected, we use that address: + address = (struct sockaddr *)&socket->peer; + addressLength = socket->peer.ss_len; + } + if (address == NULL || addressLength == 0) { + // don't know where to send to: + return EDESTADDRREQ; + } + if (socket->peer.ss_len != 0) { + // an address has been given but socket is connected already: + return EISCONN; + } + + if (socket->address.ss_len == 0) { + // try to bind first + status_t status = socket_bind(socket, NULL, 0); + if (status < B_OK) + return status; + } + + // TODO: useful, maybe even computed header space! + net_buffer *buffer = gNetBufferModule.create(256); + if (buffer == NULL) + return ENOBUFS; + + size_t length = 0; + + // copy data into buffer + for (int i = 0; i < header->msg_iovlen; i++) { + iovec tmp; + if (user_memcpy(&tmp, header->msg_iov + i, sizeof(iovec)) < B_OK || + gNetBufferModule.append(buffer, tmp.iov_base, tmp.iov_len) < B_OK) { + gNetBufferModule.free(buffer); + return ENOBUFS; + } + + length += tmp.iov_len; + } + + memcpy(&buffer->source, &socket->address, socket->address.ss_len); + memcpy(&buffer->destination, &socket->peer, socket->peer.ss_len); + + status_t status = socket->first_info->send_data(socket->first_protocol, + buffer); + if (status < B_OK) { + size_t size = buffer->size; + gNetBufferModule.free(buffer); + + if (size != length && (status == B_INTERRUPTED || status == B_WOULD_BLOCK)) { + // this appears to be a partial write + return length - size; + } + return status; + } + + return length; +} + + int socket_setsockopt(net_socket *socket, int level, int option, const void *value, int length) @@ -1080,8 +1210,10 @@ socket_listen, socket_recv, socket_recvfrom, + socket_recvmsg, socket_send, socket_sendto, + socket_sendmsg, socket_setsockopt, socket_shutdown, }; Modified: haiku/trunk/src/kits/network/socket.cpp =================================================================== --- haiku/trunk/src/kits/network/socket.cpp 2007-04-04 17:04:54 UTC (rev 20561) +++ haiku/trunk/src/kits/network/socket.cpp 2007-04-04 17:39:43 UTC (rev 20562) @@ -341,8 +341,8 @@ extern "C" ssize_t recvmsg(int socket, struct msghdr *message, int flags) { - // TODO: implement me! - return -1; + msghdr_args args = { message, flags }; + return ioctl(socket, NET_STACK_RECVMSG, &args, sizeof(args)); } @@ -386,8 +386,8 @@ extern "C" ssize_t sendmsg(int socket, const struct msghdr *message, int flags) { - // TODO: implement me! - return -1; + msghdr_args args = { (msghdr *)message, flags }; + return ioctl(socket, NET_STACK_SENDMSG, &args, sizeof(args)); } From axeld at pinc-software.de Wed Apr 4 20:00:51 2007 From: axeld at pinc-software.de (Axel =?iso-8859-15?q?D=F6rfler?=) Date: Wed, 04 Apr 2007 20:00:51 +0200 CEST Subject: [Haiku-commits] =?iso-8859-15?q?r20562_-_in_haiku/trunk=3A_header?= =?iso-8859-15?q?s/private/net_src/add-ons/kernel/drivers/network/stack_sr?= =?iso-8859-15?q?c/add-ons/kernel/network/socket_src/add-ons/kernel/networ?= =?iso-8859-15?q?k/stack_src/kits/network?= In-Reply-To: <200704041740.l34He3xt013513@sheep.berlios.de> Message-ID: <35224078625-BeMail@zon> hugosantos at mail.berlios.de wrote: > + status = check_msghdr_args(args, header, address, data, > + length, NULL); BTW, there should only be a single tab infront of the second line like this: status = check_msghdr_args(args, header, address, data, length, NULL); Bye, Axel. From hugosantos at mail.berlios.de Wed Apr 4 21:17:17 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Wed, 4 Apr 2007 21:17:17 +0200 Subject: [Haiku-commits] r20563 - haiku/trunk/src/add-ons/kernel/network/stack Message-ID: <200704041917.l34JHHAU020648@sheep.berlios.de> Author: hugosantos Date: 2007-04-04 21:17:04 +0200 (Wed, 04 Apr 2007) New Revision: 20563 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20563&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/stack/net_socket.cpp Log: some fixes to recvmsg() and sendmsg() Modified: haiku/trunk/src/add-ons/kernel/network/stack/net_socket.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/net_socket.cpp 2007-04-04 17:39:43 UTC (rev 20562) +++ haiku/trunk/src/add-ons/kernel/network/stack/net_socket.cpp 2007-04-04 19:17:04 UTC (rev 20563) @@ -808,20 +808,21 @@ // full datagram so we can cut it here with MSG_TRUNC // - returning a NULL buffer when received 0 bytes // may not make much sense as we still need the address + // - gNetBufferModule.read() uses memcpy() instead of user_memcpy + size_t nameLen = header->msg_namelen; header->msg_namelen = 0; header->msg_flags = 0; if (buffer == NULL) return 0; - size_t bytesReceived = 0; - for (i = 0; i < header->msg_iovlen && bytesReceived < buffer->size; i++) { - if (user_memcpy(&tmp, header->msg_iov + i, sizeof(iovec)) != B_OK) + size_t bufferSize = buffer->size, bytesReceived = 0; + for (i = 0; i < header->msg_iovlen && bytesReceived < bufferSize; i++) { + if (user_memcpy(&tmp, header->msg_iov + i, sizeof(iovec)) < B_OK) break; - size_t toRead = min_c(buffer->size - bytesReceived, tmp.iov_len); - + size_t toRead = min_c(bufferSize - bytesReceived, tmp.iov_len); if (gNetBufferModule.read(buffer, bytesReceived, tmp.iov_base, toRead) < B_OK) break; @@ -829,14 +830,11 @@ bytesReceived += toRead; } - if (bytesReceived == buffer->size) { - if (header->msg_namelen >= buffer->source.ss_len) { - memcpy(header->msg_name, &buffer->source, buffer->source.ss_len); - header->msg_namelen = buffer->source.ss_len; - } + if (bytesReceived == buffer->size && header->msg_name != NULL) { + header->msg_namelen = min_c(nameLen, buffer->source.ss_len); + memcpy(header->msg_name, &buffer->source, header->msg_namelen); } - size_t bufferSize = buffer->size; gNetBufferModule.free(buffer); if (bytesReceived < bufferSize) @@ -955,8 +953,16 @@ const sockaddr *address = (const sockaddr *)header->msg_name; socklen_t addressLength = header->msg_namelen; - if ((address == NULL || addressLength == 0) && socket->peer.ss_len != 0) { - // socket is connected, we use that address: + if (addressLength == 0) + address = NULL; + else if (addressLength != 0 && address == NULL) + return B_BAD_VALUE; + + if (socket->peer.ss_len != 0) { + if (address != NULL) + return EISCONN; + + // socket is connected, we use that address address = (struct sockaddr *)&socket->peer; addressLength = socket->peer.ss_len; } @@ -964,10 +970,6 @@ // don't know where to send to: return EDESTADDRREQ; } - if (socket->peer.ss_len != 0) { - // an address has been given but socket is connected already: - return EISCONN; - } if (socket->address.ss_len == 0) { // try to bind first @@ -995,8 +997,9 @@ length += tmp.iov_len; } + buffer->flags = flags; memcpy(&buffer->source, &socket->address, socket->address.ss_len); - memcpy(&buffer->destination, &socket->peer, socket->peer.ss_len); + memcpy(&buffer->destination, address, addressLength); status_t status = socket->first_info->send_data(socket->first_protocol, buffer); From hugosantos at mail.berlios.de Wed Apr 4 21:42:52 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Wed, 4 Apr 2007 21:42:52 +0200 Subject: [Haiku-commits] r20564 - haiku/trunk/src/add-ons/kernel/drivers/network/stack Message-ID: <200704041942.l34JgqFb022551@sheep.berlios.de> Author: hugosantos Date: 2007-04-04 21:42:33 +0200 (Wed, 04 Apr 2007) New Revision: 20564 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20564&view=rev Modified: haiku/trunk/src/add-ons/kernel/drivers/network/stack/kernel_stack.cpp Log: copy back msg_flags after recvmsg() (we don't really use it yet though) Modified: haiku/trunk/src/add-ons/kernel/drivers/network/stack/kernel_stack.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/network/stack/kernel_stack.cpp 2007-04-04 19:17:04 UTC (rev 20563) +++ haiku/trunk/src/add-ons/kernel/drivers/network/stack/kernel_stack.cpp 2007-04-04 19:42:33 UTC (rev 20564) @@ -454,6 +454,10 @@ return B_BAD_ADDRESS; } + if (user_memcpy(&args.header->msg_flags, &header.msg_flags, + sizeof(int)) < B_OK) + return B_BAD_ADDRESS; + return bytesRead; } From hugosantos at mail.berlios.de Wed Apr 4 21:43:06 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Wed, 4 Apr 2007 21:43:06 +0200 Subject: [Haiku-commits] r20565 - haiku/trunk/src/add-ons/kernel/network/stack Message-ID: <200704041943.l34Jh6Tk022611@sheep.berlios.de> Author: hugosantos Date: 2007-04-04 21:42:53 +0200 (Wed, 04 Apr 2007) New Revision: 20565 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20565&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/stack/net_socket.cpp Log: net_socket: make recvfrom() use recvmsg() and sendto() use sendmsg() for code reusal Modified: haiku/trunk/src/add-ons/kernel/network/stack/net_socket.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/net_socket.cpp 2007-04-04 19:42:33 UTC (rev 20564) +++ haiku/trunk/src/add-ons/kernel/network/stack/net_socket.cpp 2007-04-04 19:42:53 UTC (rev 20565) @@ -40,6 +40,8 @@ void socket_delete(net_socket *socket); int socket_bind(net_socket *socket, const struct sockaddr *address, socklen_t addressLength); +ssize_t socket_recvmsg(net_socket *, msghdr *header, int flags); +ssize_t socket_sendmsg(net_socket *, msghdr *header, int flags); struct list sSocketList; benaphore sSocketLock; @@ -757,27 +759,21 @@ socket_recvfrom(net_socket *socket, void *data, size_t length, int flags, struct sockaddr *address, socklen_t *_addressLength) { - net_buffer *buffer; - status_t status = socket->first_info->read_data( - socket->first_protocol, length, flags, &buffer); - if (status < B_OK) - return status; + iovec iov = { data, length }; + msghdr header; - // if 0 bytes we're received, no buffer will be created - if (buffer == NULL) - return 0; + memset(&header, 0, sizeof(header)); + header.msg_name = (char *)address; + header.msg_iov = &iov; + header.msg_iovlen = 1; - ssize_t bytesReceived = buffer->size; - gNetBufferModule.read(buffer, 0, data, bytesReceived); + if (_addressLength != NULL) + header.msg_namelen = *_addressLength; - // copy source address - if (address != NULL && *_addressLength > 0) { - *_addressLength = min_c(buffer->source.ss_len, *_addressLength); - memcpy(address, &buffer->source, *_addressLength); - } + ssize_t bytesReceived = socket_recvmsg(socket, &header, flags); + if (_addressLength != NULL) + *_addressLength = header.msg_namelen; - gNetBufferModule.free(buffer); - return bytesReceived; } @@ -830,7 +826,7 @@ bytesReceived += toRead; } - if (bytesReceived == buffer->size && header->msg_name != NULL) { + if (bytesReceived == bufferSize && header->msg_name != NULL) { header->msg_namelen = min_c(nameLen, buffer->source.ss_len); memcpy(header->msg_name, &buffer->source, header->msg_namelen); } @@ -894,60 +890,20 @@ socket_sendto(net_socket *socket, const void *data, size_t length, int flags, const struct sockaddr *address, socklen_t addressLength) { - if ((address == NULL || addressLength == 0) && socket->peer.ss_len != 0) { - // socket is connected, we use that address: - address = (struct sockaddr *)&socket->peer; - addressLength = socket->peer.ss_len; - } - if (address == NULL || addressLength == 0) { - // don't know where to send to: - return EDESTADDRREQ; - } - if (socket->peer.ss_len != 0) { - // an address has been given but socket is connected already: - return EISCONN; - } + iovec iov = { (void *)data, length }; + msghdr header; - if (socket->address.ss_len == 0) { - // try to bind first - status_t status = socket_bind(socket, NULL, 0); - if (status < B_OK) - return status; - } + memset(&header, 0, sizeof(header)); + header.msg_name = (char *)address; + header.msg_namelen = addressLength; + header.msg_iov = &iov; + header.msg_iovlen = 1; - // TODO: useful, maybe even computed header space! - net_buffer *buffer = gNetBufferModule.create(256); - if (buffer == NULL) - return ENOBUFS; - - // copy data into buffer - if (gNetBufferModule.append(buffer, data, length) < B_OK) { - gNetBufferModule.free(buffer); - return ENOBUFS; - } - - buffer->flags = flags; - memcpy(&buffer->source, &socket->address, socket->address.ss_len); - memcpy(&buffer->destination, address, addressLength); - - status_t status = socket->first_info->send_data(socket->first_protocol, - buffer); - if (status < B_OK) { - size_t size = buffer->size; - gNetBufferModule.free(buffer); - - if (size != length && (status == B_INTERRUPTED || status == B_WOULD_BLOCK)) { - // this appears to be a partial write - return length - size; - } - return status; - } - - return length; + return socket_sendmsg(socket, &header, flags); } -status_t +ssize_t socket_sendmsg(net_socket *socket, msghdr *header, int flags) { const sockaddr *address = (const sockaddr *)header->msg_name; From revol at free.fr Wed Apr 4 22:33:21 2007 From: revol at free.fr (=?windows-1252?q?Fran=E7ois?= Revol) Date: Wed, 04 Apr 2007 22:33:21 +0200 CEST Subject: [Haiku-commits] r20538 - haiku/trunk/src/add-ons/kernel/network/devices/ethernet In-Reply-To: <19493111511-BeMail@zon> Message-ID: <1207178803-BeMail@laptop> > "Michael Lotz" wrote: > > I used it in the ipw2100 driver to set the card up and start > > scanning > > for networks. It somehow made sense to trigger it there as it > > actually > > inits the interface, so I find "ETHER_INIT" fits pretty well. Can > > be > > rewritten of course, just to mention it. > > Since ETHER_INIT is called directly after open(), I guess it would > make > more sense to move that code there :-) > Anyway, that's at least one reason to put it back in: you might not > be > the only who used that logic :-) > Except the device might get open()ed and closed right away without wanting the if to init. For ex to see if the driver is there... Also we don't want to reinit in the middle of a transfer if someone does a cat /dev/net/foo/n. Fran?ois. From revol at free.fr Wed Apr 4 22:43:34 2007 From: revol at free.fr (=?windows-1252?q?Fran=E7ois?= Revol) Date: Wed, 04 Apr 2007 22:43:34 +0200 CEST Subject: [Haiku-commits] r20562 - in haiku/trunk: headers/private/net src/add-ons/kernel/drivers/network/stack src/add-ons/kernel/network/socket src/add-ons/kernel/network/stack src/kits/network In-Reply-To: <35224078625-BeMail@zon> Message-ID: <1820059199-BeMail@laptop> > hugosantos at mail.berlios.de wrote: > > + status = check_msghdr_args(args, header, address, > > data, > > + length, NULL); > > BTW, there should only be a single tab infront of the second line > like > this: > > status = check_msghdr_args(args, header, address, data, > length, NULL); > Hmm I've seen the former so many times... I'm not even sure the official guidelines are consistent there. Could we just get it in terms of Emacs C mode options ? Currently I use: ~/.xemacs/init.el: ------------------ (require 'cc-mode) (c-initialize-cc-mode) ;; allow local variables for C mode (setq c-style-variables-are-local-p t) ; ; http://haiku-os.org/documents/dev/haiku_coding_guidelines (defun haiku-c++-mode () "C/C++ mode with adjusted defaults followign the Haiku coding style guidelines" (interactive) (c++-mode) (c-set-style "K&R") ; TODO (setq tab-width 4) (setq indent-tabs-mode t) (setq c-basic-offset 4) (setq c-indent-level 4) (setq c-brace-imaginary-offset 0) (setq c-brace-offset -4) (setq c-argdecl-indent -4) (setq c-label-offset -4) (setq c-continued-statement-offset 4) ;(c-set-offset 'topmost-intro-cont '+) (c-set-offset 'inextern-lang '0) (c-set-offset 'innamespace '0)) (setq auto-mode-alist (cons '("haiku/.*\\.[ch][p]*$" . haiku-c++-mode) auto-mode-alist)) Oh I just noticed a typo :) Fran?ois. From korli at mail.berlios.de Wed Apr 4 22:56:57 2007 From: korli at mail.berlios.de (korli at BerliOS) Date: Wed, 4 Apr 2007 22:56:57 +0200 Subject: [Haiku-commits] r20566 - haiku/trunk/src/system/libroot/posix/glibc/libio Message-ID: <200704042056.l34Kuvpf028156@sheep.berlios.de> Author: korli Date: 2007-04-04 22:56:57 +0200 (Wed, 04 Apr 2007) New Revision: 20566 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20566&view=rev Modified: haiku/trunk/src/system/libroot/posix/glibc/libio/flockfile.c Log: added the usual weak symbols to fix bug #1134 Modified: haiku/trunk/src/system/libroot/posix/glibc/libio/flockfile.c =================================================================== --- haiku/trunk/src/system/libroot/posix/glibc/libio/flockfile.c 2007-04-04 19:42:53 UTC (rev 20565) +++ haiku/trunk/src/system/libroot/posix/glibc/libio/flockfile.c 2007-04-04 20:56:57 UTC (rev 20566) @@ -32,3 +32,7 @@ //return __libc_lock_trylock_recursive(*stream->_lock); return 1; } + +weak_alias (_IO_flockfile, flockfile); +weak_alias (_IO_funlockfile, funlockfile); +weak_alias (_IO_ftrylockfile, ftrylockfile); From hugosantos at mail.berlios.de Wed Apr 4 23:23:00 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Wed, 4 Apr 2007 23:23:00 +0200 Subject: [Haiku-commits] r20567 - haiku/trunk/src/add-ons/kernel/network/protocols/tcp Message-ID: <200704042123.l34LN0PF030113@sheep.berlios.de> Author: hugosantos Date: 2007-04-04 23:22:48 +0200 (Wed, 04 Apr 2007) New Revision: 20567 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20567&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp Log: fix locking in TCP's ReadData() Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-04 20:56:57 UTC (rev 20566) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-04 21:22:48 UTC (rev 20567) @@ -471,17 +471,21 @@ { TRACE("ReadData(%lu bytes)", numBytes); - //BenaphoreLocker lock(&fReceiveLock); + RecursiveLocker locker(fLock); if (fState == SYNCHRONIZE_SENT || fState == SYNCHRONIZE_RECEIVED) { // we need to wait until the connection becomes established if (flags & MSG_DONTWAIT) return B_WOULD_BLOCK; + locker.Unlock(); + status_t status = acquire_sem_etc(fSendLock, 1, B_RELATIVE_TIMEOUT | B_CAN_INTERRUPT, socket->receive.timeout); if (status < B_OK) return status; + + locker.Lock(); } if ((fFlags & FLAG_NO_RECEIVE) != 0 && fReceiveQueue.Available() == 0) { @@ -496,8 +500,6 @@ bigtime_t timeout = system_time() + socket->receive.timeout; - RecursiveLocker locker(fLock); - do { locker.Unlock(); From axeld at pinc-software.de Wed Apr 4 23:36:23 2007 From: axeld at pinc-software.de (Axel =?iso-8859-15?q?D=F6rfler?=) Date: Wed, 04 Apr 2007 23:36:23 +0200 CEST Subject: [Haiku-commits] r20562 - in haiku/trunk: headers/private/net src/add-ons/kernel/drivers/network/stack src/add-ons/kernel/network/socket src/add-ons/kernel/network/stack src/kits/network In-Reply-To: <1820059199-BeMail@laptop> Message-ID: <48156121022-BeMail@zon> "Fran?ois Revol" wrote: > > BTW, there should only be a single tab infront of the second line > > like this: > > status = check_msghdr_args(args, header, address, data, > > length, NULL); > Hmm I've seen the former so many times... I'm not even sure the > official guidelines are consistent there. Could we just get it in > terms > of Emacs C mode options ? I'm not sure about Emacs, but our guidelines are pretty clear on that point - it's just the question if you follow them or not. Bye, Axel. From bonefish at mail.berlios.de Thu Apr 5 01:46:07 2007 From: bonefish at mail.berlios.de (bonefish at BerliOS) Date: Thu, 5 Apr 2007 01:46:07 +0200 Subject: [Haiku-commits] r20568 - haiku/trunk/docs/user/drivers Message-ID: <200704042346.l34Nk7uQ019467@sheep.berlios.de> Author: bonefish Date: 2007-04-05 01:46:05 +0200 (Thu, 05 Apr 2007) New Revision: 20568 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20568&view=rev Modified: haiku/trunk/docs/user/drivers/fs_interface.dox haiku/trunk/docs/user/drivers/fs_modules.dox Log: More FS interface documentation. All FS hooks required for writing a basic read-only FS are documented, now. Be encouraged to review and add more. :-) Modified: haiku/trunk/docs/user/drivers/fs_interface.dox =================================================================== --- haiku/trunk/docs/user/drivers/fs_interface.dox 2007-04-04 21:22:48 UTC (rev 20567) +++ haiku/trunk/docs/user/drivers/fs_interface.dox 2007-04-04 23:46:05 UTC (rev 20568) @@ -126,6 +126,118 @@ */ /*! +\fn status_t (*file_system_module_info::mount)(mount_id id, const char *device, + uint32 flags, const char *args, fs_volume *_fs, vnode_id *_rootVnodeID) +\brief Mount a volume according to the specified parameters. + +Invoked by the VFS when it has been requested to mount the volume. The FS is +supposed to perform whatever one-time initialization is necessary for the +volume. It is required to create a volume handle for the volume and pass it +back in \a _fs. Moreover it must invoke publish_vnode() for the root node +of the volume and pass the ID of the volume back in \a _rootVnodeID. + +A disk-based FS will need to check whether \a device is not \c NULL, open +it, and analyze whether the device or image file actually represents a volume +of that FS type. + +If mounting the volume fails for whatever reason, the hook must return an +error code other than \c B_OK. In this case all resources allocated by the +hook must be freed before returning. If and only if \c B_OK is returned, the +unmount() hook will be invoked at a later point when unmounting the volume. + +\param id The ID of the volume to be mounted. It should be saved in the FS's + volume private data (volume handle). +\param device The path to the device (or image file) representing the volume + to be mounted. Can be \c NULL. +\param flags Flags: + - \c B_MOUNT_READ_ONLY: Mount the volume read-only. +\param args Null-terminated string in driver settings format, containing FS + specific parameters. +\param _fs Pointer to a pre-allocated variable the volume handle shall be + written to. +\param _rootVnodeID Pointer to a pre-allocated variable the ID of the volume's + root directory shall be written to. +\return \c B_OK if everything went fine, another error code otherwise. +*/ + +/*! +\fn status_t (*file_system_module_info::unmount)(fs_volume fs) +\brief Unmounts the given volume. + +Invoked by the VFS when it is asked to unmount the volume. The function must +free all resources associated with the mounted volume, including the volume +handle. Although the mount() hook called publish_vnode() for the root node +of the volume, unmount() must not invoke put_vnode(). + +\param fs The volume handle. +\return \c B_OK if everything went fine, another error code otherwise. The + error code will be ignored, though. +*/ + +/*! +\fn status_t (*file_system_module_info::read_fs_info)(fs_volume fs, + struct fs_info *info) +\brief Retrieves general information about the volume. + +The following fields of the \c fs_info structure need to be filled in: +- \c flags: Flags applying to the volume, e.g. \c B_FS_IS_READONLY, + \c B_FS_HAS_ATTR, etc. +- \c block_size: The size of blocks the volume data are organized in. + Meaningful mainly for disk-based FSs, other FSs should use some reasonable + value for computing \c total_blocks and \c free_blocks. +- \c io_size: Preferred size of the buffers passed to read() and write(). +- \c total_blocks: Total number of blocks the volume contains. +- \c free_blocks: Number of free blocks on the volume. +- \c total_nodes: Maximal number of nodes the volume can contain. If there is + no such limitation use \c LONGLONG_MAX. +- \c free_nodes: Number of additional nodes the volume could contain. If there + is no such limitation use \c LONGLONG_MAX. +- \c device_name: The name of the device or image file containing the volume. + Non-disk-based FSs shall fill in an empty string. +- \c volume_name: The name of the volume. + +The other values are filled in by the VFS. + +\param fs The volume handle. +\param info Pointer to a pre-allocated variable the FS info shall be written + to. +\return \c B_OK if everything went fine, another error code otherwise. The + error code will be ignored, though. +*/ + +/*! +\fn status_t (*file_system_module_info::lookup)(fs_volume fs, fs_vnode dir, + const char *name, vnode_id *_id, int *_type) +\brief Looks up the node a directory entry refers to. + +The VFS uses this hook to resolve path names to vnodes. It is used quite often +and should be implemented efficiently. + +If the parameter \a dir does not specify a directory, the function shall fail. +It shall also fail, if it is a directory, but does not contain an entry with +the given name \a name. Otherwise the function shall invoke get_vnode() for +the node the entry refers to and pass back the ID and the type of the node +in \a _id and \a _type respectively. + +Note that a directory must contain the special entries \c "." and \c "..", +referring to the same directory and the parent directory respectively. +lookup() must resolve the nodes accordingly. \c ".." for the root directory +of the volume shall be resolved to the root directory itself. + +\param fs The volume handle. +\param dir The node handle of the directory. +\param name The name of the directory entry. +\param _id Pointer to a pre-allocated variable the ID of the found node + shall be written to. +\param _type Pointer to a pre-allocated variable the type of the found node + shall be written to. The type is encoded as in the \c st_mode field of a + struct stat (bitwise anded with \c S_IFMT). +\retval B_OK Everything went fine. +\retval B_ENTRY_NOT_FOUND The given directory does not contain an entry with + the given name. +*/ + +/*! \fn status_t (*file_system_module_info::get_vnode)(fs_volume fs, vnode_id id, fs_vnode *_vnode, bool reenter) \brief Creates the private data handle to be associated with the node referred @@ -135,8 +247,8 @@ \param fs The volume handle. \param id The ID of the node. -\param _vnode Pointer to a pre-allocated variable the private data handle - shall be written to. +\param _vnode Pointer to a pre-allocated variable the node handle shall be + written to. \param reenter \c true if the hook invocation has been caused by the FS itself, e.g. by invoking ::get_vnode(). \return \c B_OK if everything went fine, another error code otherwise. @@ -151,7 +263,7 @@ node is not marked removed. \param fs The volume handle. -\param vnode The private data handle for the node. +\param vnode The node handle. \param reenter \c true if the hook invocation has been caused by the FS itself, e.g. by invoking ::put_vnode(). \return \c B_OK if everything went fine, another error code otherwise. @@ -159,15 +271,298 @@ /*! \fn status_t (*file_system_module_info::remove_vnode)(fs_volume fs, - fs_vnode vnode, bool reenter); + fs_vnode vnode, bool reenter) \brief Deletes the private data handle associated with the specified node. Invoked by the VFS when it deletes the vnode for the respective node and the node is marked removed. \param fs The volume handle. -\param vnode The private data handle for the node. +\param vnode The node handle. \param reenter \c true if the hook invocation has been caused by the FS itself, e.g. by invoking ::put_vnode(). \return \c B_OK if everything went fine, another error code otherwise. */ + +/*! +\fn status_t (*file_system_module_info::read_symlink)(fs_volume fs, + fs_vnode link, char *buffer, size_t *_bufferSize) +\brief Reads the value of a symlink. + +If the function is successful, the string written to the buffer shall be +null-terminated and the variable \a _bufferSize points to shall be set to +the length of that string, including the terminating null character. + +\param fs The volume handle. +\param link The node handle. +\param buffer Pointer to a pre-allocated buffer the link value shall be written + to. +\param buffer Pointer to a pre-allocated variable containing the size of the + buffer supplied to the function. Upon successful completion the hook shall + store the number of bytes actually written into the buffer in the variable. +\retval B_OK Everything went fine. +\retval B_BAD_VALUE \a link does not identify a symbolic link. +\retval B_BUFFER_OVERFLOW The supplied buffer is not big enough to contain the + complete link value. +*/ + +/*! +\fn status_t (*file_system_module_info::access)(fs_volume fs, fs_vnode vnode, + int mode) +\brief Checks whether the current user is allowed to access the node in the + specified way. + +\a mode is a bitwise combination of: +- \c R_OK: Read access. +- \c W_OK: Write access. +- \c X_OK: Execution. + +If the current user does not have any of the access permissions represented +by the set bits, the function shall return \c B_NOT_ALLOWED. As a special case, +if the volume is read-only and write access is requested, +\c B_READ_ONLY_DEVICE shall be returned. If the requested access mode complies +with the user's access permissions, the function shall return \c B_OK. + +For most FSs the permissions a user has are defined by the \c st_mode, +\c st_uid, and \c st_gid fields of the node's stat data. As a special +exception, the root user (geteuid() == 0<\tt>) does always have +read and write permissions, execution permission only when at least one of the +execution permission bits are set. + +\param fs The volume handle. +\param vnode The node handle. +\param mode The access mode mask. +\retval B_OK The user has the permissions to access the node in the requested + way. +\retval B_READ_ONLY_DEVICE The volume is read-only, but the write access has + been requested. +\retval B_NOT_ALLOWED The user does not have all permissions to access the node + in the requested way. +*/ + +/*! +\fn status_t (*file_system_module_info::read_stat)(fs_volume fs, + fs_vnode vnode, struct stat *stat) +\brief Retrieves the stat data for a given node. + +All values of the struct stat save \c st_dev, \c st_ino, \c st_rdev, +and \c st_type need to be filled in. + +\param fs The volume handle. +\param vnode The node handle. +\param stat Pointer to a pre-allocated variable the stat data shall be written + to. +\return \c B_OK if everything went fine, another error code otherwise. +*/ + +/*! +\fn status_t (*file_system_module_info::open)(fs_volume fs, fs_vnode vnode, + int openMode, fs_cookie *_cookie) +\brief Opens the given node. + +The function shall check whether it is possible to open the node according to +the mode specified by \c openMode (also considering the user's access +permissions), create a node cookie, and store it in the variable +\a _cookie points to. + +The open mode \a openMode is encoded in the same way as the parameter of the +POSIX function \c open(), i.e. it is either \c O_RDONLY, \c O_WRONLY, or +\c O_RDWR, bitwise or'ed with flags. The only relevant flags for this hook are +\c O_TRUNC and \c O_NONBLOCK. + +\param fs The volume handle. +\param vnode The node handle. +\param openMode The open mode. +\param _cookie Pointer to a pre-allocated variable the node cookie shall be + written to. +\return \c B_OK if everything went fine, another error code otherwise. +*/ + +/*! +\fn status_t (*file_system_module_info::close)(fs_volume fs, fs_vnode vnode, + fs_cookie cookie) +\brief Closes the given node cookie. + +The hook is invoked, when closing the node has been requested. At this point +other threads might still use the cookie, i.e. still execute hooks to which +the cookie has been passed. If the FS supports blocking I/O operations, this +hook should make sure to unblock all currently blocking threads performing +an operation using the cookie, and mark the cookie such that no further +threads will block using it. + +For many FSs this hook is a no-op. + +\param fs The volume handle. +\param vnode The node handle. +\param cookie The node cookie as returned by open(). +\return \c B_OK if everything went fine, another error code otherwise. +*/ + +/*! +\fn status_t (*file_system_module_info::free_cookie)(fs_volume fs, + fs_vnode vnode, fs_cookie cookie) +\brief Frees the given node cookie. + +The hook is invoked after close(), when no other thread uses or is going to +use the cookie. All resources associated with the cookie must be freed. + +\param fs The volume handle. +\param vnode The node handle. +\param cookie The node cookie as returned by open(). +\return \c B_OK if everything went fine, another error code otherwise. +*/ + +/*! +\fn status_t (*file_system_module_info::read)(fs_volume fs, fs_vnode vnode, + fs_cookie cookie, off_t pos, void *buffer, size_t *length) +\brief Reads data from a file. + +The function shall failed if +- the node is not a file, +- the cookie has not been opened for reading, +- \a pos is negative, or +- some other error occurs while trying to read the data, and no data have been + read at all. + +The number of bytes to be read is stored in the variable pointed to by +\a length. If less data are available at file position \a pos, or if \a pos +if greater than the size of the file, only as many data as available shall +be read, the function shall store the number of bytes actually read into the +variable pointed to by \a length, and return \c B_OK. + +\param fs The volume handle. +\param vnode The node handle. +\param cookie The node cookie as returned by open(). +\param pos The file position where to start reading data. +\param buffer Pointer to a pre-allocated buffer the read data shall be + written to. +\param length Pointer to a pre-allocated variable containing the size of the + buffer when invoked, and into which the size of the data actually read + shall be written. +\return \c B_OK if everything went fine, another error code otherwise. +*/ + +/*! +\fn status_t (*file_system_module_info::open_dir)(fs_volume fs, fs_vnode vnode, + fs_cookie *_cookie) +\brief Opens the given directory node. + +If the specified node is not a directory, or if the current user does not have +the permissions to read the directory, the function shall fail. Otherwise it +shall allocate a directory cookie and store it in the variable \a _cookie +points to. A subsequent read_dir() using the cookie shall start reading the +first entry of the directory. + +\param fs The volume handle. +\param vnode The node handle. +\param _cookie Pointer to a pre-allocated variable the directory cookie shall + be written to. +\return \c B_OK if everything went fine, another error code otherwise. +*/ + +/*! +\fn status_t (*file_system_module_info::close_dir)(fs_volume fs, + fs_vnode vnode, fs_cookie cookie) +\brief Closes the given directory cookie. + +Generally the situation is similar to the one described for close(). In +practice it is a bit, though, since directory cookies are exclusively used +for directory iteration, and it normally doesn't make sense to have multiple +threads read the same directory concurrently. Furthermore reading a directory +should not block. Therefore for most FSs this hook is a no-op. + +\param fs The volume handle. +\param vnode The node handle. +\param cookie The directory cookie as returned by open_dir(). +\return \c B_OK if everything went fine, another error code otherwise. +*/ + +/*! +\fn status_t (*file_system_module_info::free_dir_cookie)(fs_volume fs, + fs_vnode vnode, fs_cookie cookie) +\brief Frees the given directory cookie. + +The hook is invoked after close_dir(), when no other thread uses or is going +to use the cookie. All resources associated with the cookie must be freed. + +\param fs The volume handle. +\param vnode The node handle. +\param cookie The directory cookie as returned by open_dir(). +\return \c B_OK if everything went fine, another error code otherwise. +*/ + +/*! +\fn status_t (*file_system_module_info::read_dir)(fs_volume fs, fs_vnode vnode, + fs_cookie cookie, struct dirent *buffer, size_t bufferSize, uint32 *_num) +\brief Reads the next one or more directory entries. + +The number of entries to be read at maximum is stored in the variable \a _num +points to. + +Per read \c dirent the following fields have to be filled in: +- \c d_dev: The volume ID. +- \c d_ino: The ID of the node the entry refers to. +- \c d_name: The null-terminated name of the entry. +- \c d_reclen: The size of the \c dirent structure in bytes, starting from + the beginning of the structure, counting all bytes up to and including + the null-termination char of the name stored in \c d_name. + +If more than one entry is read, the corresponding \c dirent structures are +tightly packed, i.e. the second entry begins directly after the end of the +first one (i.e. \c d_reclen bytes after the beginning of the first one). +Most FSs read only one entry at a time though, even if more are requested. + +When the function is invoked after the end of the directory has been reached, +it shall set the variable \a _num points to to \c 0 and return \c B_OK. If the +provided buffer is too small to contain even the single next entry, +\c B_BUFFER_OVERFLOW shall be returned. It shall not fail, if at least one +entry has been read, and the buffer is just too small to hold as many entries +as requested. + +Note that a directory is expected to contain the special entries \c "." and +\c "..", referring to the same directory and the parent directory respectively. +The \c dirent structure returned for the \c ".." entry of the volume's root +directory shall refer to the root node itself. + +\param fs The volume handle. +\param vnode The node handle. +\param cookie The directory cookie as returned by open_dir(). +\param buffer Pointer to a pre-allocated buffer the directory entries shall be + written to. +\param bufferSize The size of \a buffer in bytes. +\param _num Pointer to a pre-allocated variable, when invoked, containing the + number of directory entries to be read, and into which the number of + entries actually read shall be written. +\return \c B_OK if everything went fine, another error code otherwise. +*/ + +/*! +\fn status_t (*file_system_module_info::rewind_dir)(fs_volume fs, + fs_vnode vnode, fs_cookie cookie) +\brief Resets the directory cookie to the first entry of the directory. +\param fs The volume handle. +\param vnode The node handle. +\param cookie The directory cookie as returned by open_dir(). +\return \c B_OK if everything went fine, another error code otherwise. +*/ + + +/*! +\fn status_t (*file_system_module_info::read_query)(fs_volume fs, + fs_cookie cookie, struct dirent *buffer, size_t bufferSize, uint32 *_num) +\brief Reads the next one or more entries matching the query. + +This hook function works pretty much the same way as read_dir(), with the +difference that it doesn't read the entries of a directory, but the entries +matching the given query. + +\param fs The volume handle. +\param cookie The query cookie as returned by open_query(). +\param buffer Pointer to a pre-allocated buffer the directory entries shall be + written to. +\param bufferSize The size of \a buffer in bytes. +\param _num Pointer to a pre-allocated variable, when invoked, containing the + number of entries to be read, and into which the number of entries + actually read shall be written. +\return \c B_OK if everything went fine, another error code otherwise. +*/ Modified: haiku/trunk/docs/user/drivers/fs_modules.dox =================================================================== --- haiku/trunk/docs/user/drivers/fs_modules.dox 2007-04-04 21:22:48 UTC (rev 20567) +++ haiku/trunk/docs/user/drivers/fs_modules.dox 2007-04-04 23:46:05 UTC (rev 20568) @@ -119,5 +119,81 @@ hook or, if the node was marked removed, \link file_system_module_info::remove_vnode remove_vnode() \endlink. +There are only four FS hooks through which the VFS gains knowledge of the +existence of a node. The first one is the +\link file_system_module_info::mount mount() \endlink +hook. It is supposed to call \c publish_vnode() for the root node of the volume +and return its ID. The second one is the +\link file_system_module_info::lookup lookup() \endlink +hook. Given a node handle of a directory and an entry name, it is supposed to +call \c get_vnode() for the node the entry refers to and return the node ID. +The remaining two hooks, +\link file_system_module_info::read_dir read_dir() \endlink +and +\link file_system_module_info::read_query read_query() \endlink, +both return entries in a struct dirent structure, which also contains +the ID of the node the entry refers to. + + +\section mandatory_hooks Mandatory Hooks + +Which hooks a FS module should provide mainly depends on what functionality +it features. E.g. a FS without support for attribute, indices, and/or queries +can omit the respective hooks (i.e. set them to \c NULL in the module +structure). Some hooks are mandatory, though. A minimal read-only FS module +must implement: + +- \link file_system_module_info::mount mount() \endlink and + \link file_system_module_info::unmount unmount() \endlink: + Mounting and unmounting a volume is required for pretty obvious reasons. + +- \link file_system_module_info::lookup lookup() \endlink: + The VFS uses this hook to resolve path names. It is probably one of the + most frequently invoked hooks. + +- \link file_system_module_info::get_vnode get_vnode() \endlink and + \link file_system_module_info::put_vnode put_vnode() \endlink: + Create respectively destroy the FS's private node handle when + the VFS creates/deletes the vnode for a particular node. + +- \link file_system_module_info::read_stat read_stat() \endlink: + Return a struct stat info for the given node, consisting of the + type and size of the node, its owner and access permissions, as well as + certain access times. + +- \link file_system_module_info::open open() \endlink, + \link file_system_module_info::close close() \endlink, and + \link file_system_module_info::free_cookie free_cookie() \endlink: + Open and close a node as explained in \ref concepts. + +- \link file_system_module_info::read read() \endlink: + Read data from an opened node (file). Even if the FS does not feature files, + the hook has to be present anyway; it should return an error in this case. + +- \link file_system_module_info::open_dir open_dir() \endlink, + \link file_system_module_info::close_dir close_dir() \endlink, and + \link file_system_module_info::free_dir_cookie free_dir_cookie() \endlink: + Open and close a directory for entry iteration as explained in \ref concepts. + +- \link file_system_module_info::read_dir read_dir() \endlink and + \link file_system_module_info::rewind_dir rewind_dir() \endlink: + Read the next entry/entries from a directory, respectively reset the iterator + to the first entry, as explained in \ref concepts. + +Although not strictly mandatory, a FS should additionally implement the +following hooks: + +- \link file_system_module_info::read_fs_info read_fs_info() \endlink: + Return general information about the volume, e.g. total and free size, and + what special features (attributes, MIME types, queries) the volume/FS + supports. + +- \link file_system_module_info::read_symlink read_symlink() \endlink: + Read the value of a symbolic link. Needed only, if the FS and volume support + symbolic links at all. If absent symbolic links stored on the volume won't + be interpreted. + +- \link file_system_module_info::access access() \endlink: + Return whether the current user has the given access permissions for a node. + If the hook is absent the user is considerd to have all permissions. */ - From hugosantos at mail.berlios.de Thu Apr 5 02:21:35 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Thu, 5 Apr 2007 02:21:35 +0200 Subject: [Haiku-commits] r20569 - haiku/trunk/src/add-ons/kernel/network/protocols/tcp Message-ID: <200704050021.l350LZAO022780@sheep.berlios.de> Author: hugosantos Date: 2007-04-05 02:21:22 +0200 (Thu, 05 Apr 2007) New Revision: 20569 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20569&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/BufferQueue.cpp haiku/trunk/src/add-ons/kernel/network/protocols/tcp/BufferQueue.h haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp Log: keep PUSH'ed pointer in receiver side of TCP so we can wait for more data in recv() Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/BufferQueue.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/BufferQueue.cpp 2007-04-04 23:46:05 UTC (rev 20568) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/BufferQueue.cpp 2007-04-05 00:21:22 UTC (rev 20569) @@ -26,7 +26,8 @@ fNumBytes(0), fContiguousBytes(0), fFirstSequence(0), - fLastSequence(0) + fLastSequence(0), + fPushPointer(0) { } @@ -352,3 +353,9 @@ return fContiguousBytes + fFirstSequence - sequence; } + +void +BufferQueue::SetPushPointer(tcp_sequence sequence) +{ + fPushPointer = sequence; +} Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/BufferQueue.h =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/BufferQueue.h 2007-04-04 23:46:05 UTC (rev 20568) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/BufferQueue.h 2007-04-05 00:21:22 UTC (rev 20569) @@ -33,6 +33,9 @@ size_t Available() const { return fContiguousBytes; } size_t Available(tcp_sequence sequence) const; + size_t PushedData() const { return fPushPointer > fFirstSequence ? fPushPointer - fFirstSequence : 0; } + void SetPushPointer(tcp_sequence sequence); + size_t Used() const { return fNumBytes; } size_t Free() const { return fMaxBytes - fNumBytes; } @@ -49,6 +52,7 @@ size_t fContiguousBytes; tcp_sequence fFirstSequence; tcp_sequence fLastSequence; + tcp_sequence fPushPointer; }; #endif // BUFFER_QUEUE_H Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-04 23:46:05 UTC (rev 20568) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-05 00:21:22 UTC (rev 20569) @@ -496,22 +496,28 @@ // read data out of buffer // TODO: add support for urgent data (MSG_OOB) - // TODO: wait until enough bytes are available bigtime_t timeout = system_time() + socket->receive.timeout; - do { + while (fReceiveQueue.PushedData() == 0 + && fReceiveQueue.Available() < numBytes + && (fFlags & FLAG_NO_RECEIVE) == 0) { locker.Unlock(); status_t status = acquire_sem_etc(fReceiveLock, 1, B_ABSOLUTE_TIMEOUT | B_CAN_INTERRUPT, timeout); - if (status < B_OK) - return status; locker.Lock(); - } while (fReceiveQueue.Available() < socket->receive.low_water_mark - && (fFlags & FLAG_NO_RECEIVE) == 0); + if (status < B_OK) { + // TODO: If we are timing out, should we push the + // available data? + if (status == B_TIMED_OUT && fReceiveQueue.Available() > 0) + break; + return status; + } + } + TRACE("ReadData(): read %lu bytes, %lu are available", numBytes, fReceiveQueue.Available()); @@ -793,6 +799,8 @@ fReceiveNext += buffer->size; TRACE("Receive(): receive next = %lu", (uint32)fReceiveNext); fReceiveQueue.Add(buffer, segment.sequence); + if (segment.flags & TCP_FLAG_PUSH) + fReceiveQueue.SetPushPointer(fReceiveNext); release_sem_etc(fReceiveLock, 1, B_DO_NOT_RESCHEDULE); // TODO: real conditional locking needed! @@ -1018,6 +1026,9 @@ } else gBufferModule->free(buffer); + if (segment.flags & TCP_FLAG_PUSH) + fReceiveQueue.SetPushPointer(fReceiveNext); + return action; } From hugosantos at mail.berlios.de Thu Apr 5 06:24:29 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Thu, 5 Apr 2007 06:24:29 +0200 Subject: [Haiku-commits] r20570 - haiku/trunk/src/add-ons/kernel/network/stack Message-ID: <200704050424.l354OTRu002514@sheep.berlios.de> Author: hugosantos Date: 2007-04-05 06:24:21 +0200 (Thu, 05 Apr 2007) New Revision: 20570 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20570&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/stack/link.cpp Log: added select() support to packet capturing Modified: haiku/trunk/src/add-ons/kernel/network/stack/link.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/link.cpp 2007-04-05 00:21:22 UTC (rev 20569) +++ haiku/trunk/src/add-ons/kernel/network/stack/link.cpp 2007-04-05 04:24:21 UTC (rev 20570) @@ -39,13 +39,20 @@ link_monitor_data(void *cookie, net_buffer *packet) { link_protocol *protocol = (link_protocol *)cookie; - + // we need to make a clone for that buffer and pass it to the socket net_buffer *buffer = gNetBufferModule.clone(packet, false); if (buffer == NULL) return B_NO_MEMORY; - return fifo_enqueue_buffer(&protocol->fifo, buffer); + status_t status = fifo_enqueue_buffer(&protocol->fifo, buffer); + if (status >= B_OK) + notify_socket(protocol->socket, B_SELECT_READ, + protocol->fifo.current_bytes); + else + gNetBufferModule.free(buffer); + + return status; } From hugosantos at mail.berlios.de Thu Apr 5 06:24:37 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Thu, 5 Apr 2007 06:24:37 +0200 Subject: [Haiku-commits] r20571 - haiku/trunk/src/add-ons/kernel/network/protocols/tcp Message-ID: <200704050424.l354ObQ5002529@sheep.berlios.de> Author: hugosantos Date: 2007-04-05 06:24:29 +0200 (Thu, 05 Apr 2007) New Revision: 20571 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20571&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp Log: fixed a critical issue with TCP's FIN handling: if FIN was set on a packet with data, fReceiveNext would be rewritten with the queue's LastSeuence which would be effectively the required sequence - 1. Increment instead fReceiveNext with the buffer's size. Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-05 04:24:21 UTC (rev 20570) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-05 04:24:29 UTC (rev 20571) @@ -1017,7 +1017,7 @@ if (buffer->size > 0) { fReceiveQueue.Add(buffer, segment.sequence); - fReceiveNext = fReceiveQueue.NextSequence(); + fReceiveNext += buffer->size; TRACE("Receive(): adding data, receive next = %lu!", (uint32)fReceiveNext); release_sem_etc(fReceiveLock, 1, B_DO_NOT_RESCHEDULE); @@ -1027,7 +1027,7 @@ gBufferModule->free(buffer); if (segment.flags & TCP_FLAG_PUSH) - fReceiveQueue.SetPushPointer(fReceiveNext); + fReceiveQueue.SetPushPointer(fReceiveQueue.LastSequence()); return action; } From hugosantos at mail.berlios.de Thu Apr 5 08:57:08 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Thu, 5 Apr 2007 08:57:08 +0200 Subject: [Haiku-commits] r20572 - haiku/trunk/src/add-ons/kernel/network/protocols/tcp Message-ID: <200704050657.l356v8cu024563@sheep.berlios.de> Author: hugosantos Date: 2007-04-05 08:56:58 +0200 (Thu, 05 Apr 2007) New Revision: 20572 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20572&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.cpp haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.h Log: fixed another TCP issue: if we were in TIME_WAIT and we received a retransmission or delayed ack, TCP would wrongly bindly immediatly acknowledge. * Moved TIME_WAIT and CLOSED handling to common Receive() path that does Sequence checking and further tests. * Moved setting FLAG_NO_RECEIVE to the end of Receive() when FIN is set so we can check for NO_RECEIVE before processing the segment text just after processing FIN. * Added a new action DELETE to be used when in TIME_WAIT and we receive a good RST Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-05 04:24:29 UTC (rev 20571) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-05 06:56:58 UTC (rev 20572) @@ -203,6 +203,7 @@ if (fState <= SYNCHRONIZE_SENT || fState == TIME_WAIT) return B_OK; + // we are only interested in the timer, not in changing state _EnterTimeWait(); return B_BUSY; // we'll be freed later when the 2MSL timer expires @@ -821,13 +822,26 @@ // is this a valid reset? if (fLastAcknowledgeSent <= segment.sequence && tcp_sequence(segment.sequence) < fLastAcknowledgeSent + fReceiveWindow) { - // TODO: close connection depending on state + if (fState == SYNCHRONIZE_RECEIVED) { + // TODO: if we came from SYN-SENT signal connection refused + // and remove all segments from tx queue + } else if (fState == ESTABLISHED || fState == FINISH_SENT + || fState == FINISH_RECEIVED || fState == FINISH_ACKNOWLEDGED) { + // TODO: RFC 793 states that on ESTABLISHED, FIN-WAIT{1,2} + // or CLOSE-WAIT "All segment queues should be + // flushed". + } + + if (fState != TIME_WAIT && fReceiveQueue.Available() > 0) { + release_sem_etc(fReceiveLock, 1, B_DO_NOT_RESCHEDULE); + // TODO: real conditional locking needed! + gSocketModule->notify(socket, B_SELECT_READ, 1); + } else { + return DELETE | DROP; + } + fError = ECONNREFUSED; fState = CLOSED; - - release_sem_etc(fReceiveLock, 1, B_DO_NOT_RESCHEDULE); - // TODO: real conditional locking needed! - gSocketModule->notify(socket, B_SELECT_READ, fReceiveQueue.Available()); } return DROP; @@ -904,7 +918,8 @@ // TODO: real conditional locking needed! gSocketModule->notify(socket, B_SELECT_READ, fReceiveQueue.Available()); } - if (fSendMax < segment.acknowledge) + + if (fSendMax < segment.acknowledge || fState == TIME_WAIT) return DROP | IMMEDIATE_ACKNOWLEDGE; if (fSendUnacknowledged >= segment.acknowledge) { // this is a duplicate acknowledge @@ -977,7 +992,6 @@ if (segment.flags & TCP_FLAG_FINISH) { TRACE("Receive(): peer is finishing connection!"); fReceiveNext++; - fFlags |= FLAG_NO_RECEIVE; release_sem_etc(fReceiveLock, 1, B_DO_NOT_RESCHEDULE); // TODO: real conditional locking needed! @@ -1015,7 +1029,7 @@ // state machine is done switching states and the data is good. // put it in the receive buffer - if (buffer->size > 0) { + if (buffer->size > 0 && (fFlags & FLAG_NO_RECEIVE) == 0) { fReceiveQueue.Add(buffer, segment.sequence); fReceiveNext += buffer->size; TRACE("Receive(): adding data, receive next = %lu!", (uint32)fReceiveNext); @@ -1029,6 +1043,9 @@ if (segment.flags & TCP_FLAG_PUSH) fReceiveQueue.SetPushPointer(fReceiveQueue.LastSequence()); + if (segment.flags & TCP_FLAG_FINISH) + fFlags |= FLAG_NO_RECEIVE; + return action; } Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.cpp 2007-04-05 04:24:29 UTC (rev 20571) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.cpp 2007-04-05 06:56:58 UTC (rev 20572) @@ -555,12 +555,6 @@ TRACE(("Endpoint %p in state %s\n", endpoint, name_for_state(endpoint->State()))); switch (endpoint->State()) { - case TIME_WAIT: - segmentAction |= IMMEDIATE_ACKNOWLEDGE; - case CLOSED: - endpoint->UpdateTimeWait(); - break; - case LISTEN: segmentAction = endpoint->ListenReceive(segment, buffer); break; @@ -576,6 +570,8 @@ case FINISH_SENT: case FINISH_ACKNOWLEDGED: case CLOSING: + case TIME_WAIT: + case CLOSED: segmentAction = endpoint->Receive(segment, buffer); break; } @@ -585,6 +581,8 @@ endpoint->SendAcknowledge(); else if (segmentAction & ACKNOWLEDGE) endpoint->DelayedAcknowledge(); + else if (segmentAction & DELETE) + gSocketModule->delete_socket(endpoint->socket); } else if ((segment.flags & TCP_FLAG_RESET) == 0) segmentAction = DROP | RESET; Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.h =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.h 2007-04-05 04:24:29 UTC (rev 20571) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.h 2007-04-05 06:56:58 UTC (rev 20572) @@ -153,6 +153,7 @@ RESET = 0x02, ACKNOWLEDGE = 0x04, IMMEDIATE_ACKNOWLEDGE = 0x08, + DELETE = 0x10, }; From axeld at mail.berlios.de Thu Apr 5 13:16:44 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Thu, 5 Apr 2007 13:16:44 +0200 Subject: [Haiku-commits] r20573 - haiku/trunk/src/kits/interface Message-ID: <200704051116.l35BGiFk007376@sheep.berlios.de> Author: axeld Date: 2007-04-05 13:16:43 +0200 (Thu, 05 Apr 2007) New Revision: 20573 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20573&view=rev Modified: haiku/trunk/src/kits/interface/OutlineListView.cpp Log: RemoveItems() implementation was missing; more or less copied the one from BListView (which is slow, but works). Modified: haiku/trunk/src/kits/interface/OutlineListView.cpp =================================================================== --- haiku/trunk/src/kits/interface/OutlineListView.cpp 2007-04-05 06:56:58 UTC (rev 20572) +++ haiku/trunk/src/kits/interface/OutlineListView.cpp 2007-04-05 11:16:43 UTC (rev 20573) @@ -1,5 +1,5 @@ /* - * Copyright 2001-2006, Haiku Inc. + * Copyright 2001-2007, Haiku Inc. * Distributed under the terms of the MIT License. * * Authors: @@ -282,11 +282,19 @@ bool -BOutlineListView::RemoveItems(int32 fullListIndex, int32 count) +BOutlineListView::RemoveItems(int32 fullIndex, int32 count) { - printf("BOutlineListView::RemoveItems Not implemented\n"); + if (fullIndex >= FullListCountItems()) + fullIndex = -1; + if (fullIndex < 0) + return false; - return false; + // TODO: very bad for performance!! + while (count--) { + BOutlineListView::RemoveItem(fullIndex); + } + + return true; } From axeld at mail.berlios.de Thu Apr 5 13:44:36 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Thu, 5 Apr 2007 13:44:36 +0200 Subject: [Haiku-commits] r20574 - haiku/trunk/src/kits/interface Message-ID: <200704051144.l35BiaQV025220@sheep.berlios.de> Author: axeld Date: 2007-04-05 13:44:35 +0200 (Thu, 05 Apr 2007) New Revision: 20574 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20574&view=rev Modified: haiku/trunk/src/kits/interface/OutlineListView.cpp Log: Now handles two cases of incorrectly built trees gracefully (instead of crashing). Modified: haiku/trunk/src/kits/interface/OutlineListView.cpp =================================================================== --- haiku/trunk/src/kits/interface/OutlineListView.cpp 2007-04-05 11:16:43 UTC (rev 20573) +++ haiku/trunk/src/kits/interface/OutlineListView.cpp 2007-04-05 11:44:35 UTC (rev 20574) @@ -25,7 +25,7 @@ quick_sort_item_array(BListItem** items, int32 first, int32 last, int (*compareFunc)(const BListItem* a, const BListItem* b)) { - if (last == first) + if (last <= first) return; BListItem* pivot = items[first + (rand() % (last - first))]; @@ -693,11 +693,9 @@ if (item->fLevel < level) break; - if (item->fLevel == level) { - // If the level matches, put them into the list - list->AddItem(item); - } - + // If the level matches, put them into the list + // (we handle the case of a missing sublevel gracefully) + list->AddItem(item); fullIndex++; if (item->HasSubitems()) { From axeld at mail.berlios.de Thu Apr 5 14:15:56 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Thu, 5 Apr 2007 14:15:56 +0200 Subject: [Haiku-commits] r20575 - haiku/trunk/src/add-ons/translators/raw Message-ID: <200704051215.l35CFulE029009@sheep.berlios.de> Author: axeld Date: 2007-04-05 14:15:56 +0200 (Thu, 05 Apr 2007) New Revision: 20575 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20575&view=rev Modified: haiku/trunk/src/add-ons/translators/raw/RAWTranslator.cpp haiku/trunk/src/add-ons/translators/raw/main.cpp Log: * Implemented support for the "header only" extension. * Added missing header when compiling RAWTranslator in test mode for Haiku. Modified: haiku/trunk/src/add-ons/translators/raw/RAWTranslator.cpp =================================================================== --- haiku/trunk/src/add-ons/translators/raw/RAWTranslator.cpp 2007-04-05 11:44:35 UTC (rev 20574) +++ haiku/trunk/src/add-ons/translators/raw/RAWTranslator.cpp 2007-04-05 12:15:56 UTC (rev 20575) @@ -141,6 +141,10 @@ if (outType != B_TRANSLATOR_BITMAP || baseType != 0) return B_NO_TRANSLATOR; + bool headerOnly = false; + if (settings != NULL) + settings->FindBool(B_TRANSLATOR_EXT_HEADER_ONLY, &headerOnly); + DCRaw raw(*source); int32 imageIndex = 0; @@ -161,7 +165,7 @@ if (imageIndex < 0 || imageIndex >= (int32)raw.CountImages()) status = B_BAD_VALUE; } - if (status == B_OK) + if (status == B_OK && !headerOnly) status = raw.ReadImageAt(imageIndex, buffer, bufferSize); } catch (status_t error) { status = error; @@ -191,9 +195,17 @@ // write out Be's Bitmap header swap_data(B_UINT32_TYPE, &header, sizeof(TranslatorBitmap), B_SWAP_HOST_TO_BENDIAN); - target->Write(&header, sizeof(TranslatorBitmap)); + ssize_t bytesWritten = target->Write(&header, sizeof(TranslatorBitmap)); + if (bytesWritten < B_OK) + return bytesWritten; - ssize_t bytesWritten = target->Write(buffer, dataSize); + if ((size_t)bytesWritten != sizeof(TranslatorBitmap)) + return B_IO_ERROR; + + if (headerOnly) + return B_OK; + + bytesWritten = target->Write(buffer, dataSize); if (bytesWritten < B_OK) return bytesWritten; Modified: haiku/trunk/src/add-ons/translators/raw/main.cpp =================================================================== --- haiku/trunk/src/add-ons/translators/raw/main.cpp 2007-04-05 11:44:35 UTC (rev 20574) +++ haiku/trunk/src/add-ons/translators/raw/main.cpp 2007-04-05 12:15:56 UTC (rev 20575) @@ -15,6 +15,7 @@ #if SHOW_MODE && TEST_MODE # include # include +# include # include # include #endif From hugosantos at gmail.com Thu Apr 5 14:49:54 2007 From: hugosantos at gmail.com (Hugo Santos) Date: Thu, 5 Apr 2007 13:49:54 +0100 Subject: [Haiku-commits] Hey :-) Message-ID: <9c46321e0704050549m77fcf9f3mff86e0b095dd285d@mail.gmail.com> Hey guys, Just to let you know i wasn't on this list so i was missing all the comments on my commits. Now i can actually see them and reply. :-) Have fun, Hugo From axeld at mail.berlios.de Thu Apr 5 15:17:55 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Thu, 5 Apr 2007 15:17:55 +0200 Subject: [Haiku-commits] r20576 - haiku/trunk/src/add-ons/translators/libtiff Message-ID: <200704051317.l35DHt1U002509@sheep.berlios.de> Author: axeld Date: 2007-04-05 15:17:55 +0200 (Thu, 05 Apr 2007) New Revision: 20576 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20576&view=rev Modified: haiku/trunk/src/add-ons/translators/libtiff/TIFFTranslator.cpp Log: The TIFF translator overwrote the document count before it was clear that it could handle the image. Modified: haiku/trunk/src/add-ons/translators/libtiff/TIFFTranslator.cpp =================================================================== --- haiku/trunk/src/add-ons/translators/libtiff/TIFFTranslator.cpp 2007-04-05 12:15:56 UTC (rev 20575) +++ haiku/trunk/src/add-ons/translators/libtiff/TIFFTranslator.cpp 2007-04-05 13:17:55 UTC (rev 20576) @@ -1,5 +1,5 @@ /* - * Copyright 2003-2006, Haiku, Inc. All Rights Reserved. + * Copyright 2003-2007, Haiku, Inc. All Rights Reserved. * Distributed under the terms of the MIT License. * * Authors: @@ -183,52 +183,52 @@ tiff_size_proc, tiff_map_file_proc, tiff_unmap_file_proc); if (!tif) return B_NO_TRANSLATOR; - + // count number of documents - int32 document_count = 0, document_index = 1; + int32 documentCount = 0, documentIndex = 1; do { - document_count++; + documentCount++; } while (TIFFReadDirectory(tif)); - + if (ioExtension) { - // add page count to ioExtension - ioExtension->RemoveName(DOCUMENT_COUNT); - ioExtension->AddInt32(DOCUMENT_COUNT, document_count); - // Check if a document index has been specified - status_t fnd = ioExtension->FindInt32(DOCUMENT_INDEX, &document_index); - if (fnd == B_OK && (document_index < 1 || document_index > document_count)) - // If a document index has been supplied, and it is an invalid value, - // return failure + if (ioExtension->FindInt32(DOCUMENT_INDEX, &documentIndex) != B_OK) + documentIndex = 1; + + if (documentIndex < 1 || documentIndex > documentCount) { + // document index is invalid return B_NO_TRANSLATOR; - else if (fnd != B_OK) - // If FindInt32 failed, make certain the document index - // is the default value - document_index = 1; + } } - + // identify the document the user specified or the first document // if the user did not specify which document they wanted to identify - if (!TIFFSetDirectory(tif, document_index - 1)) + if (!TIFFSetDirectory(tif, documentIndex - 1)) return B_NO_TRANSLATOR; + if (ioExtension) { + // add page count to ioExtension + ioExtension->RemoveName(DOCUMENT_COUNT); + ioExtension->AddInt32(DOCUMENT_COUNT, documentCount); + } + if (outInfo) { outInfo->type = B_TIFF_FORMAT; outInfo->group = B_TRANSLATOR_BITMAP; outInfo->quality = TIFF_IN_QUALITY; outInfo->capability = TIFF_IN_CAPABILITY; strcpy(outInfo->MIME, "image/tiff"); - sprintf(outInfo->name, "TIFF image (page %d of %d)", - static_cast(document_index), static_cast(document_count)); + sprintf(outInfo->name, "TIFF image"); } - - if (!poutTIFF) + + if (!poutTIFF) { // close TIFF if caller is not interested in TIFF handle TIFFClose(tif); - else + } else { // leave TIFF open and return handle if caller needs it *poutTIFF = tif; - + } + return B_OK; } From axeld at mail.berlios.de Thu Apr 5 15:29:55 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Thu, 5 Apr 2007 15:29:55 +0200 Subject: [Haiku-commits] r20577 - haiku/trunk/src/kits/translation Message-ID: <200704051329.l35DTtp0004206@sheep.berlios.de> Author: axeld Date: 2007-04-05 15:29:55 +0200 (Thu, 05 Apr 2007) New Revision: 20577 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20577&view=rev Modified: haiku/trunk/src/kits/translation/TranslatorRoster.cpp Log: No longer let translators overwrite the ioExtension message when they aren't the chosen one. Modified: haiku/trunk/src/kits/translation/TranslatorRoster.cpp =================================================================== --- haiku/trunk/src/kits/translation/TranslatorRoster.cpp 2007-04-05 13:17:55 UTC (rev 20576) +++ haiku/trunk/src/kits/translation/TranslatorRoster.cpp 2007-04-05 13:29:55 UTC (rev 20577) @@ -1,5 +1,5 @@ /* - * Copyright 2002-2006, Haiku, Inc. All Rights Reserved. + * Copyright 2002-2007, Haiku, Inc. All Rights Reserved. * Distributed under the terms of the MIT License. * * Authors: @@ -659,6 +659,7 @@ _RescanChanged(); TranslatorMap::const_iterator iterator = fTranslators.begin(); + BMessage baseExtension(*ioExtension); float bestWeight = 0.0f; while (iterator != fTranslators.end()) { @@ -673,10 +674,12 @@ const translation_format* format = _CheckHints(formats, formatsCount, hintType, hintMIME); + BMessage extension(baseExtension); translator_info info; - if (translator.Identify(source, format, ioExtension, &info, wantType) == B_OK) { + if (translator.Identify(source, format, &extension, &info, wantType) == B_OK) { float weight = info.quality * info.capability; if (weight > bestWeight) { + *ioExtension = extension; bestWeight = weight; info.translator = iterator->first; From axeld at mail.berlios.de Thu Apr 5 15:31:18 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Thu, 5 Apr 2007 15:31:18 +0200 Subject: [Haiku-commits] r20578 - haiku/trunk/src/add-ons/translators/raw Message-ID: <200704051331.l35DVImk004538@sheep.berlios.de> Author: axeld Date: 2007-04-05 15:31:17 +0200 (Thu, 05 Apr 2007) New Revision: 20578 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20578&view=rev Modified: haiku/trunk/src/add-ons/translators/raw/RAWTranslator.cpp Log: Now also exports the JPEG thumbnails as images using the translator service :-) Note, this did not work with an older libtranslation.so from Haiku, so it might also not work correctly on BeOS. Modified: haiku/trunk/src/add-ons/translators/raw/RAWTranslator.cpp =================================================================== --- haiku/trunk/src/add-ons/translators/raw/RAWTranslator.cpp 2007-04-05 13:29:55 UTC (rev 20577) +++ haiku/trunk/src/add-ons/translators/raw/RAWTranslator.cpp 2007-04-05 13:31:17 UTC (rev 20578) @@ -8,6 +8,8 @@ #include "ConfigView.h" #include "RAW.h" +#include + #include #include #include @@ -180,8 +182,12 @@ image_data_info data; raw.ImageAt(imageIndex, data); - if (!data.is_raw) - return B_NO_TRANSLATOR; + if (!data.is_raw) { + // let others handle embedded JPEG data + BMemoryIO io(buffer, bufferSize); + BTranslatorRoster* roster = BTranslatorRoster::Default(); + return roster->Translate(&io, NULL, settings, target, outType); + } uint32 dataSize = data.output_width * 4 * data.output_height; From axeld at mail.berlios.de Thu Apr 5 15:33:07 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Thu, 5 Apr 2007 15:33:07 +0200 Subject: [Haiku-commits] r20579 - haiku/trunk/src/kits/translation Message-ID: <200704051333.l35DX72c004614@sheep.berlios.de> Author: axeld Date: 2007-04-05 15:33:07 +0200 (Thu, 05 Apr 2007) New Revision: 20579 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20579&view=rev Modified: haiku/trunk/src/kits/translation/TranslatorRoster.cpp Log: ioExtension can of course be NULL... Modified: haiku/trunk/src/kits/translation/TranslatorRoster.cpp =================================================================== --- haiku/trunk/src/kits/translation/TranslatorRoster.cpp 2007-04-05 13:31:17 UTC (rev 20578) +++ haiku/trunk/src/kits/translation/TranslatorRoster.cpp 2007-04-05 13:33:07 UTC (rev 20579) @@ -659,7 +659,10 @@ _RescanChanged(); TranslatorMap::const_iterator iterator = fTranslators.begin(); - BMessage baseExtension(*ioExtension); + BMessage baseExtension; + if (ioExtension != NULL) + baseExtension = *ioExtension; + float bestWeight = 0.0f; while (iterator != fTranslators.end()) { @@ -679,7 +682,8 @@ if (translator.Identify(source, format, &extension, &info, wantType) == B_OK) { float weight = info.quality * info.capability; if (weight > bestWeight) { - *ioExtension = extension; + if (ioExtension != NULL) + *ioExtension = extension; bestWeight = weight; info.translator = iterator->first; From axeld at mail.berlios.de Thu Apr 5 16:26:06 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Thu, 5 Apr 2007 16:26:06 +0200 Subject: [Haiku-commits] r20580 - haiku/trunk/src/bin Message-ID: <200704051426.l35EQ6xH009163@sheep.berlios.de> Author: axeld Date: 2007-04-05 16:26:06 +0200 (Thu, 05 Apr 2007) New Revision: 20580 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20580&view=rev Modified: haiku/trunk/src/bin/translate.cpp Log: Translate print the output formats twice instead of the input formats. Modified: haiku/trunk/src/bin/translate.cpp =================================================================== --- haiku/trunk/src/bin/translate.cpp 2007-04-05 13:33:07 UTC (rev 20579) +++ haiku/trunk/src/bin/translate.cpp 2007-04-05 14:26:06 UTC (rev 20580) @@ -1,5 +1,5 @@ /* - * Copyright 2003-2006, Haiku. All Rights Reserved. + * Copyright 2003-2007, Haiku. All Rights Reserved. * Distributed under the terms of the MIT license. * * Authors: @@ -619,7 +619,7 @@ for (int32 j = 0; j < inCount; j++) { printf(" input:\t"); - print_translation_format(outputFormats[j]); + print_translation_format(inputFormats[j]); } for (int32 j = 0; j < outCount; j++) { From hugosantos at mail.berlios.de Thu Apr 5 16:27:11 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Thu, 5 Apr 2007 16:27:11 +0200 Subject: [Haiku-commits] r20581 - in haiku/trunk: headers/private/net src/add-ons/kernel/drivers/network/stack src/add-ons/kernel/network/socket src/add-ons/kernel/network/stack src/bin/strace src/kits/network Message-ID: <200704051427.l35ERAkn009276@sheep.berlios.de> Author: hugosantos Date: 2007-04-05 16:26:46 +0200 (Thu, 05 Apr 2007) New Revision: 20581 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20581&view=rev Modified: haiku/trunk/headers/private/net/net_socket.h haiku/trunk/headers/private/net/net_stack_driver.h haiku/trunk/src/add-ons/kernel/drivers/network/stack/kernel_stack.cpp haiku/trunk/src/add-ons/kernel/network/socket/socket.cpp haiku/trunk/src/add-ons/kernel/network/stack/net_socket.cpp haiku/trunk/src/bin/strace/NetworkTypes.cpp haiku/trunk/src/bin/strace/TypeHandler.h haiku/trunk/src/bin/strace/ioctl.cpp haiku/trunk/src/kits/network/socket.cpp Log: consolidate all RECV/SEND ioctls into a single RECEIVE/SEND pair - changed the socket module to use thew new RECEIVE/SEND in all forms of recv() and send() - changed libnetwork to use the new RECEIVE/SEND - remove transfer_args processing from strace since the structure was removed Modified: haiku/trunk/headers/private/net/net_socket.h =================================================================== --- haiku/trunk/headers/private/net/net_socket.h 2007-04-05 14:26:06 UTC (rev 20580) +++ haiku/trunk/headers/private/net/net_socket.h 2007-04-05 14:26:46 UTC (rev 20581) @@ -89,14 +89,10 @@ int (*getsockopt)(net_socket *socket, int level, int option, void *optionValue, int *_optionLength); int (*listen)(net_socket *socket, int backlog); - ssize_t (*recv)(net_socket *socket, void *data, size_t length, int flags); - ssize_t (*recvfrom)(net_socket *socket, void *data, size_t length, int flags, - struct sockaddr *address, socklen_t *_addressLength); - ssize_t (*recvmsg)(net_socket *socket, msghdr *header, int flags); - ssize_t (*send)(net_socket *socket, const void *data, size_t length, int flags); - ssize_t (*sendto)(net_socket *socket, const void *data, size_t length, - int flags, const struct sockaddr *address, socklen_t addressLength); - ssize_t (*sendmsg)(net_socket *socket, msghdr *header, int flags); + ssize_t (*receive)(net_socket *socket, struct msghdr *, void *data, + size_t length, int flags); + ssize_t (*send)(net_socket *socket, struct msghdr *, const void *data, + size_t length, int flags); int (*setsockopt)(net_socket *socket, int level, int option, const void *optionValue, int optionLength); int (*shutdown)(net_socket *socket, int direction); Modified: haiku/trunk/headers/private/net/net_stack_driver.h =================================================================== --- haiku/trunk/headers/private/net/net_stack_driver.h 2007-04-05 14:26:06 UTC (rev 20580) +++ haiku/trunk/headers/private/net/net_stack_driver.h 2007-04-05 14:26:46 UTC (rev 20581) @@ -29,12 +29,8 @@ // ops acting on an existing socket NET_STACK_BIND, // sockaddr_args * - NET_STACK_RECVFROM, // struct msghdr * - NET_STACK_RECV, // transfer_args * - NET_STACK_RECVMSG, // msghdr_args * - NET_STACK_SENDTO, // struct msghdr * - NET_STACK_SEND, // transfer_args * - NET_STACK_SENDMSG, // msghdr_args * + NET_STACK_RECEIVE, // message_args * + NET_STACK_SEND, // message_args * NET_STACK_LISTEN, // int_args * (value = backlog) NET_STACK_ACCEPT, // sockaddr_args * NET_STACK_CONNECT, // sockaddr_args * @@ -62,16 +58,10 @@ int length; }; -struct transfer_args { // used by NET_STACK_SEND/_RECV - void *data; - size_t data_length; - int flags; - struct sockaddr *address; // only used for recvfrom() and sendto() - socklen_t address_length; // "" -}; - -struct msghdr_args { +struct message_args { struct msghdr *header; + void *data; + size_t length; int flags; }; Modified: haiku/trunk/src/add-ons/kernel/drivers/network/stack/kernel_stack.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/network/stack/kernel_stack.cpp 2007-04-05 14:26:06 UTC (rev 20580) +++ haiku/trunk/src/add-ons/kernel/drivers/network/stack/kernel_stack.cpp 2007-04-05 14:26:46 UTC (rev 20581) @@ -90,35 +90,40 @@ static status_t -check_msghdr_args(msghdr_args &args, msghdr &header, sockaddr_storage &address, +check_message_args(message_args &args, msghdr &header, sockaddr_storage &address, void *data, size_t length, sockaddr **originalAddress) { - if (length < sizeof(msghdr_args)) + if (length < sizeof(message_args)) return B_BAD_VALUE; - status_t status = user_memcpy(&args, data, sizeof(msghdr_args)); + status_t status = user_memcpy(&args, data, sizeof(message_args)); if (status < B_OK) return status; - status = user_memcpy(&header, args.header, sizeof(msghdr)); - if (status < B_OK) - return status; + if (args.header != NULL) { + status = user_memcpy(&header, args.header, sizeof(msghdr)); + if (status < B_OK) + return status; - if (originalAddress == NULL) { - if (header.msg_namelen > sizeof(address)) - return B_BAD_VALUE; + if (header.msg_name == NULL) + return B_OK; - if (header.msg_name != NULL) { - status = user_memcpy(&address, header.msg_name, header.msg_namelen); - if (status < B_OK) - return B_BAD_ADDRESS; + if (originalAddress == NULL) { + if (header.msg_namelen > sizeof(address)) + return B_BAD_VALUE; + + if (header.msg_name != NULL) { + status = user_memcpy(&address, header.msg_name, header.msg_namelen); + if (status < B_OK) + return B_BAD_ADDRESS; + } + } else { + *originalAddress = (sockaddr *)header.msg_name; } - } else { - originalAddress = (sockaddr **)&header.msg_name; - } - if (header.msg_name != NULL) header.msg_name = (char *)&address; + } + return B_OK; } @@ -369,95 +374,50 @@ case NET_STACK_SEND: { - transfer_args args; - status = check_args(args, data, length); - if (status < B_OK) - return status; - - return sSocket->send(cookie->socket, args.data, args.data_length, args.flags); - } - case NET_STACK_SENDTO: - { sockaddr_storage address; - transfer_args args; - status = check_args_and_address(args, address, data, length); - if (status < B_OK) - return status; - - return sSocket->sendto(cookie->socket, args.data, args.data_length, - args.flags, args.address, args.address_length); - } - - case NET_STACK_SENDMSG: - { - sockaddr_storage address; - msghdr_args args; + message_args args; msghdr header; - status = check_msghdr_args(args, header, address, data, + status = check_message_args(args, header, address, data, length, NULL); if (status < B_OK) return status; - return sSocket->sendmsg(cookie->socket, &header, args.flags); + return sSocket->send(cookie->socket, + args.header ? &header : NULL, + args.data, args.length, args.flags); } - case NET_STACK_RECV: + case NET_STACK_RECEIVE: { - transfer_args args; - status = check_args(args, data, length); - if (status < B_OK) - return status; - - return sSocket->recv(cookie->socket, args.data, args.data_length, args.flags); - } - case NET_STACK_RECVFROM: - { + sockaddr *originalAddress = NULL; sockaddr_storage address; - transfer_args args; - status = check_args_and_address(args, address, data, length, false); - if (status < B_OK) - return status; - - ssize_t bytesRead = sSocket->recvfrom(cookie->socket, args.data, - args.data_length, args.flags, args.address, &args.address_length); - if (bytesRead < B_OK) - return bytesRead; - - status = return_address(args, data); - if (status < B_OK) - return status; - - return bytesRead; - } - - case NET_STACK_RECVMSG: - { - sockaddr *originalAddress; - sockaddr_storage address; - msghdr_args args; + message_args args; msghdr header; - status = check_msghdr_args(args, header, address, data, + status = check_message_args(args, header, address, data, length, &originalAddress); if (status < B_OK) return status; - ssize_t bytesRead = sSocket->recvmsg(cookie->socket, &header, - args.flags); + ssize_t bytesRead = sSocket->receive(cookie->socket, + args.header ? &header : NULL, args.data, + args.length, args.flags); if (bytesRead < B_OK) return bytesRead; - if (header.msg_name != NULL) { - if (user_memcpy(originalAddress, header.msg_name, - header.msg_namelen) < B_OK) + if (args.header != NULL) { + if (header.msg_name != NULL) { + if (user_memcpy(originalAddress, header.msg_name, + header.msg_namelen) < B_OK) + return B_BAD_ADDRESS; + } + + if (user_memcpy(&args.header->msg_flags, &header.msg_flags, + sizeof(int)) < B_OK) return B_BAD_ADDRESS; } - if (user_memcpy(&args.header->msg_flags, &header.msg_flags, - sizeof(int)) < B_OK) - return B_BAD_ADDRESS; - return bytesRead; } @@ -572,7 +532,7 @@ if (cookie->socket == NULL) return B_BAD_VALUE; - ssize_t bytesRead = sSocket->recv(cookie->socket, buffer, *_length, 0); + ssize_t bytesRead = sSocket->receive(cookie->socket, NULL, buffer, *_length, 0); if (bytesRead < 0) { *_length = 0; return bytesRead; @@ -608,7 +568,7 @@ if (cookie->socket == NULL) return B_BAD_VALUE; - ssize_t bytesWritten = sSocket->send(cookie->socket, buffer, *_length, 0); + ssize_t bytesWritten = sSocket->send(cookie->socket, NULL, buffer, *_length, 0); if (bytesWritten < 0) { *_length = 0; return bytesWritten; Modified: haiku/trunk/src/add-ons/kernel/network/socket/socket.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/socket/socket.cpp 2007-04-05 14:26:06 UTC (rev 20580) +++ haiku/trunk/src/add-ons/kernel/network/socket/socket.cpp 2007-04-05 14:26:46 UTC (rev 20581) @@ -15,6 +15,7 @@ #include +#include #include #include @@ -113,14 +114,13 @@ ssize_t recv(int socket, void *data, size_t length, int flags) { - transfer_args args; + message_args args; args.data = data; - args.data_length = length; + args.length = length; args.flags = flags; - args.address = NULL; - args.address_length = 0; + args.header = NULL; - return ioctl(socket, NET_STACK_RECV, &args, sizeof(args)); + return ioctl(socket, NET_STACK_RECEIVE, &args, sizeof(args)); } @@ -128,19 +128,25 @@ recvfrom(int socket, void *data, size_t length, int flags, struct sockaddr *address, socklen_t *_addressLength) { - transfer_args args; + message_args args; + msghdr header; + + memset(&header, 0, sizeof(header)); + args.data = data; - args.data_length = length; + args.length = length; args.flags = flags; - args.address = address; - args.address_length = _addressLength ? *_addressLength : 0; + args.header = &header; - ssize_t bytesReceived = ioctl(socket, NET_STACK_RECVFROM, &args, sizeof(args)); + header.msg_name = (char *)address; + header.msg_namelen = _addressLength ? *_addressLength : 0; + + ssize_t bytesReceived = ioctl(socket, NET_STACK_RECEIVE, &args, sizeof(args)); if (bytesReceived < 0) return -1; if (_addressLength != NULL) - *_addressLength = args.address_length; + *_addressLength = header.msg_namelen; return bytesReceived; } @@ -149,20 +155,34 @@ ssize_t recvmsg(int socket, struct msghdr *message, int flags) { - msghdr_args args = { message, flags }; - return ioctl(socket, NET_STACK_RECVMSG, &args, sizeof(args)); + message_args args; + + if (message == NULL || (message->msg_iovlen > 0 && message->msg_iov == NULL)) + return B_BAD_VALUE; + + args.header = message; + args.flags = flags; + + if (message->msg_iovlen > 0) { + args.data = message->msg_iov[0].iov_base; + args.length = message->msg_iov[0].iov_len; + } else { + args.data = NULL; + args.length = 0; + } + + return ioctl(socket, NET_STACK_RECEIVE, &args, sizeof(args)); } ssize_t send(int socket, const void *data, size_t length, int flags) { - transfer_args args; + message_args args; args.data = const_cast(data); - args.data_length = length; + args.length = length; args.flags = flags; - args.address = NULL; - args.address_length = 0; + args.header = NULL; return ioctl(socket, NET_STACK_SEND, &args, sizeof(args)); } @@ -172,22 +192,41 @@ sendto(int socket, const void *data, size_t length, int flags, const struct sockaddr *address, socklen_t addressLength) { - transfer_args args; + message_args args; + msghdr header; + memset(&header, 0, sizeof(header)); + args.data = const_cast(data); - args.data_length = length; + args.length = length; args.flags = flags; - args.address = const_cast(address); - args.address_length = addressLength; + args.header = &header; + header.msg_name = (char *)const_cast(address); + header.msg_namelen = addressLength; - return ioctl(socket, NET_STACK_SENDTO, &args, sizeof(args)); + return ioctl(socket, NET_STACK_SEND, &args, sizeof(args)); } ssize_t sendmsg(int socket, const struct msghdr *message, int flags) { - msghdr_args args = { (msghdr *)message, flags }; - return ioctl(socket, NET_STACK_SENDMSG, &args, sizeof(args)); + message_args args; + + if (message == NULL || (message->msg_iovlen > 0 && message->msg_iov == NULL)) + return B_BAD_VALUE; + + args.header = (msghdr *)message; + args.flags = flags; + + if (message->msg_iovlen > 0) { + args.data = message->msg_iov[0].iov_base; + args.length = message->msg_iov[0].iov_len; + } else { + args.data = NULL; + args.length = 0; + } + + return ioctl(socket, NET_STACK_SEND, &args, sizeof(args)); } Modified: haiku/trunk/src/add-ons/kernel/network/stack/net_socket.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/net_socket.cpp 2007-04-05 14:26:06 UTC (rev 20580) +++ haiku/trunk/src/add-ons/kernel/network/stack/net_socket.cpp 2007-04-05 14:26:46 UTC (rev 20581) @@ -40,8 +40,6 @@ void socket_delete(net_socket *socket); int socket_bind(net_socket *socket, const struct sockaddr *address, socklen_t addressLength); -ssize_t socket_recvmsg(net_socket *, msghdr *header, int flags); -ssize_t socket_sendmsg(net_socket *, msghdr *header, int flags); struct list sSocketList; benaphore sSocketLock; @@ -735,180 +733,113 @@ ssize_t -socket_recv(net_socket *socket, void *data, size_t length, int flags) +socket_receive(net_socket *socket, msghdr *header, void *data, size_t length, + int flags) { + size_t totalLength = length; net_buffer *buffer; - status_t status = socket->first_info->read_data( - socket->first_protocol, length, flags, &buffer); - if (status < B_OK) - return status; - - // if 0 bytes we're received, no buffer will be created - if (buffer == NULL) - return 0; - - ssize_t bytesReceived = buffer->size; - gNetBufferModule.read(buffer, 0, data, bytesReceived); - gNetBufferModule.free(buffer); - - return bytesReceived; -} - - -ssize_t -socket_recvfrom(net_socket *socket, void *data, size_t length, int flags, - struct sockaddr *address, socklen_t *_addressLength) -{ - iovec iov = { data, length }; - msghdr header; - - memset(&header, 0, sizeof(header)); - header.msg_name = (char *)address; - header.msg_iov = &iov; - header.msg_iovlen = 1; - - if (_addressLength != NULL) - header.msg_namelen = *_addressLength; - - ssize_t bytesReceived = socket_recvmsg(socket, &header, flags); - if (_addressLength != NULL) - *_addressLength = header.msg_namelen; - - return bytesReceived; -} - - -ssize_t -socket_recvmsg(net_socket *socket, msghdr *header, int flags) -{ - net_buffer *buffer; iovec tmp; int i; - size_t length = 0; - for (i = 0; i < header->msg_iovlen; i++) { - if (user_memcpy(&tmp, header->msg_iov + i, sizeof(iovec)) < B_OK) - return B_BAD_ADDRESS; - if (tmp.iov_len > 0 && tmp.iov_base == NULL) - return B_BAD_ADDRESS; - length += tmp.iov_len; + // the convention to this function is that have header been + // present, { data, length } would have been iovec[0] and is + // always considered like that + + if (header) { + // calculate the length considering all of the extra buffers + for (i = 1; i < header->msg_iovlen; i++) { + if (user_memcpy(&tmp, header->msg_iov + i, sizeof(iovec)) < B_OK) + return B_BAD_ADDRESS; + if (tmp.iov_len > 0 && tmp.iov_base == NULL) + return B_BAD_ADDRESS; + totalLength += tmp.iov_len; + } } status_t status = socket->first_info->read_data( - socket->first_protocol, length, flags, &buffer); + socket->first_protocol, totalLength, flags, &buffer); if (status < B_OK) return status; - // TODO: - consider the control buffer options - // - datagram based protocols should return the + // TODO: - datagram based protocols should return the // full datagram so we can cut it here with MSG_TRUNC // - returning a NULL buffer when received 0 bytes // may not make much sense as we still need the address // - gNetBufferModule.read() uses memcpy() instead of user_memcpy - size_t nameLen = header->msg_namelen; - header->msg_namelen = 0; - header->msg_flags = 0; + size_t nameLen = 0; + if (header) { + // TODO: - consider the control buffer options + nameLen = header->msg_namelen; + header->msg_namelen = 0; + header->msg_flags = 0; + } + if (buffer == NULL) return 0; - size_t bufferSize = buffer->size, bytesReceived = 0; - for (i = 0; i < header->msg_iovlen && bytesReceived < bufferSize; i++) { - if (user_memcpy(&tmp, header->msg_iov + i, sizeof(iovec)) < B_OK) - break; + size_t bytesReceived = buffer->size, bytesCopied = 0; - size_t toRead = min_c(bufferSize - bytesReceived, tmp.iov_len); - if (gNetBufferModule.read(buffer, bytesReceived, tmp.iov_base, - toRead) < B_OK) - break; - - bytesReceived += toRead; + length = min_c(bytesReceived, length); + if (gNetBufferModule.read(buffer, 0, data, length) < B_OK) { + gNetBufferModule.free(buffer); + return ENOBUFS; } - if (bytesReceived == bufferSize && header->msg_name != NULL) { - header->msg_namelen = min_c(nameLen, buffer->source.ss_len); - memcpy(header->msg_name, &buffer->source, header->msg_namelen); - } + // if first copy was a success, proceed to following + // copies as required + bytesCopied += length; - gNetBufferModule.free(buffer); + if (header) { + // we only start considering at iovec[1] + // as { data, length } is iovec[0] + for (i = 1; i < header->msg_iovlen && bytesCopied < bytesReceived; i++) { + if (user_memcpy(&tmp, header->msg_iov + i, sizeof(iovec)) < B_OK) + break; - if (bytesReceived < bufferSize) - return ENOBUFS; + size_t toRead = min_c(bytesReceived - bytesCopied, tmp.iov_len); + if (gNetBufferModule.read(buffer, bytesCopied, tmp.iov_base, + toRead) < B_OK) + break; - return bytesReceived; -} + bytesCopied += toRead; + } - -ssize_t -socket_send(net_socket *socket, const void *data, size_t length, int flags) -{ - if (socket->peer.ss_len == 0) - return EDESTADDRREQ; - - if (socket->address.ss_len == 0) { - // try to bind first - status_t status = socket_bind(socket, NULL, 0); - if (status < B_OK) - return status; + if (bytesCopied == bytesReceived && header->msg_name != NULL) { + header->msg_namelen = min_c(nameLen, buffer->source.ss_len); + memcpy(header->msg_name, &buffer->source, header->msg_namelen); + } } - // TODO: useful, maybe even computed header space! - net_buffer *buffer = gNetBufferModule.create(256); - if (buffer == NULL) - return ENOBUFS; + gNetBufferModule.free(buffer); - // copy data into buffer - if (gNetBufferModule.append(buffer, data, length) < B_OK) { - gNetBufferModule.free(buffer); + if (bytesCopied < bytesReceived) return ENOBUFS; - } - buffer->flags = flags; - memcpy(&buffer->source, &socket->address, socket->address.ss_len); - memcpy(&buffer->destination, &socket->peer, socket->peer.ss_len); - - status_t status = socket->first_info->send_data(socket->first_protocol, - buffer); - if (status < B_OK) { - size_t size = buffer->size; - gNetBufferModule.free(buffer); - - if (size != length && (status == B_INTERRUPTED || status == B_WOULD_BLOCK)) { - // this appears to be a partial write - return length - size; - } - - return status; - } - - return length; + return bytesCopied; } ssize_t -socket_sendto(net_socket *socket, const void *data, size_t length, int flags, - const struct sockaddr *address, socklen_t addressLength) +socket_send(net_socket *socket, msghdr *header, const void *data, + size_t length, int flags) { - iovec iov = { (void *)data, length }; - msghdr header; + const sockaddr *address = NULL; + socklen_t addressLength = 0; - memset(&header, 0, sizeof(header)); - header.msg_name = (char *)address; - header.msg_namelen = addressLength; - header.msg_iov = &iov; - header.msg_iovlen = 1; + // the convention to this function is that have header been + // present, { data, length } would have been iovec[0] and is + // always considered like that - return socket_sendmsg(socket, &header, flags); -} + if (header != NULL) { + address = (const sockaddr *)header->msg_name; + addressLength = header->msg_namelen; + if (header->msg_iovlen <= 1) + header = NULL; + } -ssize_t -socket_sendmsg(net_socket *socket, msghdr *header, int flags) -{ - const sockaddr *address = (const sockaddr *)header->msg_name; - socklen_t addressLength = header->msg_namelen; - if (addressLength == 0) address = NULL; else if (addressLength != 0 && address == NULL) @@ -922,6 +853,7 @@ address = (struct sockaddr *)&socket->peer; addressLength = socket->peer.ss_len; } + if (address == NULL || addressLength == 0) { // don't know where to send to: return EDESTADDRREQ; @@ -939,18 +871,23 @@ if (buffer == NULL) return ENOBUFS; - size_t length = 0; + if (gNetBufferModule.append(buffer, data, length) < B_OK) { + gNetBufferModule.free(buffer); + return ENOBUFS; + } - // copy data into buffer - for (int i = 0; i < header->msg_iovlen; i++) { - iovec tmp; - if (user_memcpy(&tmp, header->msg_iov + i, sizeof(iovec)) < B_OK || - gNetBufferModule.append(buffer, tmp.iov_base, tmp.iov_len) < B_OK) { - gNetBufferModule.free(buffer); - return ENOBUFS; - } + if (header) { + // copy additional data into buffer + for (int i = 1; i < header->msg_iovlen; i++) { + iovec tmp; + if (user_memcpy(&tmp, header->msg_iov + i, sizeof(iovec)) < B_OK || + gNetBufferModule.append(buffer, tmp.iov_base, tmp.iov_len) < B_OK) { + gNetBufferModule.free(buffer); + return ENOBUFS; + } - length += tmp.iov_len; + length += tmp.iov_len; + } } buffer->flags = flags; @@ -1167,12 +1104,8 @@ socket_getsockname, socket_getsockopt, socket_listen, - socket_recv, - socket_recvfrom, - socket_recvmsg, + socket_receive, socket_send, - socket_sendto, - socket_sendmsg, socket_setsockopt, socket_shutdown, }; Modified: haiku/trunk/src/bin/strace/NetworkTypes.cpp =================================================================== --- haiku/trunk/src/bin/strace/NetworkTypes.cpp 2007-04-05 14:26:06 UTC (rev 20580) +++ haiku/trunk/src/bin/strace/NetworkTypes.cpp 2007-04-05 14:26:46 UTC (rev 20581) @@ -226,19 +226,6 @@ return r; } -static string -format_pointer(Context &context, transfer_args *args) -{ - string r; - - r = "data = " + context.FormatPointer(args->data); - r += ", len = " + context.FormatUnsigned(args->data_length); - r += ", flags = " + context.FormatFlags(args->flags); - r += ", addr = " + format_pointer_value(context, args->address); - - return r; -} - struct socket_option_info { int level; int option; @@ -475,7 +462,6 @@ DEFINE_TYPE(fdset_ptr, fd_set *); POINTER_TYPE(sockaddr_args_ptr, sockaddr_args); -POINTER_TYPE(transfer_args_ptr, transfer_args); POINTER_TYPE(sockopt_args_ptr, sockopt_args); POINTER_TYPE(socket_args_ptr, socket_args); POINTER_TYPE(msghdr_ptr, msghdr); Modified: haiku/trunk/src/bin/strace/TypeHandler.h =================================================================== --- haiku/trunk/src/bin/strace/TypeHandler.h 2007-04-05 14:26:06 UTC (rev 20580) +++ haiku/trunk/src/bin/strace/TypeHandler.h 2007-04-05 14:26:46 UTC (rev 20581) @@ -103,11 +103,9 @@ struct sockaddr_args; struct socket_args; struct sockopt_args; -struct transfer_args; DEFINE_FACTORY(fdset_ptr, fd_set *); DEFINE_FACTORY(sockaddr_args_ptr, sockaddr_args *); -DEFINE_FACTORY(transfer_args_ptr, transfer_args *); DEFINE_FACTORY(sockopt_args_ptr, sockopt_args *); DEFINE_FACTORY(socket_args_ptr, socket_args *); DEFINE_FACTORY(ifreq_ptr, ifreq *); Modified: haiku/trunk/src/bin/strace/ioctl.cpp =================================================================== --- haiku/trunk/src/bin/strace/ioctl.cpp 2007-04-05 14:26:06 UTC (rev 20580) +++ haiku/trunk/src/bin/strace/ioctl.cpp 2007-04-05 14:26:46 UTC (rev 20581) @@ -33,10 +33,8 @@ IOCTL_INFO_ENTRY(NET_STACK_CONTROL_NET_MODULE), IOCTL_INFO_ENTRY(NET_STACK_GET_NEXT_STAT), IOCTL_INFO_ENTRY_TYPE(NET_STACK_BIND, struct sockaddr_args *), - IOCTL_INFO_ENTRY_TYPE(NET_STACK_RECVFROM, struct transfer_args *), - IOCTL_INFO_ENTRY_TYPE(NET_STACK_RECV, struct transfer_args *), - IOCTL_INFO_ENTRY_TYPE(NET_STACK_SENDTO, struct transfer_args *), - IOCTL_INFO_ENTRY_TYPE(NET_STACK_SEND, struct transfer_args *), + IOCTL_INFO_ENTRY_TYPE(NET_STACK_RECEIVE, struct message_args *), + IOCTL_INFO_ENTRY_TYPE(NET_STACK_SEND, struct message_args *), IOCTL_INFO_ENTRY(NET_STACK_LISTEN), IOCTL_INFO_ENTRY(NET_STACK_ACCEPT), IOCTL_INFO_ENTRY_TYPE(NET_STACK_CONNECT, struct sockaddr_args *), Modified: haiku/trunk/src/kits/network/socket.cpp =================================================================== --- haiku/trunk/src/kits/network/socket.cpp 2007-04-05 14:26:06 UTC (rev 20580) +++ haiku/trunk/src/kits/network/socket.cpp 2007-04-05 14:26:46 UTC (rev 20581) @@ -292,14 +292,13 @@ extern "C" ssize_t recv(int socket, void *data, size_t length, int flags) { - transfer_args args; + message_args args; args.data = data; - args.data_length = length; + args.length = length; args.flags = flags; - args.address = NULL; - args.address_length = 0; + args.header = NULL; - return ioctl(socket, NET_STACK_RECV, &args, sizeof(args)); + return ioctl(socket, NET_STACK_RECEIVE, &args, sizeof(args)); } @@ -310,20 +309,24 @@ bool r5compatible = check_r5_compatibility(); struct sockaddr r5addr; - transfer_args args; + message_args args; args.data = data; - args.data_length = length; + args.length = length; args.flags = flags; + msghdr header; + memset(&header, 0, sizeof(header)); + args.header = &header; + if (r5compatible) { - args.address = &r5addr; - args.address_length = sizeof(r5addr); + header.msg_name = (char *)&r5addr; + header.msg_namelen = sizeof(r5addr); } else { - args.address = address; - args.address_length = _addressLength ? *_addressLength : 0; + header.msg_name = (char *)address; + header.msg_namelen = _addressLength ? *_addressLength : 0; } - ssize_t bytesReceived = ioctl(socket, NET_STACK_RECVFROM, &args, sizeof(args)); + ssize_t bytesReceived = ioctl(socket, NET_STACK_RECEIVE, &args, sizeof(args)); if (bytesReceived < 0) return -1; @@ -332,7 +335,7 @@ if (_addressLength != NULL) *_addressLength = sizeof(struct r5_sockaddr_in); } else if (_addressLength != NULL) - *_addressLength = args.address_length; + *_addressLength = header.msg_namelen; return bytesReceived; } @@ -341,20 +344,34 @@ extern "C" ssize_t recvmsg(int socket, struct msghdr *message, int flags) { - msghdr_args args = { message, flags }; - return ioctl(socket, NET_STACK_RECVMSG, &args, sizeof(args)); + message_args args; + + if (message == NULL || (message->msg_iovlen > 0 && message->msg_iov == NULL)) + return B_BAD_VALUE; + + args.header = message; + args.flags = flags; + + if (message->msg_iovlen > 0) { + args.data = message->msg_iov[0].iov_base; + args.length = message->msg_iov[0].iov_len; + } else { + args.data = NULL; + args.length = 0; + } + + return ioctl(socket, NET_STACK_RECEIVE, &args, sizeof(args)); } extern "C" ssize_t send(int socket, const void *data, size_t length, int flags) { - transfer_args args; + message_args args; args.data = const_cast(data); - args.data_length = length; + args.length = length; args.flags = flags; - args.address = NULL; - args.address_length = 0; + args.header = NULL; return ioctl(socket, NET_STACK_SEND, &args, sizeof(args)); } @@ -372,22 +389,41 @@ addressLength = sizeof(struct sockaddr_in); } - transfer_args args; + message_args args; + msghdr header; + memset(&header, 0, sizeof(header)); + + args.header = &header; args.data = const_cast(data); - args.data_length = length; + args.length = length; args.flags = flags; - args.address = const_cast(address); - args.address_length = addressLength; + header.msg_name = (char *)const_cast(address); + header.msg_namelen = addressLength; - return ioctl(socket, NET_STACK_SENDTO, &args, sizeof(args)); + return ioctl(socket, NET_STACK_SEND, &args, sizeof(args)); } extern "C" ssize_t sendmsg(int socket, const struct msghdr *message, int flags) { - msghdr_args args = { (msghdr *)message, flags }; - return ioctl(socket, NET_STACK_SENDMSG, &args, sizeof(args)); + message_args args; + + if (message == NULL || (message->msg_iovlen > 0 && message->msg_iov == NULL)) + return B_BAD_VALUE; + + args.header = const_cast(message); + args.flags = flags; + + if (message->msg_iovlen > 0) { + args.data = message->msg_iov[0].iov_base; + args.length = message->msg_iov[0].iov_len; + } else { + args.data = NULL; + args.length = 0; + } + + return ioctl(socket, NET_STACK_SEND, &args, sizeof(args)); } From hugosantos at mail.berlios.de Thu Apr 5 18:05:25 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Thu, 5 Apr 2007 18:05:25 +0200 Subject: [Haiku-commits] r20582 - in haiku/trunk/src/add-ons/kernel/network: protocols/ipv4 protocols/udp stack Message-ID: <200704051605.l35G5PIX016391@sheep.berlios.de> Author: hugosantos Date: 2007-04-05 18:05:07 +0200 (Thu, 05 Apr 2007) New Revision: 20582 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20582&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp haiku/trunk/src/add-ons/kernel/network/stack/link.cpp haiku/trunk/src/add-ons/kernel/network/stack/net_socket.cpp Log: properly support MSG_TRUNC. we don't even have to trim the buffer, just try to fill the user buffers as much as possible Modified: haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp 2007-04-05 14:26:46 UTC (rev 20581) +++ haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp 2007-04-05 16:05:07 UTC (rev 20582) @@ -187,11 +187,6 @@ if (status < B_OK) return status; - if (numBytes < buffer->size) { - // discard any data behind the amount requested - gBufferModule->trim(buffer, numBytes); - } - *_buffer = buffer; return B_OK; } Modified: haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp 2007-04-05 14:26:46 UTC (rev 20581) +++ haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp 2007-04-05 16:05:07 UTC (rev 20582) @@ -849,12 +849,6 @@ if (status < B_OK) return status; - if (numBytes < buffer->size) { - // discard any data behind the amount requested - gBufferModule->trim(buffer, numBytes); - // TODO: we should indicate MSG_TRUNC to application! - } - TRACE(("FetchData() returns buffer with %ld data bytes\n", buffer->size)); *_buffer = buffer; return B_OK; Modified: haiku/trunk/src/add-ons/kernel/network/stack/link.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/link.cpp 2007-04-05 14:26:46 UTC (rev 20581) +++ haiku/trunk/src/add-ons/kernel/network/stack/link.cpp 2007-04-05 16:05:07 UTC (rev 20582) @@ -337,11 +337,6 @@ if (status < B_OK) return status; - if (numBytes < buffer->size) { - // discard any data behind the amount requested - gNetBufferModule.trim(buffer, numBytes); - } - *_buffer = buffer; return B_OK; } Modified: haiku/trunk/src/add-ons/kernel/network/stack/net_socket.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/net_socket.cpp 2007-04-05 14:26:46 UTC (rev 20581) +++ haiku/trunk/src/add-ons/kernel/network/stack/net_socket.cpp 2007-04-05 16:05:07 UTC (rev 20582) @@ -230,8 +230,18 @@ socket_receive_data(net_socket *socket, size_t length, uint32 flags, net_buffer **_buffer) { - return socket->first_info->read_data(socket->first_protocol, + status_t status = socket->first_info->read_data(socket->first_protocol, length, flags, _buffer); + + if (status < B_OK) + return status; + + if (*_buffer && length < (*_buffer)->size) { + // discard any data behind the amount requested + gNetBufferModule.trim(*_buffer, length); + } + + return status; } @@ -761,9 +771,7 @@ if (status < B_OK) return status; - // TODO: - datagram based protocols should return the - // full datagram so we can cut it here with MSG_TRUNC - // - returning a NULL buffer when received 0 bytes + // TODO: - returning a NULL buffer when received 0 bytes // may not make much sense as we still need the address // - gNetBufferModule.read() uses memcpy() instead of user_memcpy @@ -814,8 +822,16 @@ gNetBufferModule.free(buffer); - if (bytesCopied < bytesReceived) + if (bytesCopied < bytesReceived) { + if (flags & MSG_TRUNC) { + if (header) + header->msg_flags = MSG_TRUNC; + + return bytesReceived; + } + return ENOBUFS; + } return bytesCopied; } From hugosantos at mail.berlios.de Thu Apr 5 18:09:16 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Thu, 5 Apr 2007 18:09:16 +0200 Subject: [Haiku-commits] r20583 - haiku/trunk/src/add-ons/kernel/network/stack Message-ID: <200704051609.l35G9Gxt016737@sheep.berlios.de> Author: hugosantos Date: 2007-04-05 18:09:06 +0200 (Thu, 05 Apr 2007) New Revision: 20583 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20583&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/stack/net_socket.cpp Log: as per the Open Group Specification, MSG_TRUNC should be set in flags whenever the packet is truncated Modified: haiku/trunk/src/add-ons/kernel/network/stack/net_socket.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/net_socket.cpp 2007-04-05 16:05:07 UTC (rev 20582) +++ haiku/trunk/src/add-ons/kernel/network/stack/net_socket.cpp 2007-04-05 16:09:06 UTC (rev 20583) @@ -823,14 +823,11 @@ gNetBufferModule.free(buffer); if (bytesCopied < bytesReceived) { - if (flags & MSG_TRUNC) { - if (header) - header->msg_flags = MSG_TRUNC; + if (header) + header->msg_flags = MSG_TRUNC; + if (flags & MSG_TRUNC) return bytesReceived; - } - - return ENOBUFS; } return bytesCopied; From hugosantos at mail.berlios.de Thu Apr 5 18:17:02 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Thu, 5 Apr 2007 18:17:02 +0200 Subject: [Haiku-commits] r20584 - haiku/trunk/src/add-ons/kernel/network/protocols/tcp Message-ID: <200704051617.l35GH28X017385@sheep.berlios.de> Author: hugosantos Date: 2007-04-05 18:16:51 +0200 (Thu, 05 Apr 2007) New Revision: 20584 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20584&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp Log: support MSG_WAITALL in TCP Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-05 16:09:06 UTC (rev 20583) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-05 16:16:51 UTC (rev 20584) @@ -505,14 +505,19 @@ && (fFlags & FLAG_NO_RECEIVE) == 0) { locker.Unlock(); + // Open Group Base Specification states that when + // MSG_WAITALL is set then the function should + // block until the full amount of data can be returned. + status_t status = acquire_sem_etc(fReceiveLock, 1, - B_ABSOLUTE_TIMEOUT | B_CAN_INTERRUPT, timeout); + ((flags & MSG_WAITALL) ? 0 : B_ABSOLUTE_TIMEOUT) + | B_CAN_INTERRUPT, timeout); locker.Lock(); if (status < B_OK) { // TODO: If we are timing out, should we push the - // available data? + // available data to the user? if (status == B_TIMED_OUT && fReceiveQueue.Available() > 0) break; return status; From hugosantos at mail.berlios.de Thu Apr 5 18:23:19 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Thu, 5 Apr 2007 18:23:19 +0200 Subject: [Haiku-commits] r20585 - haiku/trunk/src/add-ons/kernel/network/protocols/tcp Message-ID: <200704051623.l35GNJH5017841@sheep.berlios.de> Author: hugosantos Date: 2007-04-05 18:23:04 +0200 (Thu, 05 Apr 2007) New Revision: 20585 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20585&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp Log: Sigh, ignore previous commit, Open Group Specification is ambiguous. Now we properly support MSG_WAITALL. Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-05 16:16:51 UTC (rev 20584) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-05 16:23:04 UTC (rev 20585) @@ -498,10 +498,14 @@ // read data out of buffer // TODO: add support for urgent data (MSG_OOB) + size_t dataNeeded = socket->receive.low_water_mark; + if (flags & MSG_WAITALL) + dataNeeded = numBytes; + bigtime_t timeout = system_time() + socket->receive.timeout; while (fReceiveQueue.PushedData() == 0 - && fReceiveQueue.Available() < numBytes + && fReceiveQueue.Available() < dataNeeded && (fFlags & FLAG_NO_RECEIVE) == 0) { locker.Unlock(); @@ -510,8 +514,7 @@ // block until the full amount of data can be returned. status_t status = acquire_sem_etc(fReceiveLock, 1, - ((flags & MSG_WAITALL) ? 0 : B_ABSOLUTE_TIMEOUT) - | B_CAN_INTERRUPT, timeout); + B_ABSOLUTE_TIMEOUT | B_CAN_INTERRUPT, timeout); locker.Lock(); From hugosantos at mail.berlios.de Thu Apr 5 19:56:20 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Thu, 5 Apr 2007 19:56:20 +0200 Subject: [Haiku-commits] r20586 - haiku/trunk/src/add-ons/kernel/network/stack Message-ID: <200704051756.l35HuKE5005147@sheep.berlios.de> Author: hugosantos Date: 2007-04-05 19:56:09 +0200 (Thu, 05 Apr 2007) New Revision: 20586 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20586&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/stack/net_socket.cpp Log: copy back the source address even when the data is truncated Modified: haiku/trunk/src/add-ons/kernel/network/stack/net_socket.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/net_socket.cpp 2007-04-05 16:23:04 UTC (rev 20585) +++ haiku/trunk/src/add-ons/kernel/network/stack/net_socket.cpp 2007-04-05 17:56:09 UTC (rev 20586) @@ -814,7 +814,7 @@ bytesCopied += toRead; } - if (bytesCopied == bytesReceived && header->msg_name != NULL) { + if (header->msg_name != NULL) { header->msg_namelen = min_c(nameLen, buffer->source.ss_len); memcpy(header->msg_name, &buffer->source, header->msg_namelen); } From hugosantos at mail.berlios.de Thu Apr 5 19:56:46 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Thu, 5 Apr 2007 19:56:46 +0200 Subject: [Haiku-commits] r20587 - in haiku/trunk: headers/private/net src/add-ons/kernel/network/protocols/ipv4 src/add-ons/kernel/network/protocols/udp src/add-ons/kernel/network/stack Message-ID: <200704051756.l35HukuW005172@sheep.berlios.de> Author: hugosantos Date: 2007-04-05 19:56:20 +0200 (Thu, 05 Apr 2007) New Revision: 20587 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20587&view=rev Modified: haiku/trunk/headers/private/net/net_stack.h haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp haiku/trunk/src/add-ons/kernel/network/stack/link.cpp haiku/trunk/src/add-ons/kernel/network/stack/stack.cpp haiku/trunk/src/add-ons/kernel/network/stack/utility.cpp haiku/trunk/src/add-ons/kernel/network/stack/utility.h Log: introduced fifo_socket_enqueue_buffer which clones the buffer, enqueues it to the fifo and notifies the socket. - changed the link, ipv4 and udp modules to use fifo_socket_enqueue_buffer Modified: haiku/trunk/headers/private/net/net_stack.h =================================================================== --- haiku/trunk/headers/private/net/net_stack.h 2007-04-05 17:56:09 UTC (rev 20586) +++ haiku/trunk/headers/private/net/net_stack.h 2007-04-05 17:56:20 UTC (rev 20587) @@ -90,6 +90,8 @@ ssize_t (*fifo_dequeue_buffer)(struct net_fifo *fifo, uint32 flags, bigtime_t timeout, struct net_buffer **_buffer); status_t (*clear_fifo)(struct net_fifo *fifo); + status_t (*fifo_socket_enqueue_buffer)(struct net_fifo *, struct net_socket *, + uint8 event, struct net_buffer *); // timer void (*init_timer)(struct net_timer *timer, net_timer_func hook, void *data); Modified: haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp 2007-04-05 17:56:09 UTC (rev 20586) +++ haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp 2007-04-05 17:56:20 UTC (rev 20587) @@ -202,19 +202,8 @@ status_t RawSocket::Write(net_buffer *source) { - // we need to make a clone for that buffer and pass it to the socket - net_buffer *buffer = gBufferModule->clone(source, false); - TRACE(("ipv4::RawSocket::Write(): cloned buffer %p\n", buffer)); - if (buffer == NULL) - return B_NO_MEMORY; - - status_t status = sStackModule->fifo_enqueue_buffer(&fFifo, buffer); - if (status >= B_OK) - sStackModule->notify_socket(fSocket, B_SELECT_READ, BytesAvailable()); - else - gBufferModule->free(buffer); - - return status; + return sStackModule->fifo_socket_enqueue_buffer(&fFifo, fSocket, + B_SELECT_READ, source); } Modified: haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp 2007-04-05 17:56:09 UTC (rev 20586) +++ haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp 2007-04-05 17:56:20 UTC (rev 20587) @@ -860,17 +860,9 @@ { TRACE(("buffer %p passed to endpoint with (%s)\n", _buffer, AddressString(sDomain, (sockaddr *)&socket->address, true).Data())); - net_buffer *buffer = gBufferModule->clone(_buffer, false); - if (buffer == NULL) - return B_NO_MEMORY; - status_t status = sStackModule->fifo_enqueue_buffer(&fFifo, buffer); - if (status >= B_OK) - sStackModule->notify_socket(socket, B_SELECT_READ, BytesAvailable()); - else - gBufferModule->free(buffer); - - return status; + return sStackModule->fifo_socket_enqueue_buffer(&fFifo, socket, + B_SELECT_READ, _buffer); } Modified: haiku/trunk/src/add-ons/kernel/network/stack/link.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/link.cpp 2007-04-05 17:56:09 UTC (rev 20586) +++ haiku/trunk/src/add-ons/kernel/network/stack/link.cpp 2007-04-05 17:56:20 UTC (rev 20587) @@ -40,19 +40,8 @@ { link_protocol *protocol = (link_protocol *)cookie; - // we need to make a clone for that buffer and pass it to the socket - net_buffer *buffer = gNetBufferModule.clone(packet, false); - if (buffer == NULL) - return B_NO_MEMORY; - - status_t status = fifo_enqueue_buffer(&protocol->fifo, buffer); - if (status >= B_OK) - notify_socket(protocol->socket, B_SELECT_READ, - protocol->fifo.current_bytes); - else - gNetBufferModule.free(buffer); - - return status; + return fifo_socket_enqueue_buffer(&protocol->fifo, protocol->socket, + B_SELECT_READ, packet); } Modified: haiku/trunk/src/add-ons/kernel/network/stack/stack.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/stack.cpp 2007-04-05 17:56:09 UTC (rev 20586) +++ haiku/trunk/src/add-ons/kernel/network/stack/stack.cpp 2007-04-05 17:56:20 UTC (rev 20587) @@ -923,6 +923,7 @@ fifo_enqueue_buffer, fifo_dequeue_buffer, clear_fifo, + fifo_socket_enqueue_buffer, init_timer, set_timer, Modified: haiku/trunk/src/add-ons/kernel/network/stack/utility.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/utility.cpp 2007-04-05 17:56:09 UTC (rev 20586) +++ haiku/trunk/src/add-ons/kernel/network/stack/utility.cpp 2007-04-05 17:56:20 UTC (rev 20587) @@ -134,11 +134,9 @@ } -status_t -fifo_enqueue_buffer(net_fifo *fifo, net_buffer *buffer) +static status_t +_fifo_enqueue_buffer(net_fifo *fifo, net_buffer *buffer) { - BenaphoreLocker locker(fifo->lock); - if (fifo->max_bytes > 0 && fifo->current_bytes + buffer->size > fifo->max_bytes) return ENOBUFS; @@ -155,7 +153,14 @@ return B_OK; } +status_t +fifo_enqueue_buffer(net_fifo *fifo, net_buffer *buffer) +{ + BenaphoreLocker locker(fifo->lock); + return _fifo_enqueue_buffer(fifo, buffer); +} + /*! Gets the first buffer from the FIFO. If there is no buffer, it will wait depending on the \a flags and \a timeout. @@ -243,6 +248,26 @@ } +status_t +fifo_socket_enqueue_buffer(net_fifo *fifo, net_socket *socket, uint8 event, + net_buffer *_buffer) +{ + net_buffer *buffer = gNetBufferModule.clone(_buffer, false); + if (buffer == NULL) + return B_NO_MEMORY; + + BenaphoreLocker locker(fifo->lock); + + status_t status = _fifo_enqueue_buffer(fifo, buffer); + if (status < B_OK) + gNetBufferModule.free(buffer); + else + notify_socket(socket, event, fifo->current_bytes); + + return status; +} + + // #pragma mark - Timer Modified: haiku/trunk/src/add-ons/kernel/network/stack/utility.h =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/utility.h 2007-04-05 17:56:09 UTC (rev 20586) +++ haiku/trunk/src/add-ons/kernel/network/stack/utility.h 2007-04-05 17:56:20 UTC (rev 20587) @@ -62,6 +62,8 @@ ssize_t fifo_dequeue_buffer(net_fifo *fifo, uint32 flags, bigtime_t timeout, struct net_buffer **_buffer); status_t clear_fifo(net_fifo *fifo); +status_t fifo_socket_enqueue_buffer(net_fifo *, net_socket *, uint8 event, + net_buffer *); // timer void init_timer(net_timer *timer, net_timer_func hook, void *data); From hugosantos at mail.berlios.de Thu Apr 5 20:35:32 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Thu, 5 Apr 2007 20:35:32 +0200 Subject: [Haiku-commits] r20588 - haiku/trunk/src/add-ons/kernel/network/protocols/udp Message-ID: <200704051835.l35IZWaQ009001@sheep.berlios.de> Author: hugosantos Date: 2007-04-05 20:35:22 +0200 (Thu, 05 Apr 2007) New Revision: 20588 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20588&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp Log: fixed an issue in UDP due to copying addresses to sockaddr, which may be too small for protocols other than IPv4. In fact, we don't need to copy the addresses at all, we can use the original address pointers in the hash key for lookup and hashing. Modified: haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp 2007-04-05 17:56:20 UTC (rev 20587) +++ haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp 2007-04-05 18:35:22 UTC (rev 20588) @@ -1,9 +1,10 @@ /* - * Copyright 2006, Haiku, Inc. All Rights Reserved. + * Copyright 2006-2007, Haiku, Inc. All Rights Reserved. * Distributed under the terms of the MIT License. * * Authors: * Oliver Tappe, zooey at hirschkaefer.de + * Hugo Santos, hugosantos at gmail.com */ @@ -25,6 +26,7 @@ #include #include #include +#include //#define TRACE_UDP @@ -81,14 +83,8 @@ class UdpEndpointManager { + typedef std::pair HashKey; - struct hash_key { - hash_key(sockaddr *ourAddress, sockaddr *peerAddress); - - sockaddr ourAddress; - sockaddr peerAddress; - }; - class Ephemerals { public: Ephemerals(); @@ -155,16 +151,6 @@ // #pragma mark - -UdpEndpointManager::hash_key::hash_key(sockaddr *_ourAddress, sockaddr *_peerAddress) -{ - memcpy(&ourAddress, _ourAddress, sizeof(sockaddr)); - memcpy(&peerAddress, _peerAddress, sizeof(sockaddr)); -} - - -// #pragma mark - - - UdpEndpointManager::Ephemerals::Ephemerals() : fLastUsed(kLast) @@ -278,13 +264,13 @@ UdpEndpointManager::Compare(void *_udpEndpoint, const void *_key) { struct UdpEndpoint *udpEndpoint = (UdpEndpoint*)_udpEndpoint; - hash_key *key = (hash_key *)_key; + const HashKey *key = (const HashKey *)_key; sockaddr *ourAddr = (sockaddr *)&udpEndpoint->socket->address; sockaddr *peerAddr = (sockaddr *)&udpEndpoint->socket->peer; - if (sAddressModule->equal_addresses_and_ports(ourAddr, &key->ourAddress) - && sAddressModule->equal_addresses_and_ports(peerAddr, &key->peerAddress)) + if (sAddressModule->equal_addresses_and_ports(ourAddr, key->first) + && sAddressModule->equal_addresses_and_ports(peerAddr, key->second)) return 0; return 1; @@ -309,8 +295,8 @@ sockaddr *peerAddr = (sockaddr*)&udpEndpoint->socket->peer; hash = ComputeHash(ourAddr, peerAddr); } else { - hash_key *key = (hash_key *)_key; - hash = ComputeHash(&key->ourAddress, &key->peerAddress); + const HashKey *key = (const HashKey *)_key; + hash = ComputeHash(key->first, key->second); } // move the bits into the relevant range (as defined by kNumHashBuckets): @@ -332,9 +318,9 @@ TRACE(("trying to find UDP-endpoint for (l:%s p:%s)\n", AddressString(sDomain, ourAddress, true).Data(), AddressString(sDomain, peerAddress, true).Data())); - hash_key key(ourAddress, peerAddress); - UdpEndpoint *endpoint = (UdpEndpoint *)hash_lookup(fActiveEndpoints, &key); - return endpoint; + + HashKey key(ourAddress, peerAddress); + return (UdpEndpoint *)hash_lookup(fActiveEndpoints, &key); } From hugosantos at mail.berlios.de Thu Apr 5 20:57:30 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Thu, 5 Apr 2007 20:57:30 +0200 Subject: [Haiku-commits] r20589 - in haiku/trunk/src/add-ons/kernel/network/protocols: ipv4 udp Message-ID: <200704051857.l35IvU8r010606@sheep.berlios.de> Author: hugosantos Date: 2007-04-05 20:57:15 +0200 (Thu, 05 Apr 2007) New Revision: 20589 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20589&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4_address.cpp haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp Log: small cleanups in UDP - don't set_to_empty_address, instead consider NULL to be the empty address and use is_empty_address(). - most ipv4 address module calls already consider NULL to be the empty address, ipv4_hash_address_pair didn't, fixed. Modified: haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4_address.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4_address.cpp 2007-04-05 18:35:22 UTC (rev 20588) +++ haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4_address.cpp 2007-04-05 18:57:15 UTC (rev 20589) @@ -350,11 +350,11 @@ static uint32 ipv4_hash_address_pair(const sockaddr *ourAddress, const sockaddr *peerAddress) { - int32 hash = (((sockaddr_in *)ourAddress)->sin_port - | ((sockaddr_in *)peerAddress)->sin_port << 16) - ^ ((sockaddr_in *)ourAddress)->sin_addr.s_addr - ^ ((sockaddr_in *)peerAddress)->sin_addr.s_addr; - return hash; + const sockaddr_in *our = (const sockaddr_in *)ourAddress; + const sockaddr_in *peer = (const sockaddr_in *)peerAddress; + + return ((our ? our->sin_port : 0) | ((peer ? peer->sin_port : 0) << 16)) + ^ (our ? our->sin_addr.s_addr : 0) ^ (peer ? peer->sin_addr.s_addr : 0); } Modified: haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp 2007-04-05 18:35:22 UTC (rev 20588) +++ haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp 2007-04-05 18:57:15 UTC (rev 20589) @@ -83,7 +83,7 @@ class UdpEndpointManager { - typedef std::pair HashKey; + typedef std::pair HashKey; class Ephemerals { public: @@ -108,7 +108,8 @@ status_t ReceiveData(net_buffer *buffer); static int Compare(void *udpEndpoint, const void *_key); - static uint32 ComputeHash(sockaddr *ourAddress, sockaddr *peerAddress); + static uint32 ComputeHash(const sockaddr *ourAddress, + const sockaddr *peerAddress); static uint32 Hash(void *udpEndpoint, const void *key, uint32 range); UdpEndpoint *FindActiveEndpoint(sockaddr *ourAddress, @@ -278,7 +279,8 @@ /*static*/ inline uint32 -UdpEndpointManager::ComputeHash(sockaddr *ourAddress, sockaddr *peerAddress) +UdpEndpointManager::ComputeHash(const sockaddr *ourAddress, + const sockaddr *peerAddress) { return sAddressModule->hash_address_pair(ourAddress, peerAddress); } @@ -287,18 +289,19 @@ /*static*/ uint32 UdpEndpointManager::Hash(void *_udpEndpoint, const void *_key, uint32 range) { + HashKey addresses; uint32 hash; if (_udpEndpoint) { - struct UdpEndpoint *udpEndpoint = (UdpEndpoint*)_udpEndpoint; - sockaddr *ourAddr = (sockaddr*)&udpEndpoint->socket->address; - sockaddr *peerAddr = (sockaddr*)&udpEndpoint->socket->peer; - hash = ComputeHash(ourAddr, peerAddr); + const UdpEndpoint *udpEndpoint = (const UdpEndpoint *)_udpEndpoint; + addresses = HashKey((const sockaddr *)&udpEndpoint->socket->address, + (const sockaddr *)&udpEndpoint->socket->peer); } else { - const HashKey *key = (const HashKey *)_key; - hash = ComputeHash(key->first, key->second); + addresses = *(const HashKey *)_key; } + hash = ComputeHash(addresses.first, addresses.second); + // move the bits into the relevant range (as defined by kNumHashBuckets): hash = (hash & 0x000007FF) ^ (hash & 0x003FF800) >> 11 ^ (hash & 0xFFC00000UL) >> 22; @@ -335,9 +338,6 @@ TRACE(("demuxing buffer %p as broadcast...\n", buffer)); - sockaddr anyAddr; - sAddressModule->set_to_empty_address(&anyAddr); - uint16 incomingPort = sAddressModule->get_port(broadcastAddr); UdpEndpoint *endpoint; @@ -369,7 +369,7 @@ } if (sAddressModule->equal_masked_addresses(addr, broadcastAddr, mask) - || sAddressModule->equal_addresses(addr, &anyAddr)) { + || sAddressModule->is_empty_address(addr, false)) { // address matches, dispatch to this endpoint: endpoint->StoreData(buffer); } @@ -394,15 +394,12 @@ TRACE(("demuxing buffer %p as unicast...\n", buffer)); - struct sockaddr anyAddr; - sAddressModule->set_to_empty_address(&anyAddr); - UdpEndpoint *endpoint; // look for full (most special) match: endpoint = FindActiveEndpoint(localAddr, peerAddr); if (!endpoint) { // look for endpoint matching local address & port: - endpoint = FindActiveEndpoint(localAddr, &anyAddr); + endpoint = FindActiveEndpoint(localAddr, NULL); if (!endpoint) { // look for endpoint matching peer address & port and local port: sockaddr localPortAddr; @@ -412,7 +409,7 @@ endpoint = FindActiveEndpoint(&localPortAddr, peerAddr); if (!endpoint) { // last chance: look for endpoint matching local port only: - endpoint = FindActiveEndpoint(&localPortAddr, &anyAddr); + endpoint = FindActiveEndpoint(&localPortAddr, NULL); } } } From hugosantos at mail.berlios.de Thu Apr 5 21:19:52 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Thu, 5 Apr 2007 21:19:52 +0200 Subject: [Haiku-commits] r20590 - in haiku/trunk/src/add-ons/kernel/network/protocols: ipv4 udp Message-ID: <200704051919.l35JJqrp011776@sheep.berlios.de> Author: hugosantos Date: 2007-04-05 21:19:38 +0200 (Thu, 05 Apr 2007) New Revision: 20590 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20590&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp Log: send buffer size is irrelevant for UDP, instead check if the fed buffer is larger than the maximum payload UDP supported. Do the same in IPV4. Modified: haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp 2007-04-05 18:57:15 UTC (rev 20589) +++ haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp 2007-04-05 19:19:38 UTC (rev 20590) @@ -977,6 +977,9 @@ bufferHeader.Detach(); } + if (buffer->size > 0xffff) + return EMSGSIZE; + TRACE(("header chksum: %ld, buffer checksum: %ld\n", gBufferModule->checksum(buffer, 0, sizeof(ipv4_header), true), gBufferModule->checksum(buffer, 0, buffer->size, true))); Modified: haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp 2007-04-05 18:57:15 UTC (rev 20589) +++ haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp 2007-04-05 19:19:38 UTC (rev 20590) @@ -764,7 +764,7 @@ status_t UdpEndpoint::SendData(net_buffer *buffer, net_route *route) { - if (buffer->size > socket->send.buffer_size) + if (buffer->size > 0xffff) return EMSGSIZE; buffer->protocol = IPPROTO_UDP; @@ -856,9 +856,6 @@ udp_init_protocol(net_socket *socket) { socket->protocol = IPPROTO_UDP; - socket->send.buffer_size = 65535 - 20 - 8; - // subtract lengths of IP and UDP headers (NOTE: IP headers could be - // larger if IP options are used, but we do not currently care for that) UdpEndpoint *endpoint = new (std::nothrow) UdpEndpoint(socket); TRACE(("udp_init_protocol(%p) created endpoint %p\n", socket, endpoint)); From zooey at hirschkaefer.de Thu Apr 5 21:35:39 2007 From: zooey at hirschkaefer.de (Oliver Tappe) Date: Thu, 05 Apr 2007 21:35:39 +0200 Subject: [Haiku-commits] r20590 - in haiku/trunk/src/add-ons/kernel/network/protocols: ipv4 udp In-Reply-To: <200704051919.l35JJqrp011776@sheep.berlios.de> References: <200704051919.l35JJqrp011776@sheep.berlios.de> Message-ID: <20070405213539.1370.3@bee.hirschkaefer.site> Hi Hugo, thanks for cleaning up the UDP-stuff. However, I do not understand one thing... (see below) On 2007-04-05 at 21:19:52 [+0200], hugosantos at mail.berlios.de wrote: [ ... ] > status_t > UdpEndpoint::SendData(net_buffer *buffer, net_route *route) > { > - if (buffer->size > socket->send.buffer_size) > + if (buffer->size > 0xffff) > return EMSGSIZE; What happens if the user request to send a datagram of 65535 bytes? The resulting net buffer is going to exceed 0xFFFF bytes, so things will blow, right? Well, probably I'm just missing something... cheers, Oliver From revol at free.fr Thu Apr 5 21:43:57 2007 From: revol at free.fr (=?windows-1252?q?Fran=E7ois?= Revol) Date: Thu, 05 Apr 2007 21:43:57 +0200 CEST Subject: [Haiku-commits] r20590 - in haiku/trunk/src/add-ons/kernel/network/protocols: ipv4 udp In-Reply-To: <20070405213539.1370.3@bee.hirschkaefer.site> Message-ID: <1595641941-BeMail@laptop> > Hi Hugo, > > thanks for cleaning up the UDP-stuff. > Hmm, looks like it's time to test NFS again :)) (it used to mount succesfully but them loose a reply and keep asking for retransmit or something) I'll let you know :) Fran?ois. From hugosantos at gmail.com Thu Apr 5 21:44:32 2007 From: hugosantos at gmail.com (Hugo Santos) Date: Thu, 5 Apr 2007 20:44:32 +0100 Subject: [Haiku-commits] r20590 - in haiku/trunk/src/add-ons/kernel/network/protocols: ipv4 udp In-Reply-To: <20070405213539.1370.3@bee.hirschkaefer.site> References: <200704051919.l35JJqrp011776@sheep.berlios.de> <20070405213539.1370.3@bee.hirschkaefer.site> Message-ID: <9c46321e0704051244l4c9e5afak2906a1ccc370b413@mail.gmail.com> Hey Oliver, On 4/5/07, Oliver Tappe wrote: > What happens if the user request to send a datagram of 65535 bytes? The > resulting net buffer is going to exceed 0xFFFF bytes, so things will blow, > right? IPv4 will reject buffers with ->size > 0xffff as well. The thing is that UDP can't assume anything about the lower layers space requirements. Hope this answers your question. Hugo From hugosantos at mail.berlios.de Thu Apr 5 22:45:20 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Thu, 5 Apr 2007 22:45:20 +0200 Subject: [Haiku-commits] r20591 - haiku/trunk/src/add-ons/kernel/network/stack Message-ID: <200704052045.l35KjKZj017542@sheep.berlios.de> Author: hugosantos Date: 2007-04-05 22:45:10 +0200 (Thu, 05 Apr 2007) New Revision: 20591 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20591&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/stack/net_buffer.cpp Log: small cleanup, use get_node_at_offset(). Modified: haiku/trunk/src/add-ons/kernel/network/stack/net_buffer.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/net_buffer.cpp 2007-04-05 19:19:38 UTC (rev 20590) +++ haiku/trunk/src/add-ons/kernel/network/stack/net_buffer.cpp 2007-04-05 20:45:10 UTC (rev 20591) @@ -240,6 +240,20 @@ } +static inline data_node * +get_node_at_offset(net_buffer_private *buffer, size_t offset) +{ + data_node *node = (data_node *)list_get_first_item(&buffer->buffers); + while (node->offset + node->used < offset) { + node = (data_node *)list_get_next_item(&buffer->buffers, node); + if (node == NULL) + return NULL; + } + + return node; +} + + // #pragma mark - @@ -528,19 +542,6 @@ } -static inline data_node * -get_node_at_offset(net_buffer_private *buffer, size_t offset) -{ - data_node *node = (data_node *)list_get_first_item(&buffer->buffers); - while (node->offset + node->used < offset) { - node = (data_node *)list_get_next_item(&buffer->buffers, node); - if (node == NULL) - return NULL; - } - - return node; -} - /*! Writes into existing allocated memory. \return B_BAD_VALUE if you write outside of the buffers current bounds. @@ -870,13 +871,10 @@ if (newSize == buffer->size) return B_OK; - data_node *node = (data_node *)list_get_first_item(&buffer->buffers); - while (node->offset + node->used < newSize) { - node = (data_node *)list_get_next_item(&buffer->buffers, node); - if (node == NULL) { - // trim size greater than buffer size - return B_BAD_VALUE; - } + data_node *node = get_node_at_offset(buffer, newSize); + if (node == NULL) { + // trim size greater than buffer size + return B_BAD_VALUE; } int32 diff = node->used + node->offset - newSize; From axeld at pinc-software.de Thu Apr 5 23:28:51 2007 From: axeld at pinc-software.de (Axel =?iso-8859-15?q?D=F6rfler?=) Date: Thu, 05 Apr 2007 23:28:51 +0200 CEST Subject: [Haiku-commits] =?iso-8859-15?q?r20587_-_in_haiku/trunk=3A_header?= =?iso-8859-15?q?s/private/net_src/add-ons/kernel/network/protocols/ipv4_s?= =?iso-8859-15?q?rc/add-ons/kernel/network/protocols/udp_src/add-ons/kerne?= =?iso-8859-15?q?l/network/stack?= In-Reply-To: <200704051756.l35HukuW005172@sheep.berlios.de> Message-ID: <47665900955-BeMail@zon> hugosantos at mail.berlios.de wrote: > + return fifo_socket_enqueue_buffer(&protocol->fifo, protocol-> > socket, > + B_SELECT_READ, packet); Not that I getting lazy, but there still should just be a single tab in front of the second line :-) Bye, Axel. From hugosantos at gmail.com Thu Apr 5 23:31:59 2007 From: hugosantos at gmail.com (Hugo Santos) Date: Thu, 5 Apr 2007 22:31:59 +0100 Subject: [Haiku-commits] r20587 - in haiku/trunk: headers/private/net src/add-ons/kernel/network/protocols/ipv4 src/add-ons/kernel/network/protocols/udp src/add-ons/kernel/network/stack In-Reply-To: <47665900955-BeMail@zon> References: <200704051756.l35HukuW005172@sheep.berlios.de> <47665900955-BeMail@zon> Message-ID: <9c46321e0704051431x42f0375bt41cd4b246cb19163@mail.gmail.com> Hey Axel, Wouldn't a single tab here put B_SELECT_READ just below return? That would be hard to read. Maybe i'm missing something? Or do you mean one single tab after the previous alignment, so in this case, two total tabs? Hugo On 4/5/07, Axel D?rfler wrote: > hugosantos at mail.berlios.de wrote: > > + return fifo_socket_enqueue_buffer(&protocol->fifo, protocol-> > > socket, > > + B_SELECT_READ, packet); > > Not that I getting lazy, but there still should just be a single tab in > front of the second line :-) > > Bye, > Axel. > > _______________________________________________ > Haiku-commits mailing list > Haiku-commits at lists.berlios.de > https://lists.berlios.de/mailman/listinfo/haiku-commits > From axeld at pinc-software.de Thu Apr 5 23:42:13 2007 From: axeld at pinc-software.de (Axel =?iso-8859-15?q?D=F6rfler?=) Date: Thu, 05 Apr 2007 23:42:13 +0200 CEST Subject: [Haiku-commits] =?iso-8859-15?q?r20587_-_in_haiku/trunk=3A_header?= =?iso-8859-15?q?s/private/net_src/add-ons/kernel/network/protocols/ipv4_s?= =?iso-8859-15?q?rc/add-ons/kernel/network/protocols/udp_src/add-ons/kerne?= =?iso-8859-15?q?l/network/stack?= In-Reply-To: <9c46321e0704051431x42f0375bt41cd4b246cb19163@mail.gmail.com> Message-ID: <48467237705-BeMail@zon> "Hugo Santos" wrote: > Wouldn't a single tab here put B_SELECT_READ just below return? > That > would be hard to read. Maybe i'm missing something? Or do you mean > one > single tab after the previous alignment, so in this case, two total > tabs? Exactly, one tab more than in the line above :-) Anyway, nice changes! Bye, Axel. From hugosantos at gmail.com Thu Apr 5 23:45:17 2007 From: hugosantos at gmail.com (Hugo Santos) Date: Thu, 5 Apr 2007 22:45:17 +0100 Subject: [Haiku-commits] r20587 - in haiku/trunk: headers/private/net src/add-ons/kernel/network/protocols/ipv4 src/add-ons/kernel/network/protocols/udp src/add-ons/kernel/network/stack In-Reply-To: <48467237705-BeMail@zon> References: <9c46321e0704051431x42f0375bt41cd4b246cb19163@mail.gmail.com> <48467237705-BeMail@zon> Message-ID: <9c46321e0704051445p1ec60b2fla4f67920c0c70aed@mail.gmail.com> On 4/5/07, Axel D?rfler wrote: > Exactly, one tab more than in the line above :-) > Anyway, nice changes! Thanks :-) I'll try to remember the tabs. Hugo From hugosantos at mail.berlios.de Fri Apr 6 00:43:04 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Fri, 6 Apr 2007 00:43:04 +0200 Subject: [Haiku-commits] r20592 - in haiku/trunk/src/add-ons/kernel/network/protocols: tcp udp Message-ID: <200704052243.l35Mh4uI018759@sheep.berlios.de> Author: hugosantos Date: 2007-04-06 00:42:45 +0200 (Fri, 06 Apr 2007) New Revision: 20592 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20592&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp Log: tiny TCP cleanups, move the read notifications to _NotifyReader(). - Also fixed the buffer size check in UDP's SendData() since UDP's length field includes the size of the header we need to check that as well. IPv4 is correct since we check for the size after prepending the header (due to it being possibly already included). Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-05 20:45:10 UTC (rev 20591) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-05 22:42:45 UTC (rev 20592) @@ -490,7 +490,8 @@ } if ((fFlags & FLAG_NO_RECEIVE) != 0 && fReceiveQueue.Available() == 0) { - // there is no data left in the queue, and we can't receive anything, anymore + // there is no data left in the queue, and we can't receive anything, + // anymore *_buffer = NULL; return B_OK; } @@ -499,6 +500,9 @@ // TODO: add support for urgent data (MSG_OOB) size_t dataNeeded = socket->receive.low_water_mark; + + // When MSG_WAITALL is set then the function should block + // until the full amount of data can be returned. if (flags & MSG_WAITALL) dataNeeded = numBytes; @@ -509,10 +513,6 @@ && (fFlags & FLAG_NO_RECEIVE) == 0) { locker.Unlock(); - // Open Group Base Specification states that when - // MSG_WAITALL is set then the function should - // block until the full amount of data can be returned. - status_t status = acquire_sem_etc(fReceiveLock, 1, B_ABSOLUTE_TIMEOUT | B_CAN_INTERRUPT, timeout); @@ -543,7 +543,7 @@ TRACE("ReadAvailable()"); RecursiveLocker locker(fLock); - return _AvailableBytesOrDisconnect(); + return _AvailableData(); } @@ -740,7 +740,7 @@ release_sem_etc(fSendLock, 1, B_DO_NOT_RESCHEDULE); release_sem_etc(fReceiveLock, 1, B_DO_NOT_RESCHEDULE); // TODO: this is not enough - we need to use B_RELEASE_ALL - gSocketModule->notify(socket, B_SELECT_READ, fReceiveQueue.Available()); + _NotifyReader(); } else { // simultaneous open fState = SYNCHRONIZE_RECEIVED; @@ -813,23 +813,21 @@ release_sem_etc(fReceiveLock, 1, B_DO_NOT_RESCHEDULE); // TODO: real conditional locking needed! - gSocketModule->notify(socket, B_SELECT_READ, - fReceiveQueue.Available()); + _NotifyReader(); return KEEP | ACKNOWLEDGE; } } } - // The fast path was not applicable, so we continue with the standard processing - // of the incoming segment + // The fast path was not applicable, so we continue with the standard + // processing of the incoming segment - // First have a look at the data being sent - if (segment.flags & TCP_FLAG_RESET) { // is this a valid reset? if (fLastAcknowledgeSent <= segment.sequence - && tcp_sequence(segment.sequence) < fLastAcknowledgeSent + fReceiveWindow) { + && tcp_sequence(segment.sequence) + < (fLastAcknowledgeSent + fReceiveWindow)) { if (fState == SYNCHRONIZE_RECEIVED) { // TODO: if we came from SYN-SENT signal connection refused // and remove all segments from tx queue @@ -843,7 +841,7 @@ if (fState != TIME_WAIT && fReceiveQueue.Available() > 0) { release_sem_etc(fReceiveLock, 1, B_DO_NOT_RESCHEDULE); // TODO: real conditional locking needed! - gSocketModule->notify(socket, B_SELECT_READ, 1); + _NotifyReader(); } else { return DELETE | DROP; } @@ -854,14 +852,15 @@ return DROP; } + if ((segment.flags & TCP_FLAG_SYNCHRONIZE) != 0 || (fState == SYNCHRONIZE_RECEIVED && (fInitialReceiveSequence > segment.sequence || (segment.flags & TCP_FLAG_ACKNOWLEDGE) != 0 && (fSendUnacknowledged > segment.acknowledge || fSendMax < segment.acknowledge)))) { - // reset the connection - either the initial SYN was faulty, or we received - // a SYN within the data stream + // reset the connection - either the initial SYN was faulty, or we + // received a SYN within the data stream return DROP | RESET; } @@ -872,7 +871,8 @@ int32 drop = fReceiveNext - segment.sequence; if (drop > 0) { if ((uint32)drop > buffer->size - || ((uint32)drop == buffer->size && (segment.flags & TCP_FLAG_FINISH) == 0)) { + || ((uint32)drop == buffer->size + && (segment.flags & TCP_FLAG_FINISH) == 0)) { // don't accidently remove a FIN we shouldn't remove segment.flags &= ~TCP_FLAG_FINISH; drop = buffer->size; @@ -924,7 +924,7 @@ release_sem_etc(fSendLock, 1, B_DO_NOT_RESCHEDULE); release_sem_etc(fReceiveLock, 1, B_DO_NOT_RESCHEDULE); // TODO: real conditional locking needed! - gSocketModule->notify(socket, B_SELECT_READ, fReceiveQueue.Available()); + _NotifyReader(); } if (fSendMax < segment.acknowledge || fState == TIME_WAIT) @@ -994,7 +994,15 @@ if (advertisedWindow > fSendMaxWindow) fSendMaxWindow = advertisedWindow; - // TODO: process urgent data! + if (segment.flags & TCP_FLAG_URGENT) { + if (fState == ESTABLISHED || fState == FINISH_SENT + || fState == FINISH_ACKNOWLEDGED) { + // TODO: Handle urgent data: + // - RCV.UP <- max(RCV.UP, SEG.UP) + // - signal the user that urgent data is available (SIGURG) + } + } + // TODO: ignore data *after* FIN if (segment.flags & TCP_FLAG_FINISH) { @@ -1003,7 +1011,7 @@ release_sem_etc(fReceiveLock, 1, B_DO_NOT_RESCHEDULE); // TODO: real conditional locking needed! - gSocketModule->notify(socket, B_SELECT_READ, _AvailableBytesOrDisconnect()); + _NotifyReader(); // other side is closing connection; change states switch (fState) { @@ -1044,7 +1052,7 @@ release_sem_etc(fReceiveLock, 1, B_DO_NOT_RESCHEDULE); // TODO: real conditional locking needed! - gSocketModule->notify(socket, B_SELECT_READ, fReceiveQueue.Available()); + _NotifyReader(); } else gBufferModule->free(buffer); @@ -1293,20 +1301,6 @@ } -ssize_t -TCPEndpoint::_AvailableBytesOrDisconnect() const -{ - size_t availableBytes = fReceiveQueue.Available(); - if (availableBytes > 0) - return availableBytes; - - if ((fFlags & FLAG_NO_RECEIVE) != 0) - return ENOTCONN; - - return 0; -} - - status_t TCPEndpoint::_ShutdownEgress(bool closing) { @@ -1333,6 +1327,27 @@ } +ssize_t +TCPEndpoint::_AvailableData() const +{ + ssize_t availableData = fReceiveQueue.Available(); + + // FLAG_NO_RECEIVE is set whenever the socket is in a state + // where read() would be non-blocking and return 0. + if ((fFlags & FLAG_NO_RECEIVE) && availableData == 0) + return ENOTCONN; + + return availableData; +} + + +void +TCPEndpoint::_NotifyReader() +{ + gSocketModule->notify(socket, B_SELECT_READ, _AvailableData()); +} + + // #pragma mark - timer Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h 2007-04-05 20:45:10 UTC (rev 20591) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h 2007-04-05 22:42:45 UTC (rev 20592) @@ -66,8 +66,9 @@ bool outstandingAcknowledge); status_t _SendQueued(bool force = false); int _GetMSS(const struct sockaddr *) const; - ssize_t _AvailableBytesOrDisconnect() const; status_t _ShutdownEgress(bool closing); + ssize_t _AvailableData() const; + void _NotifyReader(); static void _TimeWaitTimer(net_timer *timer, void *data); static void _RetransmitTimer(net_timer *timer, void *data); Modified: haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp 2007-04-05 20:45:10 UTC (rev 20591) +++ haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp 2007-04-05 22:42:45 UTC (rev 20592) @@ -764,7 +764,7 @@ status_t UdpEndpoint::SendData(net_buffer *buffer, net_route *route) { - if (buffer->size > 0xffff) + if (buffer->size > (0xffff - sizeof(udp_header))) return EMSGSIZE; buffer->protocol = IPPROTO_UDP; From hugosantos at mail.berlios.de Fri Apr 6 01:26:47 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Fri, 6 Apr 2007 01:26:47 +0200 Subject: [Haiku-commits] r20593 - haiku/trunk/src/add-ons/kernel/network/protocols/tcp Message-ID: <200704052326.l35NQlce008306@sheep.berlios.de> Author: hugosantos Date: 2007-04-06 01:26:39 +0200 (Fri, 06 Apr 2007) New Revision: 20593 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20593&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp Log: The Open Group base specification mentions that EINTR should be returned if the recv() is interrupted before _any data_ is available. So we actually check if there is data, and if so, push it to the user. Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-05 22:42:45 UTC (rev 20592) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-05 23:26:39 UTC (rev 20593) @@ -519,9 +519,12 @@ locker.Lock(); if (status < B_OK) { - // TODO: If we are timing out, should we push the - // available data to the user? - if (status == B_TIMED_OUT && fReceiveQueue.Available() > 0) + // The Open Group base specification mentions that EINTR should be + // returned if the recv() is interrupted before _any data_ is + // available. So we actually check if there is data, and if so, + // push it to the user. + if ((status == B_TIMED_OUT || status == B_INTERRUPTED) + && fReceiveQueue.Available() > 0) break; return status; } From hugosantos at mail.berlios.de Fri Apr 6 04:02:36 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Fri, 6 Apr 2007 04:02:36 +0200 Subject: [Haiku-commits] r20595 - haiku/trunk/src/bin/strace Message-ID: <200704060202.l3622a3q019676@sheep.berlios.de> Author: hugosantos Date: 2007-04-06 04:02:29 +0200 (Fri, 06 Apr 2007) New Revision: 20595 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20595&view=rev Modified: haiku/trunk/src/bin/strace/NetworkTypes.cpp haiku/trunk/src/bin/strace/TypeHandler.h Log: added message_args decoding support to strace (used by net_stack's RECEIVE/SEND). Modified: haiku/trunk/src/bin/strace/NetworkTypes.cpp =================================================================== --- haiku/trunk/src/bin/strace/NetworkTypes.cpp 2007-04-06 02:02:18 UTC (rev 20594) +++ haiku/trunk/src/bin/strace/NetworkTypes.cpp 2007-04-06 02:02:29 UTC (rev 20595) @@ -359,6 +359,9 @@ static string get_iovec(Context &context, iovec *iov, int iovlen) { + if (iov == NULL && iovlen == 0) + return "(empty)"; + string r = "{"; r += context.FormatPointer(iov); r += ", " + context.FormatSigned(iovlen); @@ -366,6 +369,19 @@ } static string +format_pointer(Context &context, message_args *msg) +{ + string r; + + r += "header = " + format_pointer_value(context, msg->header); + r += ", flags = " + context.FormatFlags(msg->flags); + r += ", data = " + context.FormatPointer(msg->data); + r += ", length = " + context.FormatUnsigned(msg->length); + + return r; +} + +static string format_pointer(Context &context, msghdr *h) { string r; @@ -373,8 +389,10 @@ r = "name = " + format_pointer_value(context, h->msg_name); r += ", name_len = " + context.FormatUnsigned(h->msg_namelen); r += ", iov = " + get_iovec(context, h->msg_iov, h->msg_iovlen); - r += ", control = " + context.FormatPointer(h->msg_control); - r += ", control_len = " + context.FormatUnsigned(h->msg_controllen); + if (h->msg_control != NULL || h->msg_controllen != 0) { + r += ", control = " + context.FormatPointer(h->msg_control); + r += ", control_len = " + context.FormatUnsigned(h->msg_controllen); + } r += ", flags = " + context.FormatFlags(h->msg_flags); return r; @@ -461,9 +479,10 @@ } DEFINE_TYPE(fdset_ptr, fd_set *); +POINTER_TYPE(ifconf_ptr, ifconf); +POINTER_TYPE(ifreq_ptr, ifreq); +POINTER_TYPE(message_args_ptr, message_args); +POINTER_TYPE(msghdr_ptr, msghdr); POINTER_TYPE(sockaddr_args_ptr, sockaddr_args); POINTER_TYPE(sockopt_args_ptr, sockopt_args); POINTER_TYPE(socket_args_ptr, socket_args); -POINTER_TYPE(msghdr_ptr, msghdr); -POINTER_TYPE(ifreq_ptr, ifreq); -POINTER_TYPE(ifconf_ptr, ifconf); Modified: haiku/trunk/src/bin/strace/TypeHandler.h =================================================================== --- haiku/trunk/src/bin/strace/TypeHandler.h 2007-04-06 02:02:18 UTC (rev 20594) +++ haiku/trunk/src/bin/strace/TypeHandler.h 2007-04-06 02:02:29 UTC (rev 20595) @@ -100,16 +100,18 @@ struct fd_set; struct ifconf; struct ifreq; +struct message_args; struct sockaddr_args; struct socket_args; struct sockopt_args; DEFINE_FACTORY(fdset_ptr, fd_set *); +DEFINE_FACTORY(ifconf_ptr, ifconf *); +DEFINE_FACTORY(ifreq_ptr, ifreq *); +DEFINE_FACTORY(message_args_ptr, message_args *); DEFINE_FACTORY(sockaddr_args_ptr, sockaddr_args *); +DEFINE_FACTORY(socket_args_ptr, socket_args *); DEFINE_FACTORY(sockopt_args_ptr, sockopt_args *); -DEFINE_FACTORY(socket_args_ptr, socket_args *); -DEFINE_FACTORY(ifreq_ptr, ifreq *); -DEFINE_FACTORY(ifconf_ptr, ifconf *); DEFINE_FACTORY(int_ptr, int *); DEFINE_FACTORY(long_ptr, long *); From hugosantos at mail.berlios.de Fri Apr 6 04:02:31 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Fri, 6 Apr 2007 04:02:31 +0200 Subject: [Haiku-commits] r20594 - haiku/trunk/src/add-ons/kernel/network/protocols/tcp Message-ID: <200704060202.l3622VYa019664@sheep.berlios.de> Author: hugosantos Date: 2007-04-06 04:02:18 +0200 (Fri, 06 Apr 2007) New Revision: 20594 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20594&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp Log: check if receive timeout is infinite before doing the usual preparation for ABSOLUTE_TIMEOUT Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-05 23:26:39 UTC (rev 20593) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-06 02:02:18 UTC (rev 20594) @@ -506,7 +506,9 @@ if (flags & MSG_WAITALL) dataNeeded = numBytes; - bigtime_t timeout = system_time() + socket->receive.timeout; + bigtime_t timeout = socket->receive.timeout; + if (timeout != B_INFINITE_TIMEOUT) + timeout += system_time(); while (fReceiveQueue.PushedData() == 0 && fReceiveQueue.Available() < dataNeeded From bonefish at mail.berlios.de Fri Apr 6 04:37:12 2007 From: bonefish at mail.berlios.de (bonefish at BerliOS) Date: Fri, 6 Apr 2007 04:37:12 +0200 Subject: [Haiku-commits] r20596 - in haiku/trunk: . build/jam Message-ID: <200704060237.l362bCIP022008@sheep.berlios.de> Author: bonefish Date: 2007-04-06 04:37:12 +0200 (Fri, 06 Apr 2007) New Revision: 20596 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20596&view=rev Added: haiku/trunk/build/jam/MathRules Modified: haiku/trunk/Jamrules Log: Added rules for performing basic integer arithmetics (+, -, *). The rules operate manually on digit lists, so they are certainly not fast and shouldn't be used excessively, but at least it's possible to do calculations in Jam now, should the need arise. Modified: haiku/trunk/Jamrules =================================================================== --- haiku/trunk/Jamrules 2007-04-06 02:02:29 UTC (rev 20595) +++ haiku/trunk/Jamrules 2007-04-06 02:37:12 UTC (rev 20596) @@ -19,6 +19,7 @@ # At the end include BuildSetup that sets up global variables etc. The # optional user-defined UserBuildConfig is included thereafter. include [ FDirName $(HAIKU_BUILD_RULES_DIR) HelperRules ] ; +include [ FDirName $(HAIKU_BUILD_RULES_DIR) MathRules ] ; include [ FDirName $(HAIKU_BUILD_RULES_DIR) BeOSRules ] ; include [ FDirName $(HAIKU_BUILD_RULES_DIR) ConfigRules ] ; include [ FDirName $(HAIKU_BUILD_RULES_DIR) DocumentationRules ] ; Added: haiku/trunk/build/jam/MathRules =================================================================== --- haiku/trunk/build/jam/MathRules 2007-04-06 02:02:29 UTC (rev 20595) +++ haiku/trunk/build/jam/MathRules 2007-04-06 02:37:12 UTC (rev 20596) @@ -0,0 +1,605 @@ +# Rules providing basic arithmetic operations + +HAIKU_ZERO = + 0 ; +HAIKU_ONE = + 1 ; + +HAIKU_PAD_9 = 0 1 2 3 4 5 6 7 8 ; + +# a > b <==> $(HAIKU_DIGIT_GREATER_$(a)[1$(b)]) +HAIKU_DIGIT_GREATER_0 = $(HAIKU_PAD_9) ; +HAIKU_DIGIT_GREATER_1 = $(HAIKU_PAD_9) 1 ; +HAIKU_DIGIT_GREATER_2 = $(HAIKU_PAD_9) 1 1 ; +HAIKU_DIGIT_GREATER_3 = $(HAIKU_PAD_9) 1 1 1 ; +HAIKU_DIGIT_GREATER_4 = $(HAIKU_PAD_9) 1 1 1 1 ; +HAIKU_DIGIT_GREATER_5 = $(HAIKU_PAD_9) 1 1 1 1 1 ; +HAIKU_DIGIT_GREATER_6 = $(HAIKU_PAD_9) 1 1 1 1 1 1 ; +HAIKU_DIGIT_GREATER_7 = $(HAIKU_PAD_9) 1 1 1 1 1 1 1 ; +HAIKU_DIGIT_GREATER_8 = $(HAIKU_PAD_9) 1 1 1 1 1 1 1 1 ; +HAIKU_DIGIT_GREATER_9 = $(HAIKU_PAD_9) 1 1 1 1 1 1 1 1 1 ; + +# a + b == $(HAIKU_DIGIT_ADD_$(a)[1$(b)]) (carry ignored) +HAIKU_DIGIT_ADD_0 = $(HAIKU_PAD_9) 0 1 2 3 4 5 6 7 8 9 ; +HAIKU_DIGIT_ADD_1 = $(HAIKU_PAD_9) 1 2 3 4 5 6 7 8 9 0 ; +HAIKU_DIGIT_ADD_2 = $(HAIKU_PAD_9) 2 3 4 5 6 7 8 9 0 1 ; +HAIKU_DIGIT_ADD_3 = $(HAIKU_PAD_9) 3 4 5 6 7 8 9 0 1 2 ; +HAIKU_DIGIT_ADD_4 = $(HAIKU_PAD_9) 4 5 6 7 8 9 0 1 2 3 ; +HAIKU_DIGIT_ADD_5 = $(HAIKU_PAD_9) 5 6 7 8 9 0 1 2 3 4 ; +HAIKU_DIGIT_ADD_6 = $(HAIKU_PAD_9) 6 7 8 9 0 1 2 3 4 5 ; +HAIKU_DIGIT_ADD_7 = $(HAIKU_PAD_9) 7 8 9 0 1 2 3 4 5 6 ; +HAIKU_DIGIT_ADD_8 = $(HAIKU_PAD_9) 8 9 0 1 2 3 4 5 6 7 ; +HAIKU_DIGIT_ADD_9 = $(HAIKU_PAD_9) 9 0 1 2 3 4 5 6 7 8 ; + +# a - b == $(HAIKU_DIGIT_SUB_$(a)[1$(b)]) (carry ignored) +HAIKU_DIGIT_SUB_0 = $(HAIKU_PAD_9) 0 9 8 7 6 5 4 3 2 1 ; +HAIKU_DIGIT_SUB_1 = $(HAIKU_PAD_9) 1 0 9 8 7 6 5 4 3 2 ; +HAIKU_DIGIT_SUB_2 = $(HAIKU_PAD_9) 2 1 0 9 8 7 6 5 4 3 ; +HAIKU_DIGIT_SUB_3 = $(HAIKU_PAD_9) 3 2 1 0 9 8 7 6 5 4 ; +HAIKU_DIGIT_SUB_4 = $(HAIKU_PAD_9) 4 3 2 1 0 9 8 7 6 5 ; +HAIKU_DIGIT_SUB_5 = $(HAIKU_PAD_9) 5 4 3 2 1 0 9 8 7 6 ; +HAIKU_DIGIT_SUB_6 = $(HAIKU_PAD_9) 6 5 4 3 2 1 0 9 8 7 ; +HAIKU_DIGIT_SUB_7 = $(HAIKU_PAD_9) 7 6 5 4 3 2 1 0 9 8 ; +HAIKU_DIGIT_SUB_8 = $(HAIKU_PAD_9) 8 7 6 5 4 3 2 1 0 9 ; +HAIKU_DIGIT_SUB_9 = $(HAIKU_PAD_9) 9 8 7 6 5 4 3 2 1 0 ; + +# a * b == $(HAIKU_DIGIT_MULT_CARRY_$(a)[1$(b)]) $(HAIKU_DIGIT_MULT_$(a)[1$(b)]) +HAIKU_DIGIT_MULT_0 = $(HAIKU_PAD_9) 0 0 0 0 0 0 0 0 0 0 ; +HAIKU_DIGIT_MULT_1 = $(HAIKU_PAD_9) 0 1 2 3 4 5 6 7 8 9 ; +HAIKU_DIGIT_MULT_2 = $(HAIKU_PAD_9) 0 2 4 6 8 0 2 4 6 8 ; +HAIKU_DIGIT_MULT_3 = $(HAIKU_PAD_9) 0 3 6 9 2 5 8 1 4 7 ; +HAIKU_DIGIT_MULT_4 = $(HAIKU_PAD_9) 0 4 8 2 6 0 4 8 2 6 ; +HAIKU_DIGIT_MULT_5 = $(HAIKU_PAD_9) 0 5 0 5 0 5 0 5 0 5 ; +HAIKU_DIGIT_MULT_6 = $(HAIKU_PAD_9) 0 6 2 8 4 0 6 2 8 4 ; +HAIKU_DIGIT_MULT_7 = $(HAIKU_PAD_9) 0 7 4 1 8 5 2 9 6 3 ; +HAIKU_DIGIT_MULT_8 = $(HAIKU_PAD_9) 0 8 6 4 2 0 8 6 4 2 ; +HAIKU_DIGIT_MULT_9 = $(HAIKU_PAD_9) 0 9 8 7 6 5 4 3 2 1 ; + +HAIKU_DIGIT_MULT_CARRY_0 = $(HAIKU_PAD_9) 0 0 0 0 0 0 0 0 0 0 ; +HAIKU_DIGIT_MULT_CARRY_1 = $(HAIKU_PAD_9) 0 0 0 0 0 0 0 0 0 0 ; +HAIKU_DIGIT_MULT_CARRY_2 = $(HAIKU_PAD_9) 0 0 0 0 0 1 1 1 1 1 ; +HAIKU_DIGIT_MULT_CARRY_3 = $(HAIKU_PAD_9) 0 0 0 0 1 1 1 2 2 2 ; +HAIKU_DIGIT_MULT_CARRY_4 = $(HAIKU_PAD_9) 0 0 0 1 1 2 2 2 3 3 ; +HAIKU_DIGIT_MULT_CARRY_5 = $(HAIKU_PAD_9) 0 0 1 1 2 2 3 3 4 4 ; +HAIKU_DIGIT_MULT_CARRY_6 = $(HAIKU_PAD_9) 0 0 1 1 2 3 3 4 4 5 ; +HAIKU_DIGIT_MULT_CARRY_7 = $(HAIKU_PAD_9) 0 0 1 2 2 3 4 4 5 6 ; +HAIKU_DIGIT_MULT_CARRY_8 = $(HAIKU_PAD_9) 0 0 1 2 3 4 4 5 6 7 ; +HAIKU_DIGIT_MULT_CARRY_9 = $(HAIKU_PAD_9) 0 0 1 2 3 4 5 6 7 8 ; + + +# pragma mark - Number Operations + + +rule NormalizeNum number +{ + # NormalizeNum ; + + local sign ; + if $(number[1]) = "-" || $(number[1] = "+" { + sign = $(number[1]) ; + number = $(number[2-]) ; + } else { + sign = "+" ; + } + + # cut off leading zeros + local number = [ FReverse $(number) ] ; + while $(number[1]) = 0 { + number = $(number[2-]) ; + } + number = [ FReverse $(number) ] ; + + # zero is respresented as + 0 + if ! $(number) { + number = 0 ; + sign = "+" ; + } + + return $(sign) $(number) ; +} + +rule Num string : dontExit +{ + # Num [ : ] ; + + # split the string into three parts: sign, digits, and remainder + local temp = [ Match ([^0-9]*)([0-9]+)(.*) : $(string) ] ; + + # there must be digits, but there must not be a remainder + if ! $(temp[2]) || $(temp[3]) { + if $(dontExit) { + return ; + } + Exit "Not a number" ; + } + + # get the sign + local number ; + if ! $(temp[1]) { + number = "+" ; + } else if $(temp[1]) = "+" || $(temp[1]) = "-" { + number = $(temp[1]) ; + } else { + if $(dontExit) { + return ; + } + Exit "Not a number (sign)" ; + } + + # split the digits + temp = $(temp[2]) ; + while $(temp[1]) { + # split off the last digit + temp = [ Match (.*)([0-9]) : $(temp[1]) ] ; + number += $(temp[2]) ; + } + + # normalize + return [ NormalizeNum $(number) ] ; +} + +rule Num2String number +{ + # Num2String ; + + local sign = $(number[1]) ; + if $(sign) = "+" { + sign = "" ; + } + + number = [ FReverse $(number[2-]) ] ; + + return $(sign)$(number:J=) ; +} + +rule NumGreaterAbs a : b +{ + # NumGreaterAbs : ; + + # we compare from least to most significant digit + local cmp = 0 ; + while $(a) && $(b) { + # chop off the first digit + local da = $(a[1]:E=0) ; + local db = $(b[1]:E=0) ; + a = $(a[2-]) ; + b = $(b[2-]) ; + + if $(da) != $(db) { + if $(HAIKU_DIGIT_GREATER_$(da)[1$(db)]) { + cmp = 1 ; + } else { + cmp = -1 ; + } + } + } + + # a is greater, if b is not longer and a is either longer or equally long + # and greater according to the digits comparison + if ! $(b) && ( $(a) || $(cmp) = 1 ) { + return 1 ; + } + return ; +} + +rule AddNumAbs a : b +{ + # AddNum : ; + + local result ; + local carry ; + while $(a) || $(b) || $(carry) { + # chop off the first digit + local da = $(a[1]:E=0) ; + local db = $(b[1]:E=0) ; + a = $(a[2-]) ; + b = $(b[2-]) ; + + # add carry to the first digit + if $(carry) { + local daa = $(HAIKU_DIGIT_ADD_1[1$(da)]) ; + carry = $(HAIKU_DIGIT_GREATER_$(da)[1$(daa)]) ; + da = $(daa) ; + } + + # add digits + local dr = $(HAIKU_DIGIT_ADD_$(da)[1$(db)]) ; + if $(HAIKU_DIGIT_GREATER_$(da)[1$(dr)]) { + carry = 1 ; + } + + result += $(dr) ; + } + + return $(result) ; +} + +rule SubNumAbs a : b +{ + # SubNum : ; + + local result ; + local carry ; + while $(a) && ( $(b) || $(carry) ) { + # chop off the first digit + local da = $(a[1]:E=0) ; + local db = $(b[1]:E=0) ; + a = $(a[2-]) ; + b = $(b[2-]) ; + + # sub carry from the first digit + if $(carry) { + local daa = $(HAIKU_DIGIT_SUB_$(da)[11]) ; + carry = $(HAIKU_DIGIT_GREATER_$(daa)[1$(da)]) ; + da = $(daa) ; + } + + # sub digits + local dr = $(HAIKU_DIGIT_SUB_$(da)[1$(db)]) ; + if $(HAIKU_DIGIT_GREATER_$(dr)[1$(da)]) { + carry = 1 ; + } + + result += $(dr) ; + } + + if $(b) || $(carry) { + Exit "Error: SubNumAbs: Can't subtract greater from smaller number." ; + } + + return $(result) ; +} + +rule NegNum a +{ + # NegNum ; + + if $(a[1]) = "+" { + if $(a) = $(HAIKU_ZERO) { + return $(a) ; + } + return "-" $(a[2-]) ; + } else { + return "+" $(a[2-]) ; + } +} + +rule AddNum a : b +{ + # AddNum : ; + + local signa = $(a[1]) ; + local signb = $(b[1]) ; + a = $(a[2-]) ; + b = $(b[2-]) ; + + if $(signa) = $(signb) { + return $(signa) [ AddNumAbs $(a) : $(b) ] ; + } else { + local result ; + if [ NumGreaterAbs $(a) : $(b) ] { + result = $(signa) [ SubNumAbs $(a) : $(b) ] ; + } else { + result = $(signb) [ SubNumAbs $(b) : $(a) ] ; + } + return [ NormalizeNum $(result) ] ; + } +} + +rule SubNum a : b +{ + # SubNum : ; + return [ AddNum $(a) : [ NegNum $(b) ] ] ; +} + +rule MultNumAbsDigit a : digit +{ + # MultNumAbsDigit : ; + + local digitMultiples = $(HAIKU_DIGIT_MULT_$(digit)) ; + local digitCarries = $(HAIKU_DIGIT_MULT_CARRY_$(digit)) ; + + local result ; + local carry = 0 ; + while $(a) || $(carry) != 0 { + # chop off the first digit + local da = $(a[1]:E=0) ; + a = $(a[2-]) ; + + local dr = $(digitMultiples[1$(da)]) ; + + # add carry to the resulting digit + if $(carry) { + local dra = $(HAIKU_DIGIT_ADD_$(dr)[1$(carry)]) ; + carry = $(HAIKU_DIGIT_GREATER_$(dr)[1$(dra)]:E=0) ; + dr = $(dra) ; + } + + # new carry + carry = $(HAIKU_DIGIT_ADD_$(carry:E=0)[1$(digitCarries[1$(da)])]) ; + + result += $(dr) ; + } + + return $(result) ; +} + +rule MultNum a : b +{ + # MultNum : ; + + # If one of the factors is 0, we save us computation and normalization. + if $(a) = $(HAIKU_ZERO) || $(b) = $(HAIKU_ZERO) { + return $(HAIKU_ZERO) ; + } + + # get the sign for the result + local sign = "+" ; + if $(a[1]) != $(b[1]) { + sign = "-" ; + } + + a = $(a[2-]) ; + b = $(b[2-]) ; + + # multiply the individual digits of b with a and add up the result + local result = 0 ; + local prefix ; + while $(b) { + local db = $(b[1]) ; + b = $(b[2-]) ; + + local adb = $(prefix) [ MultNumAbsDigit $(a) : $(db) ] ; + result = [ AddNumAbs $(result) : $(adb) ] ; + + prefix += 0 ; + } + + return $(sign) $(result) ; +} + +rule NumGreater a : b +{ + local signa = $(a[1]) ; + local signb = $(b[1]) ; + a = $(a[2-]) ; + b = $(b[2-]) ; + + if $(signa) = $(signb) { + if $(signa) = "+" { + return [ NumGreaterAbs $(a) : $(b) ] ; + } else { + return [ NumGreaterAbs $(b) : $(a) ] ; + } + } else { + if $(signa) = "+" { + return 1 ; + } else { + return ; + } + } +} + + +# pragma mark - Number String Operations + + +rule Inc a +{ + # Inc ; + return [ Num2String [ AddNum [ Num $(a) ] : + 1 ] ] ; +} + +rule Dec a +{ + # Dec ; + return [ Num2String [ AddNum [ Num $(a) ] : - 1 ] ] ; +} + +rule Neg a +{ + # Neg ; + return [ Num2String [ NegNum [ Num $(a) ] ] ] ; +} + +rule Add a : b +{ + # Add : ; + return [ Num2String [ AddNum [ Num $(a) ] : [ Num $(b) ] ] ] ; +} + +rule Sub a : b +{ + # Sub : ; + return [ Num2String [ SubNum [ Num $(a) ] : [ Num $(b) ] ] ] ; +} + +rule Mult a : b +{ + # Mult : ; + return [ Num2String [ MultNum [ Num $(a) ] : [ Num $(b) ] ] ] ; +} + +rule Equal a : b +{ + # Equal : ; + if [ Num $(a) ] = [ Num $(b) ] { + return 1 ; + } + + return ; +} + +rule Less a : b +{ + # Less : ; + return [ NumGreater [ Num $(b) ] : [ Num $(a) ] ] ; +} + +rule Greater a : b +{ + # Greater : ; + return [ NumGreater [ Num $(a) ] : [ Num $(b) ] ] ; +} + +rule LessOrEqual a : b +{ + # LessOrEqual : ; + if [ NumGreater [ Num $(a) ] : [ Num $(b) ] ] { + return ; + } + return 1 ; +} + +rule GreaterOrEqual a : b +{ + # GreaterOrEqual : ; + if [ NumGreater [ Num $(b) ] : [ Num $(a) ] ] { + return ; + } + return 1 ; +} + + +# pragma mark - Expression Parser + + +rule ParseAtom expression +{ + # ParseAtom ; + + # expression: '(' expression ')' | number + + if $(expression[1]) = "(" { + local result = [ ParseExpression $(expression[2-]) ] ; + if $(result[2]) != ")" { + Exit "ParseAtom: Parse error: Expected \")\"." ; + } + return $(result[1]) $(result[3-]) ; + } else { + if ! $(expression) { + Exit "ParseAtom: Parse error: Unexpected end of expression." ; + } + + local num = [ Num $(expression[1]) : 1 ] ; + if ! $(num) { + Exit "ParseAtom: Parse error: Expected number instead of:" + $(expression[1]) ; + } + + return [ Num2String $(num) ] $(expression[2-]) ; + } +} + +rule ParseUnary expression +{ + # ParseUnary ; + + # expression: ('+'/'-')* atom + + if ! $(expression) { + Exit "ParseUnary: Parse error: Unexpected end of expression." ; + } + + # eat all unary "+" and "-" operations + local neg ; + while $(expression[1]) = "+" || $(expression[1]) = "-" { + if $(expression[1]) = "-" { + if $(neg) { + neg = ; + } else { + neg = 1 ; + } + } + + expression = $(expression[2-]) ; + } + + local result = [ ParseAtom $(expression) ] ; + + if $(neg) { + return [ Neg $(result[1]) ] $(result[2-]) ; + } + return $(result) ; +} + +rule ParseTerm expression +{ + # ParseTerm ; + + # expression: unary ('*' unary)* + + local result = [ ParseUnary $(expression) ] ; + local product = $(result[1]) ; + expression = $(result[2-]) ; + + while $(expression[1]) = "*" { + # get the operation + local operation ; + operation = Mult ; + + # parse the next operand + result = [ ParseUnary $(expression[2-]) ] ; + expression = $(result[2-]) ; + + # compute the product + product = [ $(operation) $(product) : $(result[1]) ] ; + } + + return $(product) $(expression) ; +} + +rule ParseExpression expression +{ + # ParseExpression ; + + # expression: term ('+'/'-' term)* + + local result = [ ParseTerm $(expression) ] ; + local sum = $(result[1]) ; + expression = $(result[2-]) ; + + while $(expression[1]) = "+" || $(expression[1]) = "-" { + # get the operation + local operation ; + if $(expression[1]) = "+" { + operation = Add ; + } else { + operation = Sub ; + } + + # parse the next operand + result = [ ParseTerm $(expression[2-]) ] ; + expression = $(result[2-]) ; + + # compute the sum + sum = [ $(operation) $(sum) : $(result[1]) ] ; + } + + return $(sum) $(expression) ; +} + + +rule Expr expression +{ + # Expr ; + + # tokenize the expression + local tokens ; + for string in $(expression) { + while $(string) { + local split = [ Match "[ \t]*(-|[()+*]|[0-9]*)(.*)" : $(string) ] ; + if ! $(split[1]) { + Exit "Expr: Syntax error: Invalid token: \"$(string)\"." ; + } + + tokens += $(split[1]) ; + string = $(split[2]) ; + } + } + + local result = [ ParseExpression $(tokens) ] ; + if $(result[2-]) { + Exit "Expr: Garbage at end of expression:" $(result[2-]) ; + } + + return $(result[1]) ; +} From bonefish at mail.berlios.de Fri Apr 6 04:39:38 2007 From: bonefish at mail.berlios.de (bonefish at BerliOS) Date: Fri, 6 Apr 2007 04:39:38 +0200 Subject: [Haiku-commits] r20597 - haiku/trunk/build/jam Message-ID: <200704060239.l362dcwH022215@sheep.berlios.de> Author: bonefish Date: 2007-04-06 04:39:37 +0200 (Fri, 06 Apr 2007) New Revision: 20597 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20597&view=rev Modified: haiku/trunk/build/jam/MiscRules Log: Added rules NextID, which returns an numerical ID incremented with each invocation, and NewUniqueTarget, which returns a unique target name. Modified: haiku/trunk/build/jam/MiscRules =================================================================== --- haiku/trunk/build/jam/MiscRules 2007-04-06 02:37:12 UTC (rev 20596) +++ haiku/trunk/build/jam/MiscRules 2007-04-06 02:39:37 UTC (rev 20597) @@ -29,7 +29,11 @@ SubInclude $(1) ; } } - + + +# pragma mark - MakeLocate variants + + rule MakeLocateCommonPlatform { MakeLocate $(1) : $(COMMON_PLATFORM_LOCATE_TARGET) ; @@ -76,6 +80,13 @@ } } + +# pragma mark - Deferred SubIncludes + + +# The variable used to collect the deferred SubIncludes. +HAIKU_DEFERRED_SUB_INCLUDES = ; + rule DeferredSubInclude params { # DeferredSubInclude ; @@ -125,5 +136,26 @@ } } -# The variable used to collect the deferred SubIncludes. -HAIKU_DEFERRED_SUB_INCLUDES = ; + +# pragma mark - Unique IDs/targets + + +# private to NextID; incremented with each NextID invocation +HAIKU_NEXT_ID = 0 ; + +rule NextID +{ + # NextID ; + + local result = $(HAIKU_NEXT_ID:J=) ; + HAIKU_NEXT_ID = [ AddNumAbs $(HAIKU_NEXT_ID) : 1 ] ; + return $(result) ; +} + +rule NewUniqueTarget basename +{ + # NewUniqueTarget [ basename ] ; + + local id = [ NextID ] ; + return $(basename[1]:E=_target:G=unique!target)_$(id) ; +} From bonefish at mail.berlios.de Fri Apr 6 05:14:58 2007 From: bonefish at mail.berlios.de (bonefish at BerliOS) Date: Fri, 6 Apr 2007 05:14:58 +0200 Subject: [Haiku-commits] r20598 - haiku/trunk/build/jam Message-ID: <200704060314.l363EwFK024212@sheep.berlios.de> Author: bonefish Date: 2007-04-06 05:14:58 +0200 (Fri, 06 Apr 2007) New Revision: 20598 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20598&view=rev Modified: haiku/trunk/build/jam/BuildSetup haiku/trunk/build/jam/MiscRules Log: New handy build system feature: It is now possible to pass a command line to jam that contains build targets and that will be executed by the build system after building the targets and replacing their occurrences in the command line by their paths. The keyword indicating such a command line is "run", targets are marked by a leading ":". E.g.: jam -q run ':xres' -l :libtracker.so This builds the xres tool for the host platform and libtracker.so for Haiku, and afterwards lists the resources libtracker.so contains. Note, that this feature requires using Haiku's jam version. The functionality is implemented by the new RunCommandLine rule, which can, of course, also be used in the UserBuildConfig. Modified: haiku/trunk/build/jam/BuildSetup =================================================================== --- haiku/trunk/build/jam/BuildSetup 2007-04-06 02:39:37 UTC (rev 20597) +++ haiku/trunk/build/jam/BuildSetup 2007-04-06 03:14:58 UTC (rev 20598) @@ -11,13 +11,22 @@ # directory paths and the like. -# If the target to be built is "all" (i.e. the default) and we're in the output -# directory, the root directory of the build system, or in "src/", we change the -# target to be built to "haiku-image". +# analyze an optionally replace jam's target parameters HAIKU_ORIGINAL_JAM_TARGETS = $(JAM_TARGETS) ; -if $(JAM_TARGETS) = all { - if ! $(INVOCATION_SUBDIR) || $(INVOCATION_SUBDIR) = src { - JAM_TARGETS = haiku-image ; +if $(JAM_TARGETS) { + # If the target to be built is "all" (i.e. the default) and we're in the + # output directory, the root directory of the build system, or in "src/", we + # change the target to be built to "haiku-image". + if $(JAM_TARGETS) = all { + if ! $(INVOCATION_SUBDIR) || $(INVOCATION_SUBDIR) = src { + JAM_TARGETS = haiku-image ; + } + + # The "run" target allows for running arbitrary command lines containing + # build system targets, which are built and replaced accordingly. + } else if $(JAM_TARGETS[1]) = run && $(JAM_TARGETS[2]) { + local run = [ RunCommandLine $(JAM_TARGETS[2-]) ] ; + JAM_TARGETS = $(run) ; } } Modified: haiku/trunk/build/jam/MiscRules =================================================================== --- haiku/trunk/build/jam/MiscRules 2007-04-06 02:39:37 UTC (rev 20597) +++ haiku/trunk/build/jam/MiscRules 2007-04-06 03:14:58 UTC (rev 20598) @@ -159,3 +159,61 @@ local id = [ NextID ] ; return $(basename[1]:E=_target:G=unique!target)_$(id) ; } + + +# pragma mark - RunCommandLine + + +rule RunCommandLine commandLine +{ + # RunCommandLine + # + # Creates a pseudo target that, when made by jam, causes the supplied shell + # command line to be executed. Elements of with the prefix ":" + # are replaced by the rule. After stripping the prefix such a string specifies + # a build system target and the finally executed command line will contain + # a path to the target instead. + # The pseudo target will depend on all targets thus identified. Each + # invocation of this rule creates a different pseudo target, which is + # returned to the caller. + + # collect the targets in the command line and replace them by $targetX* + # variables + local substitutedCommandLine ; + local targets ; + + local targetVarName = target ; + local i ; + for i in $(commandLine) { + # targets are marked by the ":" prefix + local target = [ Match :(.*) : $(i) ] ; + if $(target) { + targets += $(target) ; + targetVarName = $(targetVarName)X ; + i = "$"$(targetVarName) ; + } + + substitutedCommandLine += $(i) ; + } + + # define the "run" target + local run = [ NewUniqueTarget run ] ; + COMMAND_LINE on $(run) = $(substitutedCommandLine) ; + NotFile $(run) ; + Always $(run) ; + Depends $(run) : $(targets) ; + RunCommandLine1 $(run) : $(targets) ; + + return $(run) ; +} + +actions RunCommandLine1 { + target=target; + for t in $(2) ; do + target+=X + eval "${target}=${t}" + done + $(HOST_ADD_BUILD_COMPATIBILITY_LIB_DIR) + $(COMMAND_LINE) +} + From hugosantos at mail.berlios.de Fri Apr 6 08:23:35 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Fri, 6 Apr 2007 08:23:35 +0200 Subject: [Haiku-commits] r20599 - haiku/trunk/src/add-ons/kernel/network/devices/ethernet Message-ID: <200704060623.l366NZ7i013375@sheep.berlios.de> Author: hugosantos Date: 2007-04-06 08:23:27 +0200 (Fri, 06 Apr 2007) New Revision: 20599 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20599&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/devices/ethernet/ethernet.cpp Log: check if the device going down is the head of the check list and remove it. Modified: haiku/trunk/src/add-ons/kernel/network/devices/ethernet/ethernet.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/devices/ethernet/ethernet.cpp 2007-04-06 03:14:58 UTC (rev 20598) +++ haiku/trunk/src/add-ons/kernel/network/devices/ethernet/ethernet.cpp 2007-04-06 06:23:27 UTC (rev 20599) @@ -216,7 +216,8 @@ // if the device is still part of the list, remove it if (device->GetDoublyLinkedListLink()->next != NULL - || device->GetDoublyLinkedListLink()->previous != NULL) + || device->GetDoublyLinkedListLink()->previous != NULL + || device == sCheckList.Head()) sCheckList.Remove(device); close(device->fd); From hugosantos at mail.berlios.de Fri Apr 6 08:23:46 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Fri, 6 Apr 2007 08:23:46 +0200 Subject: [Haiku-commits] r20600 - haiku/trunk/src/add-ons/kernel/network/stack Message-ID: <200704060623.l366NkZ4013390@sheep.berlios.de> Author: hugosantos Date: 2007-04-06 08:23:35 +0200 (Fri, 06 Apr 2007) New Revision: 20600 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20600&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp haiku/trunk/src/add-ons/kernel/network/stack/domains.cpp haiku/trunk/src/add-ons/kernel/network/stack/domains.h haiku/trunk/src/add-ons/kernel/network/stack/interfaces.cpp haiku/trunk/src/add-ons/kernel/network/stack/interfaces.h haiku/trunk/src/add-ons/kernel/network/stack/routes.cpp haiku/trunk/src/add-ons/kernel/network/stack/routes.h Log: started some work to properly handle device_removed() and setting interfaces down in general. - remove all routes that use interfaces going down. - when a device is going down, remove associated domain interfaces. - interfaces weren't getting a properly referenced device interface, fixed. - down call down_device_interface when deleting a interface, instead set it down and let the upcounts do its job. Modified: haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp 2007-04-06 06:23:27 UTC (rev 20599) +++ haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp 2007-04-06 06:23:35 UTC (rev 20600) @@ -332,10 +332,7 @@ if (((uint32)request.ifr_flags & IFF_UP) != (interface->flags & IFF_UP)) { if ((interface->flags & IFF_UP) != 0) { - // bring the interface down - interface->flags &= ~(IFF_UP | IFF_LINK); - interface->first_info->interface_down( - interface->first_protocol); + interface_set_down(interface); } else { // bring it up status = interface->first_info->interface_up( @@ -564,6 +561,8 @@ deviceInterface->up_count--; + domain_interface_went_down(protocol->interface); + if (deviceInterface->up_count > 0) return; Modified: haiku/trunk/src/add-ons/kernel/network/stack/domains.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/domains.cpp 2007-04-06 06:23:27 UTC (rev 20599) +++ haiku/trunk/src/add-ons/kernel/network/stack/domains.cpp 2007-04-06 06:23:35 UTC (rev 20600) @@ -225,6 +225,49 @@ } +void +domain_interface_went_down(net_interface *interface) +{ + // the domain should be locked here. always check + // all callers to be sure. We get here via + // interface_set_down(). + + dprintf("domain_interface_went_down(%i, %s)\n", + interface->domain->family, interface->name); + + // domain might have been locked by: + // - domain_removed_device_interface() <--- here + // remove_interface_from_domain() + // delete_interface() + // interface_set_down() + // - datalink_control() <--- here + // interface_set_down() + invalidate_routes(interface->domain, interface); +} + + +void +domain_removed_device_interface(net_device_interface *interface) +{ + BenaphoreLocker locker(sDomainLock); + + net_domain_private *domain = NULL; + while (true) { + domain = (net_domain_private *)list_get_next_item(&sDomains, domain); + if (domain == NULL) + break; + + BenaphoreLocker locker(domain->lock); + + net_interface_private *priv = find_interface(domain, interface->name); + if (priv == NULL) + continue; + + remove_interface_from_domain(priv); + } +} + + status_t register_domain(int family, const char *name, struct net_protocol_module_info *module, Modified: haiku/trunk/src/add-ons/kernel/network/stack/domains.h =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/domains.h 2007-04-06 06:23:27 UTC (rev 20599) +++ haiku/trunk/src/add-ons/kernel/network/stack/domains.h 2007-04-06 06:23:35 UTC (rev 20600) @@ -16,6 +16,9 @@ #include +struct net_device_interface; + + struct net_domain_private : net_domain { struct list_link link; @@ -34,6 +37,8 @@ status_t add_interface_to_domain(net_domain *domain, struct ifreq& request); status_t remove_interface_from_domain(net_interface *interface); void domain_interfaces_link_changed(net_device *device); +void domain_interface_went_down(net_interface *); +void domain_removed_device_interface(net_device_interface *); net_domain *get_domain(int family); status_t register_domain(int family, const char *name, Modified: haiku/trunk/src/add-ons/kernel/network/stack/interfaces.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/interfaces.cpp 2007-04-06 06:23:27 UTC (rev 20599) +++ haiku/trunk/src/add-ons/kernel/network/stack/interfaces.cpp 2007-04-06 06:23:35 UTC (rev 20600) @@ -63,6 +63,16 @@ } +net_device_interface * +grab_device_interface(net_device_interface *interface) +{ + if (interface == NULL || atomic_add(&interface->ref_count, 1) == 0) + return NULL; + + return interface; +} + + // #pragma mark - interfaces @@ -135,7 +145,7 @@ interface->type = 0; interface->mtu = deviceInterface->device->mtu; interface->metric = 0; - interface->device_interface = deviceInterface; + interface->device_interface = grab_device_interface(deviceInterface); status_t status = get_domain_datalink_protocols(interface); if (status < B_OK) { @@ -154,14 +164,33 @@ void +interface_set_down(net_interface *interface) +{ + if ((interface->flags & IFF_UP) == 0) + return; + + // TODO: IFF_LINK should belong in device only + interface->flags &= ~(IFF_UP | IFF_LINK); + interface->first_info->interface_down(interface->first_protocol); +} + + +void delete_interface(net_interface_private *interface) { - if ((interface->flags & IFF_UP) != 0) { - // the interface is still up - we need to change that before deleting it - interface->flags &= ~IFF_UP; - down_device_interface(interface->device_interface); - } + // deleting an interface is fairly complex as we need + // to clear all references to it throughout the stack + // this will possibly call (if IFF_UP): + // interface_protocol_down() + // domain_interface_went_down() + // invalidate_routes() + // remove_route() + // update_route_infos() + // get_route_internal() + // down_device_interface() -- if upcount reaches 0 + interface_set_down(interface); + put_device_interface(interface->device_interface); free(interface->address); @@ -388,9 +417,15 @@ { net_device *device = interface->device; + dprintf("down_device_interface(%s)\n", interface->name); + device->flags &= ~IFF_UP; interface->module->down(device); + // TODO: there is a race condition between the previous + // ->down and device->module->receive_data which + // locks us here waiting for the reader_thread + // make sure the reader thread is gone before shutting down the interface status_t status; wait_for_thread(interface->reader_thread, &status); @@ -600,7 +635,25 @@ device_removed(net_device *device) { BenaphoreLocker locker(sInterfaceLock); - // TODO: all what this function should do is to clear the IFF_UP flag of the interfaces. + + net_device_interface *interface = find_device_interface(device->name); + if (interface == NULL) + return ENODEV; + + // Propagate the loss of the device throughout the stack. + // This is very complex, refer to delete_interface() for + // further details. + + // this will possibly call: + // remove_interface_from_domain() [domain gets locked] + // delete_interface() + // ... [see delete_interface()] + domain_removed_device_interface(interface); + + // TODO: make sure all readers are gone + // make sure all watchers are gone + // remove device interface + return B_OK; } Modified: haiku/trunk/src/add-ons/kernel/network/stack/interfaces.h =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/interfaces.h 2007-04-06 06:23:27 UTC (rev 20599) +++ haiku/trunk/src/add-ons/kernel/network/stack/interfaces.h 2007-04-06 06:23:35 UTC (rev 20600) @@ -69,6 +69,7 @@ const char *baseName, net_device_interface *deviceInterface, struct net_interface_private **_interface); void delete_interface(net_interface_private *interface); +void interface_set_down(net_interface *); // device interfaces void get_device_interface_address(net_device_interface *interface, Modified: haiku/trunk/src/add-ons/kernel/network/stack/routes.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/routes.cpp 2007-04-06 06:23:27 UTC (rev 20599) +++ haiku/trunk/src/add-ons/kernel/network/stack/routes.cpp 2007-04-06 06:23:35 UTC (rev 20600) @@ -493,6 +493,28 @@ } +void +invalidate_routes(net_domain *_domain, net_interface *interface) +{ + // this function is called with the domain locked + // (see domain_interface_went_down) + net_domain_private *domain = (net_domain_private *)_domain; + + dprintf("invalidate_routes(%i, %s)\n", domain->family, interface->name); + + RouteList::Iterator iterator = domain->routes.GetIterator(); + while (iterator.HasNext()) { + net_route *route = iterator.Next(); + + // TODO handle refcounting, if the route needs to linger + // for some reason we should set interface or + // something of the sorts that invalidates it's reference + if (route->interface == interface) + remove_route(domain, route); + } +} + + struct net_route * get_route(struct net_domain *_domain, const struct sockaddr *address) { Modified: haiku/trunk/src/add-ons/kernel/network/stack/routes.h =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/routes.h 2007-04-06 06:23:27 UTC (rev 20599) +++ haiku/trunk/src/add-ons/kernel/network/stack/routes.h 2007-04-06 06:23:35 UTC (rev 20600) @@ -39,6 +39,7 @@ const struct net_route *route); status_t get_route_information(struct net_domain *domain, void *buffer, size_t length); +void invalidate_routes(net_domain *, net_interface *); struct net_route *get_route(struct net_domain *domain, const struct sockaddr *address); void put_route(struct net_domain *domain, struct net_route *route); From hugosantos at mail.berlios.de Fri Apr 6 11:48:15 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Fri, 6 Apr 2007 11:48:15 +0200 Subject: [Haiku-commits] r20601 - in haiku/trunk/src/add-ons/kernel/network: devices/ethernet stack Message-ID: <200704060948.l369mFMs028437@sheep.berlios.de> Author: hugosantos Date: 2007-04-06 11:48:02 +0200 (Fri, 06 Apr 2007) New Revision: 20601 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20601&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/devices/ethernet/ethernet.cpp haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp haiku/trunk/src/add-ons/kernel/network/stack/domains.cpp haiku/trunk/src/add-ons/kernel/network/stack/interfaces.cpp Log: a bit more work towards proper locking including a fix to a refcount bug - fixed a issue in add_interface_to_domain where the device interface's refcount was always incremented since that function was getting the device interface handle and not returning it unconditionlly - if the ethernet device goes down, and the fd is close()ed, return B_FILE_ERROR instead of calling into the driver again Modified: haiku/trunk/src/add-ons/kernel/network/devices/ethernet/ethernet.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/devices/ethernet/ethernet.cpp 2007-04-06 06:23:35 UTC (rev 20600) +++ haiku/trunk/src/add-ons/kernel/network/devices/ethernet/ethernet.cpp 2007-04-06 09:48:02 UTC (rev 20601) @@ -221,6 +221,7 @@ sCheckList.Remove(device); close(device->fd); + device->fd = -1; } @@ -290,6 +291,9 @@ { ethernet_device *device = (ethernet_device *)_device; + if (device->fd == -1) + return B_FILE_ERROR; + // TODO: better header space net_buffer *buffer = gBufferModule->create(256); if (buffer == NULL) Modified: haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp 2007-04-06 06:23:35 UTC (rev 20600) +++ haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp 2007-04-06 09:48:02 UTC (rev 20601) @@ -44,14 +44,12 @@ net_device_interface *interface = (net_device_interface *)_interface; net_device *device = interface->device; status_t status = B_OK; - int32 tries = 0; while ((device->flags & IFF_UP) != 0) { net_buffer *buffer; status = device->module->receive_data(device, &buffer); if (status == B_OK) { //dprintf("received buffer of %ld bytes length\n", buffer->size); - tries = 0; // feed device monitors // TODO: locking! @@ -88,18 +86,24 @@ } gNetBufferModule.free(buffer); - } - - if (status < B_OK) { - // this is a near real-time thread - don't render the system unusable - // in case of a device going down + } else { + // In case of error, give the other threads some + // time to run since this is a near real time thread. + // + // TODO: can this value be lower? 1000 works fine in + // my system. 10ms seems a bit too much and adds + // as latency. snooze(10000); - - if (++tries > 20) { - // TODO: bring down the interface! - break; - } } + + // if the interface went down IFF_UP was removed + // and the receive_data() above should have been + // interrupted. One check should be enough, specially + // considering the snooze above. + // + // TODO: make sure that when receive_data() returns + // after closing the new device->flags are + // already visible in all processors. } return status; @@ -254,19 +258,13 @@ if (user_memcpy(&request, value, sizeof(struct ifreq)) < B_OK) return B_BAD_ADDRESS; - benaphore_lock(&domain->lock); - status_t status; + BenaphoreLocker _(domain->lock); net_interface *interface = find_interface(domain, request.ifr_name); - if (interface != NULL) - status = remove_interface_from_domain(interface); - else - status = ENODEV; - - benaphore_unlock(&domain->lock); - - return status; + if (interface == NULL) + return ENODEV; + return remove_interface_from_domain(interface); } case SIOCGIFCOUNT: @@ -321,7 +319,7 @@ if (user_memcpy(&request, value, sizeof(struct ifreq)) < B_OK) return B_BAD_ADDRESS; - benaphore_lock(&domain->lock); + BenaphoreLocker _(domain->lock); status_t status = B_OK; net_interface *interface = find_interface(domain, @@ -355,7 +353,6 @@ } else status = B_BAD_VALUE; - benaphore_unlock(&domain->lock); return status; } } Modified: haiku/trunk/src/add-ons/kernel/network/stack/domains.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/domains.cpp 2007-04-06 06:23:35 UTC (rev 20600) +++ haiku/trunk/src/add-ons/kernel/network/stack/domains.cpp 2007-04-06 09:48:02 UTC (rev 20601) @@ -154,27 +154,30 @@ const char *deviceName = request.ifr_parameter.device[0] ? request.ifr_parameter.device : request.ifr_name; + const char *baseName = request.ifr_parameter.base_name[0] + ? request.ifr_parameter.base_name : request.ifr_name; + net_device_interface *deviceInterface = get_device_interface(deviceName); if (deviceInterface == NULL) return ENODEV; BenaphoreLocker locker(domain->lock); + net_interface_private *interface = NULL; + status_t status; + if (find_interface(domain, request.ifr_name) != NULL) - return B_NAME_IN_USE; + status = B_NAME_IN_USE; + else + status = create_interface(domain, request.ifr_name, + baseName, deviceInterface, &interface); - net_interface_private *interface; - status_t status = create_interface(domain, - request.ifr_name, request.ifr_parameter.base_name[0] - ? request.ifr_parameter.base_name : request.ifr_name, - deviceInterface, &interface); - if (status < B_OK) { - put_device_interface(deviceInterface); - return status; - } + put_device_interface(deviceInterface); - list_add_item(&domain->interfaces, interface); - return B_OK; + if (status == B_OK) + list_add_item(&domain->interfaces, interface); + + return status; } Modified: haiku/trunk/src/add-ons/kernel/network/stack/interfaces.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/interfaces.cpp 2007-04-06 06:23:35 UTC (rev 20600) +++ haiku/trunk/src/add-ons/kernel/network/stack/interfaces.cpp 2007-04-06 09:48:02 UTC (rev 20601) @@ -652,7 +652,6 @@ // TODO: make sure all readers are gone // make sure all watchers are gone - // remove device interface return B_OK; } From axeld at pinc-software.de Fri Apr 6 12:24:29 2007 From: axeld at pinc-software.de (Axel =?iso-8859-15?q?D=F6rfler?=) Date: Fri, 06 Apr 2007 12:24:29 +0200 CEST Subject: [Haiku-commits] =?iso-8859-15?q?r20600_-_haiku/trunk/src/add-ons/?= =?iso-8859-15?q?kernel/network/stack?= In-Reply-To: <200704060623.l366NkZ4013390@sheep.berlios.de> Message-ID: <5579220973-BeMail@zon> hugosantos at mail.berlios.de wrote: > - remove all routes that use interfaces going down. > - when a device is going down, remove associated domain interfaces. Is that really what we want? At least I thought all there would be to do is to clear the IFF_UP flag in that case. > +void domain_interface_went_down(net_interface *); > +void domain_removed_device_interface(net_device_interface *); And another thing: please always name parameters even in the prototypes. Bye, Axel. From hugosantos at gmail.com Fri Apr 6 17:41:59 2007 From: hugosantos at gmail.com (Hugo Santos) Date: Fri, 6 Apr 2007 16:41:59 +0100 Subject: [Haiku-commits] r20600 - haiku/trunk/src/add-ons/kernel/network/stack In-Reply-To: <5579220973-BeMail@zon> References: <200704060623.l366NkZ4013390@sheep.berlios.de> <5579220973-BeMail@zon> Message-ID: <9c46321e0704060841i40f31f36jf5c651e065bd9636@mail.gmail.com> Hey Axel, On 4/6/07, Axel D?rfler wrote: > hugosantos at mail.berlios.de wrote: > > - remove all routes that use interfaces going down. > > - when a device is going down, remove associated domain interfaces. > > Is that really what we want? At least I thought all there would be to > do is to clear the IFF_UP flag in that case. The message is not very clear, what i mean as the device (not interface) going down is that it is being removed. In that case we need to remove the interfaces as we dont know if the device will ever come back, and even if it does it might not have the same name. Regarding the removal of routes when an interface goes down, it might have been a bit of an oversight, i'll review that. The route selection mechanism can instead be augmented to not pick interfaces without IFF_UP. My only concern right now is that when an interface goes down you lose a sense of the link from the domain perspective, and when you get back up you have no idea if you are in the same link or not, so the routes might not make sense -- we should run DHCP again, etc. In IPv6 for instance, the stateless auto-configured routes have associated timeouts (which might be something like a minute), that make no sense to die some time in the future instead of when the interface goes down. In fact, when you put an interface down you are saying to cease the protocol activity with that interface. Keeping old information around is just a convenience. I'm still thinking a bit about the locking for device_interface. I think i'll add a RX lock (a benaphore since its a single reader multiple writers), but currently in my tree there is a race between the RX lock and the domain lock, i'm still reviewing it. > And another thing: please always name parameters even in the > prototypes. Ok then. Hugo From revol at free.fr Fri Apr 6 17:57:01 2007 From: revol at free.fr (=?windows-1252?q?Fran=E7ois?= Revol) Date: Fri, 06 Apr 2007 17:57:01 +0200 CEST Subject: [Haiku-commits] r20590 - in haiku/trunk/src/add-ons/kernel/network/protocols: ipv4 udp In-Reply-To: <1595641941-BeMail@laptop> Message-ID: <729471565-BeMail@laptop> > > Hi Hugo, > > > > thanks for cleaning up the UDP-stuff. > > > > Hmm, looks like it's time to test NFS again :)) > (it used to mount succesfully but them loose a reply and keep asking > for retransmit or something) Indeed it now works nice: http://revolf.free.fr/beos/shots/shot_haiku_nfs_002_working.png No more hangup after 20 seconds, playing the mp3 file did work :) Just left some minor issues with paths (probably non working get_vnode_name). Congrats on UDP :) Fran?ois. From superstippi at gmx.de Fri Apr 6 22:17:47 2007 From: superstippi at gmx.de (Stephan Assmus) Date: Fri, 06 Apr 2007 22:17:47 +0200 Subject: [Haiku-commits] r20590 - in haiku/trunk/src/add-ons/kernel/network/protocols: ipv4 udp In-Reply-To: <729471565-BeMail@laptop> References: <729471565-BeMail@laptop> Message-ID: <20070406221747.1240.2@stippis.mshome.net> On 2007-04-06 at 17:57:01 [+0200], Fran?ois Revol wrote: > Indeed it now works nice: > http://revolf.free.fr/beos/shots/shot_haiku_nfs_002_working.png > > No more hangup after 20 seconds, playing the mp3 file did work :) > > Just left some minor issues with paths (probably non working > get_vnode_name). > > Congrats on UDP :) Pretty neat! :-) Hugo rocks! Best regards, -Stephan From bonefish at mail.berlios.de Fri Apr 6 23:13:36 2007 From: bonefish at mail.berlios.de (bonefish at BerliOS) Date: Fri, 6 Apr 2007 23:13:36 +0200 Subject: [Haiku-commits] r20602 - in haiku/trunk/build: jam scripts Message-ID: <200704062113.l36LDaXb013029@sheep.berlios.de> Author: bonefish Date: 2007-04-06 23:13:35 +0200 (Fri, 06 Apr 2007) New Revision: 20602 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20602&view=rev Modified: haiku/trunk/build/jam/BuildSetup haiku/trunk/build/jam/HaikuImage haiku/trunk/build/jam/ImageRules haiku/trunk/build/jam/UserBuildConfig.sample haiku/trunk/build/scripts/build_haiku_image Log: New build system feature to shorten the turn-around times when working with image files. E.g. jam -q update-image libbe.so kernel_x86 will only build libbe.so and the kernel (if necessary) and copy them onto the already existing Haiku image. The MIME DB will not be reinstalled, and only those source directories will be copied for which the AddSourceDirectoryToHaikuImage rule is given a second argument (e.g. "1"). The image will otherwise remain unchanged. The "update-vmware-image" and "update-install" work similarly for the VMWare image and the directory installation respectively. Note that, due to the way the VMWare image is created (prepending a header to the standard image), the file itself is fully rebuilt, i.e. changes made during the emulation will be lost after updating the VMWare image. The feature requires Haiku's jam. With other jam versions a similar effect can be reached by accordingly setting the HAIKU_IMAGE_UPDATE_ONLY and HAIKU_INCLUDE_IN_IMAGE in the UserBuildConfig file. Modified: haiku/trunk/build/jam/BuildSetup =================================================================== --- haiku/trunk/build/jam/BuildSetup 2007-04-06 09:48:02 UTC (rev 20601) +++ haiku/trunk/build/jam/BuildSetup 2007-04-06 21:13:35 UTC (rev 20602) @@ -27,6 +27,22 @@ } else if $(JAM_TARGETS[1]) = run && $(JAM_TARGETS[2]) { local run = [ RunCommandLine $(JAM_TARGETS[2-]) ] ; JAM_TARGETS = $(run) ; + + # "update-image", "update-vmware-image", and "update-install" targets allow + # for updating only specific targets in the image/installation dir. + } else if $(JAM_TARGETS[1]) = update-image + || $(JAM_TARGETS[1]) = update-vmware-image + || $(JAM_TARGETS[1]) = update-install { + HAIKU_IMAGE_UPDATE_ONLY = 1 ; + HAIKU_INCLUDE_IN_IMAGE on $(JAM_TARGETS[2-]) = 1 ; + + if $(JAM_TARGETS[1]) = update-image { + JAM_TARGETS = haiku-image ; + } else if $(JAM_TARGETS[1]) = update-vmware-image { + JAM_TARGETS = haiku-vmware-image ; + } else { + JAM_TARGETS = install-haiku ; + } } } Modified: haiku/trunk/build/jam/HaikuImage =================================================================== --- haiku/trunk/build/jam/HaikuImage 2007-04-06 09:48:02 UTC (rev 20601) +++ haiku/trunk/build/jam/HaikuImage 2007-04-06 21:13:35 UTC (rev 20602) @@ -348,6 +348,7 @@ AddVariableToScript $(script) : imageSize : $(HAIKU_IMAGE_SIZE) ; AddVariableToScript $(script) : addBuildCompatibilityLibDir : $(HOST_ADD_BUILD_COMPATIBILITY_LIB_DIR) ; +AddVariableToScript $(script) : updateOnly : $(HAIKU_IMAGE_UPDATE_ONLY) ; AddTargetVariableToScript $(script) : bfs_shell : bfsShell ; AddTargetVariableToScript $(script) : fs_shell_command : fsShellCommand ; AddTargetVariableToScript $(script) : copyattr ; Modified: haiku/trunk/build/jam/ImageRules =================================================================== --- haiku/trunk/build/jam/ImageRules 2007-04-06 09:48:02 UTC (rev 20601) +++ haiku/trunk/build/jam/ImageRules 2007-04-06 21:13:35 UTC (rev 20602) @@ -95,10 +95,10 @@ } -rule AddDirectoryToHaikuImage +rule AddDirectoryToHaikuImage directoryTokens { - # AddDirectoryToHaikuImage - local directoryTokens = $(1) ; + # AddDirectoryToHaikuImage + local directory = [ FDirName $(directoryTokens) ] ; directory = $(directory:G=HaikuImage) ; @@ -120,6 +120,20 @@ return $(directory) ; } +rule FilterImageUpdateTargets targets +{ + # FilterImageUpdateTargets targets + + local filteredTargets ; + local target ; + for target in $(targets) { + if [ on $(target) return $(HAIKU_INCLUDE_IN_IMAGE) ] { + filteredTargets += $(target) ; + } + } + return $(filteredTargets) ; +} + rule AddFilesToHaikuImage { # AddFilesToHaikuImage : [ : dest name ] @@ -128,6 +142,12 @@ local targets = $(2) ; local destName = $(3) ; + # If the image shall only be updated, we filter out all targets not marked + # accordingly. + if $(HAIKU_IMAGE_UPDATE_ONLY) { + targets = [ FilterImageUpdateTargets $(targets) ] ; + } + # We create a unique dummy target per target to install. local target ; for target in $(targets) { @@ -146,14 +166,18 @@ } } -rule AddSymlinkToHaikuImage +rule AddSymlinkToHaikuImage directoryTokens : linkTarget : linkName { # AddSymlinkToHaikuImage : [ : ] ; # - local directory = [ AddDirectoryToHaikuImage $(1) ] ; - local linkTarget = $(2) ; - local linkName = $(3) ; + # If the image shall only be updated, we don't add any symlinks. + if $(HAIKU_IMAGE_UPDATE_ONLY) { + return ; + } + + local directory = [ AddDirectoryToHaikuImage $(directoryTokens) ] ; + if ! $(linkName) { local path = [ FReverse [ FSplitPath $(linkTarget) ] ] ; linkName = $(path[1]) ; @@ -164,11 +188,15 @@ SYMLINKS_TO_INSTALL on $(directory) += $(link) ; } -rule AddSourceDirectoryToHaikuImage dirTokens +rule AddSourceDirectoryToHaikuImage dirTokens : alwaysUpdate { - # AddSourceDirectoryToHaikuImage ; + # AddSourceDirectoryToHaikuImage : ; - HAIKU_INSTALL_SOURCE_DIRS += [ FDirName $(HAIKU_TOP) $(dirTokens) ] ; + # If the image shall only be updated, we update sources only, if explicitely + # requested. + if ! $(HAIKU_IMAGE_UPDATE_ONLY) || $(alwaysUpdate) { + HAIKU_INSTALL_SOURCE_DIRS += [ FDirName $(HAIKU_TOP) $(dirTokens) ] ; + } } rule AddDriversToHaikuImage @@ -182,6 +210,11 @@ AddFilesToHaikuImage beos system add-ons kernel drivers bin : $(targets) ; + # If the image shall only be updated, we don't add any symlinks. + if $(HAIKU_IMAGE_UPDATE_ONLY) { + return ; + } + # get the relative symlink path prefix local linkPrefix = ; for i in $(relativeDirectoryTokens) { @@ -204,7 +237,8 @@ local relativeDirectoryTokens = $(1) ; local target = $(2) ; local links = $(3) ; - local directoryTokens = beos system add-ons kernel registration $(relativeDirectoryTokens) ; + local directoryTokens = beos system add-ons kernel registration + $(relativeDirectoryTokens) ; # get the relative symlink path prefix local linkPrefix = ; @@ -214,15 +248,20 @@ linkPrefix += .. drivers bin ; # add the symlink - AddSymlinkToHaikuImage $(directoryTokens) : [ FDirName $(linkPrefix) $(target:BS) ] : $(links) ; + AddSymlinkToHaikuImage $(directoryTokens) + : [ FDirName $(linkPrefix) $(target:BS) ] : $(links) ; } -rule AddBootModuleSymlinks +rule AddBootModuleSymlinks targets { # AddBootModuleSymlinks ; # - local targets = $(1) ; + # If the image shall only be updated, we don't add any symlinks. + if $(HAIKU_IMAGE_UPDATE_ONLY) { + return ; + } + # add the symlinks local target ; for target in $(targets) { @@ -267,7 +306,10 @@ } Depends $(scriptBody) : $(dirsToCreate) ; - CreateHaikuImageMakeDirectoriesScript1 $(scriptBody) : $(dirsToCreate) ; + # If the image shall only be updated, we don't create directories. + if $(dirsToCreate) && ! $(HAIKU_IMAGE_UPDATE_ONLY) { + CreateHaikuImageMakeDirectoriesScript1 $(scriptBody) : $(dirsToCreate) ; + } } actions piecemeal CreateHaikuImageMakeDirectoriesScript1 Modified: haiku/trunk/build/jam/UserBuildConfig.sample =================================================================== --- haiku/trunk/build/jam/UserBuildConfig.sample 2007-04-06 09:48:02 UTC (rev 20601) +++ haiku/trunk/build/jam/UserBuildConfig.sample 2007-04-06 21:13:35 UTC (rev 20602) @@ -35,6 +35,17 @@ # Install Haiku in directory /Haiku. HAIKU_INSTALL_DIR = /Haiku ; +# Affects the haiku-image, haiku-vmware-image, and install-haiku targets. Only +# targets on which the HAIKU_INCLUDE_IN_IMAGE variable has been set will be +# updated in the image file/installation directory. +# The update-image, update-vmware-image, and update-install targets always set +# this variable, so one likely doesn't ever need to set it manually. +HAIKU_IMAGE_UPDATE_ONLY = 1 ; + +# libbe.so and the kernel will be updated on image updates. Note that this +# doesn't work for pseudo targets like "kernel". +HAIKU_INCLUDE_IN_IMAGE on libbe.so kernel_x86 = 1 ; + # Add "crashing_app" to the beos/bin directory of the Haiku image/installation. # Note, that this also makes the image depend on the target, i.e. it is # automatically updated when the image is built. @@ -43,9 +54,13 @@ # Make a symlink to home/config/bin/crash. AddSymlinkToHaikuImage home config bin : /beos/bin/crashing_app : crash ; -# Adds the source directory src/kits/storage (recursively) to the image -# (as /boot/home/HaikuSources/src/kits/storage). -AddSourceDirectoryToHaikuImage src kits storage ; +# Adds the source directories src/kits/storage and src/tests/servers/debug +# (recursively) to the image (as /boot/home/HaikuSources/src/kits/storage +# and /boot/home/HaikuSources/src/tests/servers/debug respectively). +# Note that the second directory will also be copied, if the image will only +# be updated; the first one won't in that case. +AddSourceDirectoryToHaikuImage src/kits/storage ; +AddSourceDirectoryToHaikuImage src/tests/servers/debug : 1 ; # Specify scripts that shall be run when populating the image/installation # directory. The "early" script is run before anything has been copied onto Modified: haiku/trunk/build/scripts/build_haiku_image =================================================================== --- haiku/trunk/build/scripts/build_haiku_image 2007-04-06 09:48:02 UTC (rev 20601) +++ haiku/trunk/build/scripts/build_haiku_image 2007-04-06 21:13:35 UTC (rev 20602) @@ -1,6 +1,6 @@ #!/bin/sh -# The first argument is the shell script that initializes the variables. +# The first argument is the shell script that initializes the variables: # sourceDir # outputDir # tmpDir @@ -10,6 +10,7 @@ # imageSize # addBuildCompatibilityLibDir # sourceDirsToCopy +# updateOnly # # bfsShell # copyattr @@ -53,16 +54,20 @@ # create the image and mount it if [ $isImage ]; then echo - echo "Creating image ..." - dd if=/dev/zero of=$imagePath bs=1M count=$imageSize - $bfsShell --initialize $imagePath Haiku - $makebootable $imagePath + if [ ! $updateOnly ]; then + echo "Creating image ..." + dd if=/dev/zero of=$imagePath bs=1M count=$imageSize + $bfsShell --initialize $imagePath Haiku + $makebootable $imagePath + fi $bfsShell -n $imagePath > /dev/null & sleep 1 fi -$mkindex BEOS:APP_SIG - # needed to launch apps via signature +# create BEOS:APP_SIG index -- needed to launch apps via signature +if [ ! $updateOnly ]; then + $mkindex BEOS:APP_SIG +fi echo "Populating image ..." while [ $# -gt 0 ]; do @@ -73,55 +78,58 @@ # install MIME database # TODO: It should be possible to do that in the build system too. -mimeDBSource=$sourceDir/src/data/beos_mime -mimeDBDest=${tPrefix}home/config/settings/beos_mime -echo "Deleting old MIME database ..." +if [ ! $updateOnly ]; then + mimeDBSource=$sourceDir/src/data/beos_mime + mimeDBDest=${tPrefix}home/config/settings/beos_mime -$rm -rf $mimeDBDest -$mkdir -p $mimeDBDest -mkdir -p $tmpDir -mimeTmpDir=$tmpDir/mime -mimeTmpIndex=0 + echo "Deleting old MIME database ..." -# create tmp dir for the MIME conversion stuff -mkdir -p $mimeTmpDir + $rm -rf $mimeDBDest + $mkdir -p $mimeDBDest + mkdir -p $tmpDir + mimeTmpDir=$tmpDir/mime + mimeTmpIndex=0 -echo "Installing MIME database ..." + # create tmp dir for the MIME conversion stuff + mkdir -p $mimeTmpDir -for inSuperFile in $mimeDBSource/*.super; do - superType=$(basename $inSuperFile .super) - outSuperDir=$mimeDBDest/$superType + echo "Installing MIME database ..." - # compile rdef to rsrc file and the rsrc file to attributes - mimeTmpIndex=$(($mimeTmpIndex + 1)) - tmpFile=$mimeTmpDir/mimedb$$_${mimeTmpIndex}.rsrc - tmpFile2=$mimeTmpDir/mimedb$$_${mimeTmpIndex}.mime - $rc -o $tmpFile $inSuperFile - mkdir -p $tmpFile2 - $resattr -O -o $tmpFile2 $tmpFile - $cp -r ${sPrefix}$tmpFile2 $outSuperDir + for inSuperFile in $mimeDBSource/*.super; do + superType=$(basename $inSuperFile .super) + outSuperDir=$mimeDBDest/$superType - # iterate through the sub types - for inSubFile in $mimeDBSource/$superType/*; do - # check, if the type exists - if test -f $inSubFile && grep META:TYPE $inSubFile > /dev/null 2>&1 ; then - subType=$(basename $inSubFile) - outSubFile=$outSuperDir/$subType + # compile rdef to rsrc file and the rsrc file to attributes + mimeTmpIndex=$(($mimeTmpIndex + 1)) + tmpFile=$mimeTmpDir/mimedb$$_${mimeTmpIndex}.rsrc + tmpFile2=$mimeTmpDir/mimedb$$_${mimeTmpIndex}.mime + $rc -o $tmpFile $inSuperFile + mkdir -p $tmpFile2 + $resattr -O -o $tmpFile2 $tmpFile + $cp -r ${sPrefix}$tmpFile2 $outSuperDir - # compile rdef to rsrc file and the rsrc file to attributes - mimeTmpIndex=$(($mimeTmpIndex + 1)) - tmpFile=$mimeTmpDir/mimedb$$_${mimeTmpIndex}.rsrc - tmpFile2=$mimeTmpDir/mimedb$$_${mimeTmpIndex}.mime - $rc -o $tmpFile $inSubFile - $resattr -O -o $tmpFile2 $tmpFile - $cp ${sPrefix}$tmpFile2 $outSubFile - fi + # iterate through the sub types + for inSubFile in $mimeDBSource/$superType/*; do + # check, if the type exists + if test -f $inSubFile && grep META:TYPE $inSubFile > /dev/null 2>&1 ; then + subType=$(basename $inSubFile) + outSubFile=$outSuperDir/$subType + + # compile rdef to rsrc file and the rsrc file to attributes + mimeTmpIndex=$(($mimeTmpIndex + 1)) + tmpFile=$mimeTmpDir/mimedb$$_${mimeTmpIndex}.rsrc + tmpFile2=$mimeTmpDir/mimedb$$_${mimeTmpIndex}.mime + $rc -o $tmpFile $inSubFile + $resattr -O -o $tmpFile2 $tmpFile + $cp ${sPrefix}$tmpFile2 $outSubFile + fi + done done -done -# cleanup tmp dir -rm -rf $mimeTmpDir + # cleanup tmp dir + rm -rf $mimeTmpDir +fi # ! updateOnly # install sources From korli at mail.berlios.de Sat Apr 7 00:40:24 2007 From: korli at mail.berlios.de (korli at BerliOS) Date: Sat, 7 Apr 2007 00:40:24 +0200 Subject: [Haiku-commits] r20603 - in haiku/trunk: headers/os/game src/kits/game Message-ID: <200704062240.l36MeOJg008829@sheep.berlios.de> Author: korli Date: 2007-04-07 00:40:23 +0200 (Sat, 07 Apr 2007) New Revision: 20603 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20603&view=rev Modified: haiku/trunk/headers/os/game/FileGameSound.h haiku/trunk/src/kits/game/FileGameSound.cpp haiku/trunk/src/kits/game/GSUtility.cpp haiku/trunk/src/kits/game/GameProducer.cpp haiku/trunk/src/kits/game/GameSound.cpp haiku/trunk/src/kits/game/Jamfile haiku/trunk/src/kits/game/PushGameSound.cpp haiku/trunk/src/kits/game/SimpleGameSound.cpp haiku/trunk/src/kits/game/StreamingGameSound.cpp Log: change the way FileGameSound works : avoid using a port code style, some clean up Modified: haiku/trunk/headers/os/game/FileGameSound.h =================================================================== --- haiku/trunk/headers/os/game/FileGameSound.h 2007-04-06 21:13:35 UTC (rev 20602) +++ haiku/trunk/headers/os/game/FileGameSound.h 2007-04-06 22:40:23 UTC (rev 20603) @@ -95,8 +95,6 @@ status_t Init(const entry_ref* file); - static int32 ReadThread(void* arg); - bool Load(); bool Read(void * buffer, size_t bytes); Modified: haiku/trunk/src/kits/game/FileGameSound.cpp =================================================================== --- haiku/trunk/src/kits/game/FileGameSound.cpp 2007-04-06 21:13:35 UTC (rev 20602) +++ haiku/trunk/src/kits/game/FileGameSound.cpp 2007-04-06 22:40:23 UTC (rev 20603) @@ -24,24 +24,18 @@ // Description: BFileGameSound is a class that streams data out of a file. //------------------------------------------------------------------------------ -// Standard Includes ----------------------------------------------------------- #include #include -// System Includes ------------------------------------------------------------- #include +#include #include #include #include -// Project Includes ------------------------------------------------------------ -#include -#include +#include "GameSoundDevice.h" +#include "GSUtility.h" -// Local Includes -------------------------------------------------------------- -#include - -// Local Defines --------------------------------------------------------------- const int32 kPages = 20; struct _gs_media_tracker { @@ -150,7 +144,8 @@ fPaused(false), fPauseGain(1.0) { - if (InitCheck() == B_OK) SetInitError(Init(file)); + if (InitCheck() == B_OK) + SetInitError(Init(file)); } @@ -185,11 +180,9 @@ if (fAudioStream) { - if (fAudioStream->stream) fAudioStream->file->ReleaseTrack(fAudioStream->stream); + if (fAudioStream->stream) + fAudioStream->file->ReleaseTrack(fAudioStream->stream); - fAudioStream->file->CloseFile(); - - //delete fAudioStream->stream; delete fAudioStream->file; } @@ -209,17 +202,9 @@ BFileGameSound::StartPlaying() { // restart playback if needed - if (IsPlaying()) StopPlaying(); + if (IsPlaying()) + StopPlaying(); - fPort = create_port(kPages, "audioque"); - - // create the thread that will read the file - fReadThread = spawn_thread(ReadThread, "audiostream", B_NORMAL_PRIORITY, this); - if (fReadThread < B_OK) return B_NO_MORE_THREADS; - - status_t error = resume_thread(fReadThread); - if (error != B_OK) return error; - // start playing the file return BStreamingGameSound::StartPlaying(); } @@ -237,10 +222,6 @@ fStopping = false; fAudioStream->position = 0; fPlayPosition = 0; - - // we don't need to read any more - kill_thread(fReadThread); - delete_port(fPort); return error; } @@ -250,9 +231,7 @@ BFileGameSound::Preload() { if (!IsPlaying()) - { - for(int32 i = 0; i < kPages / 2; i++) Load(); - } + Load(); return B_OK; } @@ -262,23 +241,20 @@ BFileGameSound::FillBuffer(void *inBuffer, size_t inByteCount) { - int32 cookie; size_t bytes = inByteCount; - if (!fPaused || fPausing) - { - // time to read a new buffer - if (fPlayPosition == 0) read_port_etc(fPort, &cookie, fBuffer, fBufferSize, B_TIMEOUT, 0); - - if (fPausing) - { + if (!fPaused || fPausing) { + if (fPlayPosition == 0 || fPlayPosition + inByteCount >= fBufferSize) { + Load(); + } + + if (fPausing) { Lock(); bool rampDone = false; - // Fill the requsted buffer, stopping if the paused flag is set - switch(Format().format) - { + // Fill the requested buffer, stopping if the paused flag is set + switch(Format().format) { case gs_audio_format::B_GS_U8: rampDone = ::FillBuffer(fPausing, (uint8*)inBuffer, (uint8*)&fBuffer[fPlayPosition], &bytes); break; @@ -297,11 +273,9 @@ } // We finished ramping - if (rampDone) - { - if (bytes < inByteCount && !fPausing) - { - // Since are resumming play back, we need to copy any remaining samples + if (rampDone) { + if (bytes < inByteCount && !fPausing) { + // Since we are resuming play back, we need to copy any remaining samples char * buffer = (char*)inBuffer; memcpy(&buffer[bytes], &fBuffer[fPlayPosition + bytes], inByteCount - bytes); } @@ -311,15 +285,12 @@ } Unlock(); - } - else - { + } else { size_t byte = 0; char * buffer = (char*)inBuffer; // We need to be able to stop asap when the pause flag is flipped. - while(byte < bytes && (!fPaused || fPausing)) - { + while(byte < bytes && (!fPaused || fPausing)) { buffer[byte] = fBuffer[fPlayPosition + byte]; byte++; } @@ -328,13 +299,7 @@ } } - fPlayPosition += bytes; - if (fPlayPosition >= fBufferSize) - { - // We have finished reading the buffer. Setup for the next buffer. - fPlayPosition = 0; - memset(fBuffer, 0, fBufferSize); - } + fPlayPosition += bytes; } @@ -394,31 +359,35 @@ fAudioStream->file = new BMediaFile(file); status_t error = fAudioStream->file->InitCheck(); - if (error != B_OK) return error; + if (error != B_OK) + return error; fAudioStream->stream = fAudioStream->file->TrackAt(0); // is this is an audio file? - media_format mformat; - fAudioStream->stream->EncodedFormat(&mformat); - if (!mformat.IsAudio()) return B_MEDIA_BAD_FORMAT; + media_format playFormat; + fAudioStream->stream->EncodedFormat(&playFormat); + if (!playFormat.IsAudio()) + return B_MEDIA_BAD_FORMAT; gs_audio_format dformat = Device()->Format(); // request the format we want the sound - memset(&mformat, 0, sizeof(media_format)); - mformat.type = B_MEDIA_RAW_AUDIO; - fAudioStream->stream->DecodedFormat(&mformat); + memset(&playFormat, 0, sizeof(media_format)); + playFormat.type = B_MEDIA_RAW_AUDIO; + if (fAudioStream->stream->DecodedFormat(&playFormat) != B_OK) + return B_MEDIA_BAD_FORMAT; // translate the format into a "GameKit" friendly one gs_audio_format gsformat; - media_to_gs_format(&gsformat, &mformat.u.raw_audio); + media_to_gs_format(&gsformat, &playFormat.u.raw_audio); // Since the buffer sized read from the file is most likely differnt // then the buffer used by the audio mixer, we must allocate a buffer // large enough to hold the largest request. fBufferSize = gsformat.buffer_size; - if (fBufferSize < dformat.buffer_size) fBufferSize = dformat.buffer_size; + if (fBufferSize < dformat.buffer_size) + fBufferSize = dformat.buffer_size; // create the buffer fBuffer = new char[fBufferSize * 2]; @@ -430,57 +399,28 @@ // Ask the device to attach our sound to it gs_id sound; error = Device()->CreateBuffer(&sound, this, &gsformat); - if (error != B_OK) return error; + if (error != B_OK) + return error; return BGameSound::Init(sound); } -int32 -BFileGameSound::ReadThread(void* arg) -{ - BFileGameSound* obj = (BFileGameSound*)arg; - - while(true) obj->Load(); - - return 0; -} - - bool BFileGameSound::Load() { - int64 frames; - char * buffer = &fBuffer[fBufferSize + fAudioStream->position]; - status_t err = fAudioStream->stream->ReadFrames(buffer, &frames); - if (err < B_OK) { - StopPlaying(); // XXX this is a hack, the whole class design is broken - } - int32 frame = fAudioStream->stream->CurrentFrame(); - - fAudioStream->position += fFrameSize * frames; - if (fAudioStream->position >= fBufferSize) - { - // we have filled the enter buffer, time to send - write_port(fPort, fBufferSize, &fBuffer[fBufferSize], fBufferSize); - fAudioStream->position = 0; + if (fPlayPosition != 0) { + memcpy(fBuffer, fBuffer + fPlayPosition, fBufferSize - fPlayPosition); + fPlayPosition = fBufferSize - fPlayPosition; } - if (frame >= fAudioStream->frames) - { - if (fLooping) - { - // since we are looping, we need to start reading from - // the begining of the file again. - int64 firstFrame = 0; - fAudioStream->stream->SeekToFrame(&firstFrame); - - fStopping = true; - } - else fStopping = true; - } - + // time to read a new buffer + int64 frames = 0; + fAudioStream->stream->ReadFrames(fBuffer + fPlayPosition, &frames); + fBufferSize = fPlayPosition + frames * fFrameSize; + fPlayPosition = 0; + return true; } Modified: haiku/trunk/src/kits/game/GSUtility.cpp =================================================================== --- haiku/trunk/src/kits/game/GSUtility.cpp 2007-04-06 21:13:35 UTC (rev 20602) +++ haiku/trunk/src/kits/game/GSUtility.cpp 2007-04-06 22:40:23 UTC (rev 20603) @@ -33,7 +33,7 @@ #include // Local Includes -------------------------------------------------------------- -#include +#include "GSUtility.h" // Local Defines --------------------------------------------------------------- Modified: haiku/trunk/src/kits/game/GameProducer.cpp =================================================================== --- haiku/trunk/src/kits/game/GameProducer.cpp 2007-04-06 21:13:35 UTC (rev 20602) +++ haiku/trunk/src/kits/game/GameProducer.cpp 2007-04-06 22:40:23 UTC (rev 20603) @@ -42,12 +42,12 @@ #include // Project Includes ------------------------------------------------------------ -#include -#include -#include +#include "GameSoundBuffer.h" +#include "GameSoundDevice.h" +#include "GSUtility.h" // Local Includes -------------------------------------------------------------- -#include +#include "GameProducer.h" // Local Defines --------------------------------------------------------------- struct _gs_play Modified: haiku/trunk/src/kits/game/GameSound.cpp =================================================================== --- haiku/trunk/src/kits/game/GameSound.cpp 2007-04-06 21:13:35 UTC (rev 20602) +++ haiku/trunk/src/kits/game/GameSound.cpp 2007-04-06 22:40:23 UTC (rev 20603) @@ -25,18 +25,14 @@ // of the rest of it's childern. //------------------------------------------------------------------------------ -// Standard Includes ----------------------------------------------------------- #include #include -// System Includes ------------------------------------------------------------- +#include -// Project Includes ------------------------------------------------------------ -#include -#include +#include "GameSoundBuffer.h" +#include "GameSoundDevice.h" -// Local Includes -------------------------------------------------------------- -#include using std::nothrow; Modified: haiku/trunk/src/kits/game/Jamfile =================================================================== --- haiku/trunk/src/kits/game/Jamfile 2007-04-06 21:13:35 UTC (rev 20602) +++ haiku/trunk/src/kits/game/Jamfile 2007-04-06 22:40:23 UTC (rev 20603) @@ -1,5 +1,7 @@ SubDir HAIKU_TOP src kits game ; +SetSubDirSupportedPlatformsBeOSCompatible ; + AddSubDirSupportedPlatforms libbe_test ; UsePrivateHeaders app ; Modified: haiku/trunk/src/kits/game/PushGameSound.cpp =================================================================== --- haiku/trunk/src/kits/game/PushGameSound.cpp 2007-04-06 21:13:35 UTC (rev 20602) +++ haiku/trunk/src/kits/game/PushGameSound.cpp 2007-04-06 22:40:23 UTC (rev 20603) @@ -24,21 +24,14 @@ // Description: BPushGameSound class //------------------------------------------------------------------------------ -// Standard Includes ----------------------------------------------------------- #include -// System Includes ------------------------------------------------------------- #include - -// Project Includes ------------------------------------------------------------ -#include - -// Local Includes -------------------------------------------------------------- #include -// Local Defines --------------------------------------------------------------- +#include "GSUtility.h" -// BPushGameSound -------------------------------------------------------------- + BPushGameSound::BPushGameSound(size_t inBufferFrameCount, const gs_audio_format *format, size_t inBufferCount, Modified: haiku/trunk/src/kits/game/SimpleGameSound.cpp =================================================================== --- haiku/trunk/src/kits/game/SimpleGameSound.cpp 2007-04-06 21:13:35 UTC (rev 20602) +++ haiku/trunk/src/kits/game/SimpleGameSound.cpp 2007-04-06 22:40:23 UTC (rev 20603) @@ -43,7 +43,8 @@ BGameSoundDevice *device) : BGameSound(device) { - if (InitCheck() == B_OK) SetInitError(Init(inFile)); + if (InitCheck() == B_OK) + SetInitError(Init(inFile)); } @@ -69,7 +70,8 @@ BGameSoundDevice *device) : BGameSound(device) { - if (InitCheck() == B_OK) SetInitError(Init(inData, inFrameCount, format)); + if (InitCheck() == B_OK) + SetInitError(Init(inData, inFrameCount, format)); } Modified: haiku/trunk/src/kits/game/StreamingGameSound.cpp =================================================================== --- haiku/trunk/src/kits/game/StreamingGameSound.cpp 2007-04-06 21:13:35 UTC (rev 20602) +++ haiku/trunk/src/kits/game/StreamingGameSound.cpp 2007-04-06 22:40:23 UTC (rev 20603) @@ -30,10 +30,10 @@ // System Includes ------------------------------------------------------------- // Project Includes ------------------------------------------------------------ -#include +#include "GameSoundDevice.h" // Local Includes -------------------------------------------------------------- -#include +#include "StreamingGameSound.h" // Local Defines --------------------------------------------------------------- BStreamingGameSound::BStreamingGameSound(size_t inBufferFrameCount, From bonefish at mail.berlios.de Sat Apr 7 03:27:29 2007 From: bonefish at mail.berlios.de (bonefish at BerliOS) Date: Sat, 7 Apr 2007 03:27:29 +0200 Subject: [Haiku-commits] r20604 - in haiku/trunk: build/jam src/add-ons/accelerants/atimach64 src/add-ons/accelerants/et6x00 src/add-ons/accelerants/intel_extreme src/add-ons/accelerants/matrox src/add-ons/accelerants/neomagic src/add-ons/accelerants/nvidia src/add-ons/accelerants/radeon src/add-ons/accelerants/s3savage src/add-ons/accelerants/skeleton src/add-ons/accelerants/tdfx src/add-ons/accelerants/vesa src/add-ons/accelerants/via src/add-ons/accelerants/vmware src/add-ons/decorators/BeDecorator src/add-ons/decorators/MacDecorator src/add-ons/decorators/WinDecorator src/add-ons/disk_scanner/partition src/add-ons/input_server/devices/easypen src/add-ons/input_server/devices/keyboard src/add-ons/input_server/devices/mouse src/add-ons/input_server/devices/serial_mouse src/add-ons/input_server/devices/tablet src/add-ons/input_server/filters/screensaver src/add-ons/input_server/methods/canna src/add-ons/kernel/disk_scanner/fs src/add-ons/kernel/file_systems/udf/drive_setup_addon src/add-on! s/kernel/partitioning_systems/amiga src/add-ons/kernel/partitioning_systems/apple src/add-ons/kernel/partitioning_systems/intel src/add-ons/kernel/partitioning_systems/session src/add-ons/mail_daemon/inbound_filters/match_header src/add-ons/mail_daemon/inbound_filters/r5_filter src/add-ons/mail_daemon/inbound_filters/spam_filter src/add-ons/mail_daemon/inbound_protocols/imap src/add-ons/mail_daemon/inbound_protocols/pop3 src/add-ons/mail_daemon/outbound_filters/fortune src/add-ons/mail_daemon/outbound_protocols/smtp src/add-ons/mail_daemon/system_filters/inbox src/add-ons/mail_daemon/system_filters/notifier src/add-ons/mail_daemon/system_filters/outbox src/add-ons/mail_daemon/system_filters/parser src/add-ons/media/media-add-ons/demultiplexer src/add-ons/media/media-add-ons/esound_sink src/add-ons/media/media-add-ons/legacy src/add-ons/media/media-add-ons/mixer src/add-ons/media/media-add-ons/multi_audio src/add-ons/media/media-add-ons/radeon src/add-ons/media/media-add-ons! /reader src/add-ons/media/media-add-ons/tone_producer_demo src! /add-ons Message-ID: <200704070127.l371RTtC010322@sheep.berlios.de> Author: bonefish Date: 2007-04-07 03:27:19 +0200 (Sat, 07 Apr 2007) New Revision: 20604 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20604&view=rev Modified: haiku/trunk/build/jam/MainBuildRules haiku/trunk/src/add-ons/accelerants/atimach64/Jamfile haiku/trunk/src/add-ons/accelerants/et6x00/Jamfile haiku/trunk/src/add-ons/accelerants/intel_extreme/Jamfile haiku/trunk/src/add-ons/accelerants/matrox/Jamfile haiku/trunk/src/add-ons/accelerants/neomagic/Jamfile haiku/trunk/src/add-ons/accelerants/nvidia/Jamfile haiku/trunk/src/add-ons/accelerants/radeon/Jamfile haiku/trunk/src/add-ons/accelerants/s3savage/Jamfile haiku/trunk/src/add-ons/accelerants/skeleton/Jamfile haiku/trunk/src/add-ons/accelerants/tdfx/Jamfile haiku/trunk/src/add-ons/accelerants/vesa/Jamfile haiku/trunk/src/add-ons/accelerants/via/Jamfile haiku/trunk/src/add-ons/accelerants/vmware/Jamfile haiku/trunk/src/add-ons/decorators/BeDecorator/Jamfile haiku/trunk/src/add-ons/decorators/MacDecorator/Jamfile haiku/trunk/src/add-ons/decorators/WinDecorator/Jamfile haiku/trunk/src/add-ons/disk_scanner/partition/Jamfile haiku/trunk/src/add-ons/input_server/devices/easypen/Jamfile haiku/trunk/src/add-ons/input_server/devices/keyboard/Jamfile haiku/trunk/src/add-ons/input_server/devices/mouse/Jamfile haiku/trunk/src/add-ons/input_server/devices/serial_mouse/Jamfile haiku/trunk/src/add-ons/input_server/devices/tablet/Jamfile haiku/trunk/src/add-ons/input_server/filters/screensaver/Jamfile haiku/trunk/src/add-ons/input_server/methods/canna/Jamfile haiku/trunk/src/add-ons/kernel/disk_scanner/fs/Jamfile haiku/trunk/src/add-ons/kernel/file_systems/udf/drive_setup_addon/Jamfile haiku/trunk/src/add-ons/kernel/partitioning_systems/amiga/Jamfile haiku/trunk/src/add-ons/kernel/partitioning_systems/apple/Jamfile haiku/trunk/src/add-ons/kernel/partitioning_systems/intel/Jamfile haiku/trunk/src/add-ons/kernel/partitioning_systems/session/Jamfile haiku/trunk/src/add-ons/mail_daemon/inbound_filters/match_header/Jamfile haiku/trunk/src/add-ons/mail_daemon/inbound_filters/r5_filter/Jamfile haiku/trunk/src/add-ons/mail_daemon/inbound_filters/spam_filter/Jamfile haiku/trunk/src/add-ons/mail_daemon/inbound_protocols/imap/Jamfile haiku/trunk/src/add-ons/mail_daemon/inbound_protocols/pop3/Jamfile haiku/trunk/src/add-ons/mail_daemon/outbound_filters/fortune/Jamfile haiku/trunk/src/add-ons/mail_daemon/outbound_protocols/smtp/Jamfile haiku/trunk/src/add-ons/mail_daemon/system_filters/inbox/Jamfile haiku/trunk/src/add-ons/mail_daemon/system_filters/notifier/Jamfile haiku/trunk/src/add-ons/mail_daemon/system_filters/outbox/Jamfile haiku/trunk/src/add-ons/mail_daemon/system_filters/parser/Jamfile haiku/trunk/src/add-ons/media/media-add-ons/demultiplexer/Jamfile haiku/trunk/src/add-ons/media/media-add-ons/esound_sink/Jamfile haiku/trunk/src/add-ons/media/media-add-ons/legacy/Jamfile haiku/trunk/src/add-ons/media/media-add-ons/mixer/Jamfile haiku/trunk/src/add-ons/media/media-add-ons/multi_audio/Jamfile haiku/trunk/src/add-ons/media/media-add-ons/radeon/Jamfile haiku/trunk/src/add-ons/media/media-add-ons/reader/Jamfile haiku/trunk/src/add-ons/media/media-add-ons/tone_producer_demo/Jamfile haiku/trunk/src/add-ons/media/media-add-ons/usb_vision/Jamfile haiku/trunk/src/add-ons/media/media-add-ons/usb_webcam/Jamfile haiku/trunk/src/add-ons/media/media-add-ons/video_producer_demo/Jamfile haiku/trunk/src/add-ons/media/media-add-ons/writer/Jamfile haiku/trunk/src/add-ons/media/plugins/ac3_decoder/Jamfile haiku/trunk/src/add-ons/media/plugins/aiff_reader/Jamfile haiku/trunk/src/add-ons/media/plugins/au_reader/Jamfile haiku/trunk/src/add-ons/media/plugins/avcodec/Jamfile haiku/trunk/src/add-ons/media/plugins/avi_reader/Jamfile haiku/trunk/src/add-ons/media/plugins/matroska/Jamfile haiku/trunk/src/add-ons/media/plugins/mov_reader/Jamfile haiku/trunk/src/add-ons/media/plugins/mp3_decoder/Jamfile haiku/trunk/src/add-ons/media/plugins/mp3_reader/Jamfile haiku/trunk/src/add-ons/media/plugins/mp4_reader/Jamfile haiku/trunk/src/add-ons/media/plugins/musepack/Jamfile haiku/trunk/src/add-ons/media/plugins/ogg/Jamfile haiku/trunk/src/add-ons/media/plugins/raw_decoder/Jamfile haiku/trunk/src/add-ons/media/plugins/speex/Jamfile haiku/trunk/src/add-ons/media/plugins/vorbis/Jamfile haiku/trunk/src/add-ons/media/plugins/wav_reader/Jamfile haiku/trunk/src/add-ons/opengl/mesa_software_renderer/Jamfile haiku/trunk/src/add-ons/print/drivers/canon_lips/lips3/Jamfile haiku/trunk/src/add-ons/print/drivers/canon_lips/lips4/Jamfile haiku/trunk/src/add-ons/print/drivers/pcl5/Jamfile haiku/trunk/src/add-ons/print/drivers/pcl6/Jamfile haiku/trunk/src/add-ons/print/drivers/pdf/source/Jamfile haiku/trunk/src/add-ons/print/drivers/postscript/Jamfile haiku/trunk/src/add-ons/print/drivers/preview/Jamfile haiku/trunk/src/add-ons/print/transports/hp_jetdirect/Jamfile haiku/trunk/src/add-ons/print/transports/ipp/Jamfile haiku/trunk/src/add-ons/print/transports/lpr/Jamfile haiku/trunk/src/add-ons/print/transports/parallel_port/Jamfile haiku/trunk/src/add-ons/print/transports/print_to_file/Jamfile haiku/trunk/src/add-ons/print/transports/serial_port/Jamfile haiku/trunk/src/add-ons/print/transports/usb_port/Jamfile haiku/trunk/src/add-ons/screen_savers/haiku/Jamfile haiku/trunk/src/add-ons/tracker/filetype/Jamfile haiku/trunk/src/add-ons/tracker/mark_as/Jamfile haiku/trunk/src/tests/add-ons/kernel/disk_scanner/Jamfile haiku/trunk/src/tests/add-ons/kernel/disk_scanner/fs/Jamfile haiku/trunk/src/tests/add-ons/kernel/disk_scanner/partition/Jamfile haiku/trunk/src/tests/add-ons/kernel/disk_scanner/session/Jamfile haiku/trunk/src/tests/add-ons/kernel/file_systems/udf/r5/drive_setup_addon/Jamfile haiku/trunk/src/tests/add-ons/kernel/file_systems/userlandfs/bfs/Jamfile haiku/trunk/src/tests/add-ons/kernel/file_systems/userlandfs/r5/src/test/netfs/client/Jamfile haiku/trunk/src/tests/add-ons/kernel/file_systems/userlandfs/r5/src/test/ramfs/Jamfile haiku/trunk/src/tests/add-ons/kernel/file_systems/userlandfs/r5/src/test/reiserfs/Jamfile haiku/trunk/src/tests/add-ons/kernel/file_systems/userlandfs/ramfs/Jamfile haiku/trunk/src/tests/add-ons/kernel/file_systems/userlandfs/ramfs/beos_interface/Jamfile haiku/trunk/src/tests/add-ons/kernel/file_systems/userlandfs/reiserfs/Jamfile haiku/trunk/src/tests/add-ons/kernel/file_systems/userlandfs/reiserfs/beos_interface/Jamfile haiku/trunk/src/tests/add-ons/kernel/network/core/Jamfile haiku/trunk/src/tests/add-ons/kernel/network/interfaces/ethernet/Jamfile haiku/trunk/src/tests/add-ons/kernel/network/interfaces/loopback/Jamfile haiku/trunk/src/tests/add-ons/kernel/network/interfaces/ppp/Jamfile haiku/trunk/src/tests/add-ons/kernel/network/ppp/ipcp/Jamfile haiku/trunk/src/tests/add-ons/kernel/network/ppp/modem/Jamfile haiku/trunk/src/tests/add-ons/kernel/network/ppp/pap/Jamfile haiku/trunk/src/tests/add-ons/kernel/network/ppp/pppoe/Jamfile haiku/trunk/src/tests/add-ons/kernel/network/protocols/icmp/Jamfile haiku/trunk/src/tests/add-ons/kernel/network/protocols/ipv4/Jamfile haiku/trunk/src/tests/add-ons/kernel/network/protocols/raw/Jamfile haiku/trunk/src/tests/add-ons/kernel/network/protocols/route/Jamfile haiku/trunk/src/tests/add-ons/kernel/network/protocols/tcp/Jamfile haiku/trunk/src/tests/add-ons/kernel/network/protocols/udp/Jamfile haiku/trunk/src/tests/kits/net/new_stack/atomizer/Jamfile haiku/trunk/src/tests/kits/net/new_stack/framings/ethernet/Jamfile haiku/trunk/src/tests/kits/net/new_stack/interfaces/ether_drivers/Jamfile haiku/trunk/src/tests/kits/net/new_stack/interfaces/loopback/Jamfile haiku/trunk/src/tests/kits/net/new_stack/memory_pool/Jamfile haiku/trunk/src/tests/kits/net/new_stack/protocols/arp/Jamfile haiku/trunk/src/tests/kits/net/new_stack/protocols/ipv4/Jamfile haiku/trunk/src/tests/kits/net/new_stack/stack/Jamfile haiku/trunk/src/tests/servers/input/msgspy/Jamfile haiku/trunk/src/tests/servers/input/view_input_device/Jamfile Log: Removed the obsolete second argument ("relpath") of the Addon rule and shuffled "isExecutable" to the end. The new order favors the common use cases. Adjusted all Addon invocations and while at it also removed separate LinkAgainst invocations. Modified: haiku/trunk/build/jam/MainBuildRules =================================================================== --- haiku/trunk/build/jam/MainBuildRules 2007-04-06 22:40:23 UTC (rev 20603) +++ haiku/trunk/build/jam/MainBuildRules 2007-04-07 01:27:19 UTC (rev 20604) @@ -98,46 +98,42 @@ Executable $(1) : $(2) : $(3) : $(4) ; } -rule Addon +rule Addon target : sources : libraries : isExecutable { - # Addon : : : : ; - # : Name of the add-on. - # : Path where the add-on shall live relative to the add-on dir. + # Addon : : : ; + # : The add-on. # : Source files. - # : true, if the target shall be executable as well. # : Libraries to be linked against. -# TODO: is no longer needed + # : true, if the target shall be executable as well. - if ! [ IsPlatformSupportedForTarget $(1) ] { + if ! [ IsPlatformSupportedForTarget $(target) ] { return ; } - local isExecutable = $(4) ; - - Main $(1) : $(3) ; + Main $(target) : $(sources) ; - local linkFlags = -Xlinker -soname=\"$(1:G=)\" ; + local linkFlags = -Xlinker -soname=\"$(target:G=)\" ; if $(isExecutable) != true { linkFlags = -nostart $(linkFlags) ; } - LINKFLAGS on $(1) = [ on $(1) return $(LINKFLAGS) ] $(linkFlags) ; - LinkAgainst $(1) : $(5) ; + LINKFLAGS on $(target) = [ on $(target) return $(LINKFLAGS) ] $(linkFlags) ; + LinkAgainst $(target) : $(libraries) ; - AddSharedObjectGlueCode $(1) : $(isExecutable) ; + AddSharedObjectGlueCode $(target) : $(isExecutable) ; } -rule Translator +rule Translator target : sources : libraries { - # Translator : : ; + # Translator : : ; # TODO: Although they currently all are, translators don't need to be # executable. Introduce a flag as for Addon. - Addon $(1) : Translators : $(2) : true : $(3) ; + Addon $(target) : $(sources) : $(libraries) : true ; } -rule ScreenSaver +rule ScreenSaver target : sources : libraries { - # ScreenSaver : : ; - Addon $(1) : screen_savers : $(2) : false : $(3) ; + # ScreenSaver : : ; + Addon $(target) : $(sources) : $(libraries) : false ; } rule StaticLibrary Modified: haiku/trunk/src/add-ons/accelerants/atimach64/Jamfile =================================================================== --- haiku/trunk/src/add-ons/accelerants/atimach64/Jamfile 2007-04-06 22:40:23 UTC (rev 20603) +++ haiku/trunk/src/add-ons/accelerants/atimach64/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) @@ -3,7 +3,7 @@ UsePrivateHeaders graphics ; UsePrivateHeaders [ FDirName graphics atimach64 ] ; -Addon atimach64.accelerant : accelerants : +Addon atimach64.accelerant : Acceleration.c Cursor.c EngineManagment.c Modified: haiku/trunk/src/add-ons/accelerants/et6x00/Jamfile =================================================================== --- haiku/trunk/src/add-ons/accelerants/et6x00/Jamfile 2007-04-06 22:40:23 UTC (rev 20603) +++ haiku/trunk/src/add-ons/accelerants/et6x00/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) @@ -2,7 +2,7 @@ UsePrivateHeaders [ FDirName graphics et6x00 ] ; -Addon et6x00.accelerant : accelerants : +Addon et6x00.accelerant : Acceleration.c EngineManagment.c GetAccelerantHook.c @@ -11,8 +11,6 @@ InitAccelerant.c ProposeDisplayMode.c SetDisplayMode.c - : false - : ; Depends et6x00.accelerant : et6x00.driver ; Modified: haiku/trunk/src/add-ons/accelerants/intel_extreme/Jamfile =================================================================== --- haiku/trunk/src/add-ons/accelerants/intel_extreme/Jamfile 2007-04-06 22:40:23 UTC (rev 20603) +++ haiku/trunk/src/add-ons/accelerants/intel_extreme/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) @@ -6,7 +6,7 @@ UsePrivateHeaders [ FDirName graphics intel_extreme ] ; UsePrivateHeaders [ FDirName graphics common ] ; -Addon intel_extreme.accelerant : accelerants : +Addon intel_extreme.accelerant : accelerant.cpp cursor.cpp dpms.cpp @@ -15,11 +15,10 @@ memory.cpp mode.cpp overlay.cpp - : false : be ; Package haiku-intel_extreme-cvs : intel_extreme.accelerant : boot home config add-ons accelerants ; - \ No newline at end of file + Modified: haiku/trunk/src/add-ons/accelerants/matrox/Jamfile =================================================================== --- haiku/trunk/src/add-ons/accelerants/matrox/Jamfile 2007-04-06 22:40:23 UTC (rev 20603) +++ haiku/trunk/src/add-ons/accelerants/matrox/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) @@ -6,7 +6,7 @@ UsePrivateHeaders [ FDirName graphics matrox ] ; UseHeaders [ FDirName $(SUBDIR) engine ] ; -Addon mga.accelerant : accelerants : +Addon mga.accelerant : Cursor.c EngineManagment.c GetAccelerantHook.c @@ -17,7 +17,7 @@ Overlay.c ProposeDisplayMode.c SetDisplayMode.c - : false : libmatrox_engine.a + : libmatrox_engine.a ; Package haiku-matrox-cvs : Modified: haiku/trunk/src/add-ons/accelerants/neomagic/Jamfile =================================================================== --- haiku/trunk/src/add-ons/accelerants/neomagic/Jamfile 2007-04-06 22:40:23 UTC (rev 20603) +++ haiku/trunk/src/add-ons/accelerants/neomagic/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) @@ -6,7 +6,7 @@ UsePrivateHeaders [ FDirName graphics neomagic ] ; UseHeaders [ FDirName $(SUBDIR) engine ] ; -Addon nm.accelerant : accelerants : +Addon nm.accelerant : Acceleration.c Cursor.c EngineManagment.c @@ -18,7 +18,7 @@ Overlay.c ProposeDisplayMode.c SetDisplayMode.c - : false : libneomagic_engine.a + : libneomagic_engine.a ; Package haiku-neomagic-cvs : Modified: haiku/trunk/src/add-ons/accelerants/nvidia/Jamfile =================================================================== --- haiku/trunk/src/add-ons/accelerants/nvidia/Jamfile 2007-04-06 22:40:23 UTC (rev 20603) +++ haiku/trunk/src/add-ons/accelerants/nvidia/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) @@ -6,7 +6,7 @@ UsePrivateHeaders [ FDirName graphics nvidia ] ; UseHeaders [ FDirName $(SUBDIR) engine ] ; -Addon nv.accelerant : accelerants : +Addon nv.accelerant : Acceleration.c Cursor.c EngineManagment.c @@ -18,7 +18,7 @@ Overlay.c ProposeDisplayMode.c SetDisplayMode.c - : false : libnvidia_engine.a + : libnvidia_engine.a ; Package haiku-nvidia-cvs : Modified: haiku/trunk/src/add-ons/accelerants/radeon/Jamfile =================================================================== --- haiku/trunk/src/add-ons/accelerants/radeon/Jamfile 2007-04-06 22:40:23 UTC (rev 20603) +++ haiku/trunk/src/add-ons/accelerants/radeon/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) @@ -6,7 +6,7 @@ UsePrivateHeaders [ FDirName graphics radeon ] ; UsePrivateHeaders [ FDirName graphics common ] ; -Addon radeon.accelerant : accelerants : +Addon radeon.accelerant : Acceleration.c CP.c Cursor.c @@ -33,7 +33,6 @@ settings.cpp theatre_out.c vesa_modes.c - : false : libaccelerantscommon.a libradeon.a be ; Modified: haiku/trunk/src/add-ons/accelerants/s3savage/Jamfile =================================================================== --- haiku/trunk/src/add-ons/accelerants/s3savage/Jamfile 2007-04-06 22:40:23 UTC (rev 20603) +++ haiku/trunk/src/add-ons/accelerants/s3savage/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) @@ -5,7 +5,7 @@ UsePrivateHeaders graphics ; UsePrivateHeaders [ FDirName graphics s3savage ] ; -Addon s3savage.accelerant : accelerants : +Addon s3savage.accelerant : Acceleration.c Cursor.c EngineManagement.c @@ -20,7 +20,6 @@ s3drv.c s3vga.c - : false : be ; Modified: haiku/trunk/src/add-ons/accelerants/skeleton/Jamfile =================================================================== --- haiku/trunk/src/add-ons/accelerants/skeleton/Jamfile 2007-04-06 22:40:23 UTC (rev 20603) +++ haiku/trunk/src/add-ons/accelerants/skeleton/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) @@ -6,7 +6,7 @@ UsePrivateHeaders [ FDirName graphics skeleton ] ; UseHeaders [ FDirName $(SUBDIR) engine ] ; -Addon skel.accelerant : accelerants : +Addon skel.accelerant : Acceleration.c Cursor.c EngineManagement.c @@ -18,7 +18,7 @@ Overlay.c ProposeDisplayMode.c SetDisplayMode.c - : false : libskeleton_engine.a + : libskeleton_engine.a ; Package haiku-skeleton-cvs : Modified: haiku/trunk/src/add-ons/accelerants/tdfx/Jamfile =================================================================== --- haiku/trunk/src/add-ons/accelerants/tdfx/Jamfile 2007-04-06 22:40:23 UTC (rev 20603) +++ haiku/trunk/src/add-ons/accelerants/tdfx/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) @@ -4,7 +4,7 @@ UsePrivateHeaders [ FDirName graphics tdfx ] ; -Addon tdfx.accelerant : accelerants : +Addon tdfx.accelerant : voodoo3_accelerant.c Acceleration.c Cursor.c Modified: haiku/trunk/src/add-ons/accelerants/vesa/Jamfile =================================================================== --- haiku/trunk/src/add-ons/accelerants/vesa/Jamfile 2007-04-06 22:40:23 UTC (rev 20603) +++ haiku/trunk/src/add-ons/accelerants/vesa/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) @@ -5,11 +5,10 @@ #AddResources vesa.accelerant : vesa.accelerant.rdef ; -Addon vesa.accelerant : accelerants : +Addon vesa.accelerant : accelerant.cpp dpms.cpp engine.cpp hooks.cpp mode.cpp - : false # this add-on is not executable - ; +; Modified: haiku/trunk/src/add-ons/accelerants/via/Jamfile =================================================================== --- haiku/trunk/src/add-ons/accelerants/via/Jamfile 2007-04-06 22:40:23 UTC (rev 20603) +++ haiku/trunk/src/add-ons/accelerants/via/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) @@ -6,7 +6,7 @@ UsePrivateHeaders [ FDirName graphics via ] ; UseHeaders [ FDirName $(SUBDIR) engine ] ; -Addon via.accelerant : accelerants : +Addon via.accelerant : Acceleration.c Cursor.c EngineManagement.c @@ -18,7 +18,7 @@ Overlay.c ProposeDisplayMode.c SetDisplayMode.c - : false : libvia_engine.a + : libvia_engine.a ; Package haiku-via_gfx-cvs : Modified: haiku/trunk/src/add-ons/accelerants/vmware/Jamfile =================================================================== --- haiku/trunk/src/add-ons/accelerants/vmware/Jamfile 2007-04-06 22:40:23 UTC (rev 20603) +++ haiku/trunk/src/add-ons/accelerants/vmware/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) @@ -5,7 +5,7 @@ UsePrivateHeaders [ FDirName graphics vmware ] ; UsePrivateHeaders graphics ; -Addon vmware.accelerant : accelerants : +Addon vmware.accelerant : Acceleration.c Cursor.c EngineManagment.c @@ -16,7 +16,6 @@ InitAccelerant.c ProposeDisplayMode.c SetDisplayMode.c - : false ; Package haiku-vmware-video-svn : Modified: haiku/trunk/src/add-ons/decorators/BeDecorator/Jamfile =================================================================== --- haiku/trunk/src/add-ons/decorators/BeDecorator/Jamfile 2007-04-06 22:40:23 UTC (rev 20603) +++ haiku/trunk/src/add-ons/decorators/BeDecorator/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) @@ -5,8 +5,7 @@ UseHeaders [ FDirName $(HAIKU_TOP) src servers app drawing ] ; UsePrivateHeaders app shared interface graphics ; -Addon ClassicBe : decorators : +Addon ClassicBe : BeDecorator.cpp - : false : be app_server ; Modified: haiku/trunk/src/add-ons/decorators/MacDecorator/Jamfile =================================================================== --- haiku/trunk/src/add-ons/decorators/MacDecorator/Jamfile 2007-04-06 22:40:23 UTC (rev 20603) +++ haiku/trunk/src/add-ons/decorators/MacDecorator/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) @@ -4,8 +4,7 @@ UseHeaders [ FDirName $(HAIKU_TOP) src servers app server ] ; UsePrivateHeaders [ FDirName servers app ] ; -Addon MacDecorator : decorators : +Addon MacDecorator : MacDecorator.cpp - : false : be libappserver.so ; Modified: haiku/trunk/src/add-ons/decorators/WinDecorator/Jamfile =================================================================== --- haiku/trunk/src/add-ons/decorators/WinDecorator/Jamfile 2007-04-06 22:40:23 UTC (rev 20603) +++ haiku/trunk/src/add-ons/decorators/WinDecorator/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) @@ -4,8 +4,7 @@ UseHeaders [ FDirName $(HAIKU_TOP) src servers app server ] ; UsePrivateHeaders [ FDirName servers app ] ; -Addon WinDecorator : decorators : +Addon WinDecorator : WinDecorator.cpp - : false : be libappserver.so ; Modified: haiku/trunk/src/add-ons/disk_scanner/partition/Jamfile =================================================================== --- haiku/trunk/src/add-ons/disk_scanner/partition/Jamfile 2007-04-06 22:40:23 UTC (rev 20603) +++ haiku/trunk/src/add-ons/disk_scanner/partition/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) @@ -3,7 +3,7 @@ UsePrivateHeaders shared ; UsePrivateHeaders storage ; -Addon intel : disk_scanner : intel.cpp : false +Addon intel : intel.cpp : libdiskdevice.so be ; AbsSymLink intel : intel : /boot/home/config/add-ons/disk_scanner/partition ; Modified: haiku/trunk/src/add-ons/input_server/devices/easypen/Jamfile =================================================================== --- haiku/trunk/src/add-ons/input_server/devices/easypen/Jamfile 2007-04-06 22:40:23 UTC (rev 20603) +++ haiku/trunk/src/add-ons/input_server/devices/easypen/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) @@ -4,8 +4,7 @@ UsePrivateHeaders input ; -Addon easypen : input_server/devices : +Addon easypen : EasyPenInputDevice.cpp - : false : be device input_server ; Modified: haiku/trunk/src/add-ons/input_server/devices/keyboard/Jamfile =================================================================== --- haiku/trunk/src/add-ons/input_server/devices/keyboard/Jamfile 2007-04-06 22:40:23 UTC (rev 20603) +++ haiku/trunk/src/add-ons/input_server/devices/keyboard/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) @@ -5,14 +5,13 @@ UsePrivateHeaders input kernel tracker ; UseArchHeaders $(TARGET_ARCH) ; -Addon keyboard : input_server/devices : +Addon keyboard : KeyboardInputDevice.cpp Keymap.cpp TMWindow.cpp TMListItem.cpp - : false : input_server be ; Package haiku-inputkit-cvs : Modified: haiku/trunk/src/add-ons/input_server/devices/mouse/Jamfile =================================================================== --- haiku/trunk/src/add-ons/input_server/devices/mouse/Jamfile 2007-04-06 22:40:23 UTC (rev 20603) +++ haiku/trunk/src/add-ons/input_server/devices/mouse/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) @@ -4,9 +4,8 @@ UsePrivateHeaders input ; -Addon mouse : input_server/devices : +Addon mouse : MouseInputDevice.cpp - : false : be input_server ; Package haiku-inputkit-cvs : Modified: haiku/trunk/src/add-ons/input_server/devices/serial_mouse/Jamfile =================================================================== --- haiku/trunk/src/add-ons/input_server/devices/serial_mouse/Jamfile 2007-04-06 22:40:23 UTC (rev 20603) +++ haiku/trunk/src/add-ons/input_server/devices/serial_mouse/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) @@ -4,10 +4,9 @@ UsePrivateHeaders input ; -Addon serial_mouse : input_server/devices : +Addon serial_mouse : MouseInputDevice.cpp SerialMouse.cpp - : false : be device input_server ; Package haiku-inputkit-cvs : Modified: haiku/trunk/src/add-ons/input_server/devices/tablet/Jamfile =================================================================== --- haiku/trunk/src/add-ons/input_server/devices/tablet/Jamfile 2007-04-06 22:40:23 UTC (rev 20603) +++ haiku/trunk/src/add-ons/input_server/devices/tablet/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) @@ -4,9 +4,8 @@ UsePrivateHeaders input ; -Addon tablet : input_server/devices : +Addon tablet : TabletInputDevice.cpp - : false : be input_server ; Package haiku-inputkit-cvs : Modified: haiku/trunk/src/add-ons/input_server/filters/screensaver/Jamfile =================================================================== --- haiku/trunk/src/add-ons/input_server/filters/screensaver/Jamfile 2007-04-06 22:40:23 UTC (rev 20603) +++ haiku/trunk/src/add-ons/input_server/filters/screensaver/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) @@ -4,9 +4,8 @@ UsePrivateHeaders screen_saver ; -Addon screen_saver : input_server/filters : +Addon screen_saver : ScreenSaverFilter.cpp - : false : be libscreensaver.so input_server ; Package haiku-screensaverkit-cvs : Modified: haiku/trunk/src/add-ons/input_server/methods/canna/Jamfile =================================================================== --- haiku/trunk/src/add-ons/input_server/methods/canna/Jamfile 2007-04-06 22:40:23 UTC (rev 20603) +++ haiku/trunk/src/add-ons/input_server/methods/canna/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) @@ -11,13 +11,12 @@ SubDirC++Flags -fmultiple-symbol-spaces ; } -Addon canna : input_server/methods : +Addon canna : CannaInterface.cpp CannaLooper.cpp CannaMethod.cpp KouhoWindow.cpp PaletteWindow.cpp - : false : be textencoding input_server libcanna.a librk.a ; Package haiku-cannaIM-cvs : Modified: haiku/trunk/src/add-ons/kernel/disk_scanner/fs/Jamfile =================================================================== --- haiku/trunk/src/add-ons/kernel/disk_scanner/fs/Jamfile 2007-04-06 22:40:23 UTC (rev 20603) +++ haiku/trunk/src/add-ons/kernel/disk_scanner/fs/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) @@ -5,7 +5,7 @@ UsePrivateHeaders [ FDirName storage ] ; # For now build a userland version only. -Addon bfs : userland file_systems : +Addon bfs : bfs.c ; Modified: haiku/trunk/src/add-ons/kernel/file_systems/udf/drive_setup_addon/Jamfile =================================================================== --- haiku/trunk/src/add-ons/kernel/file_systems/udf/drive_setup_addon/Jamfile 2007-04-06 22:40:23 UTC (rev 20603) +++ haiku/trunk/src/add-ons/kernel/file_systems/udf/drive_setup_addon/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) @@ -31,16 +31,13 @@ # Note that the add-on is named "i-udf-ds" to put it alphabetically # before the standard iso9660 add-on, thus giving it first dibs at # iso9660/UDF hybrid discs. -Addon i-udf-ds : [ FDirName drive_setup fs ] : +Addon i-udf-ds : udf-ds.cpp Recognition.cpp UdfDebug.cpp UdfString.cpp UdfStructures.cpp Utils.cpp - - : false - : ; SEARCH on [ FGristFiles Modified: haiku/trunk/src/add-ons/kernel/partitioning_systems/amiga/Jamfile =================================================================== --- haiku/trunk/src/add-ons/kernel/partitioning_systems/amiga/Jamfile 2007-04-06 22:40:23 UTC (rev 20603) +++ haiku/trunk/src/add-ons/kernel/partitioning_systems/amiga/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) @@ -8,7 +8,7 @@ amiga_rdb.cpp ; -#Addon amiga_rdb : userland partitioning_systems : +#Addon amiga_rdb : # amiga_rdb.cpp # ; # Modified: haiku/trunk/src/add-ons/kernel/partitioning_systems/apple/Jamfile =================================================================== --- haiku/trunk/src/add-ons/kernel/partitioning_systems/apple/Jamfile 2007-04-06 22:40:23 UTC (rev 20603) +++ haiku/trunk/src/add-ons/kernel/partitioning_systems/apple/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) @@ -8,7 +8,7 @@ apple.cpp ; -#Addon apple : userland partitioning_systems : +#Addon apple : # apple.cpp # ; # Modified: haiku/trunk/src/add-ons/kernel/partitioning_systems/intel/Jamfile =================================================================== --- haiku/trunk/src/add-ons/kernel/partitioning_systems/intel/Jamfile 2007-04-06 22:40:23 UTC (rev 20603) +++ haiku/trunk/src/add-ons/kernel/partitioning_systems/intel/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) @@ -13,7 +13,7 @@ # Also build a userland version # ToDo: it's probably not a good idea to build them into the same directory -#Addon intel : userland partitioning_systems : +#Addon intel : # intel.cpp # PartitionMap.cpp # PartitionMapParser.cpp Modified: haiku/trunk/src/add-ons/kernel/partitioning_systems/session/Jamfile =================================================================== --- haiku/trunk/src/add-ons/kernel/partitioning_systems/session/Jamfile 2007-04-06 22:40:23 UTC (rev 20603) +++ haiku/trunk/src/add-ons/kernel/partitioning_systems/session/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) @@ -22,7 +22,7 @@ ; # also build a userland version -#Addon session : userland partitioning_systems : +#Addon session : # [ FGristFiles $(session_files:S=$(SUFOBJ)) ] #; # Modified: haiku/trunk/src/add-ons/mail_daemon/inbound_filters/match_header/Jamfile =================================================================== --- haiku/trunk/src/add-ons/mail_daemon/inbound_filters/match_header/Jamfile 2007-04-06 22:40:23 UTC (rev 20603) +++ haiku/trunk/src/add-ons/mail_daemon/inbound_filters/match_header/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) @@ -11,7 +11,7 @@ SubDirHdrs [ FDirName $(HAIKU_TOP) headers os add-ons mail_daemon ] ; -Addon Match\ Header : mail_daemon inbound_filters : +Addon Match\ Header : ConfigView.cpp RuleFilter.cpp StringMatcher.cpp ; Modified: haiku/trunk/src/add-ons/mail_daemon/inbound_filters/r5_filter/Jamfile =================================================================== --- haiku/trunk/src/add-ons/mail_daemon/inbound_filters/r5_filter/Jamfile 2007-04-06 22:40:23 UTC (rev 20603) +++ haiku/trunk/src/add-ons/mail_daemon/inbound_filters/r5_filter/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) @@ -11,7 +11,7 @@ SubDirHdrs [ FDirName $(HAIKU_TOP) headers os add-ons mail_daemon ] ; -Addon R5\ Daemon\ Filter : mail_daemon inbound_filters : +Addon R5\ Daemon\ Filter : filter.cpp ; LinkAgainst R5\ Daemon\ Filter : Modified: haiku/trunk/src/add-ons/mail_daemon/inbound_filters/spam_filter/Jamfile =================================================================== --- haiku/trunk/src/add-ons/mail_daemon/inbound_filters/spam_filter/Jamfile 2007-04-06 22:40:23 UTC (rev 20603) +++ haiku/trunk/src/add-ons/mail_daemon/inbound_filters/spam_filter/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) @@ -11,7 +11,7 @@ SubDirHdrs [ FDirName $(HAIKU_TOP) headers os add-ons mail_daemon ] ; -Addon Spam\ Filter : mail_daemon inbound_filters : +Addon Spam\ Filter : SpamFilterConfig.cpp SpamFilter.cpp ; Modified: haiku/trunk/src/add-ons/mail_daemon/inbound_protocols/imap/Jamfile =================================================================== --- haiku/trunk/src/add-ons/mail_daemon/inbound_protocols/imap/Jamfile 2007-04-06 22:40:23 UTC (rev 20603) +++ haiku/trunk/src/add-ons/mail_daemon/inbound_protocols/imap/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) @@ -16,7 +16,7 @@ SubDirHdrs [ FDirName / boot home config include ] ; } -Addon IMAP : mail_daemon inbound_protocols : +Addon IMAP : imap_client.cpp imap_config.cpp NestedString.cpp ; Modified: haiku/trunk/src/add-ons/mail_daemon/inbound_protocols/pop3/Jamfile =================================================================== --- haiku/trunk/src/add-ons/mail_daemon/inbound_protocols/pop3/Jamfile 2007-04-06 22:40:23 UTC (rev 20603) +++ haiku/trunk/src/add-ons/mail_daemon/inbound_protocols/pop3/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) @@ -16,7 +16,7 @@ SubDirHdrs [ FDirName / boot home config include ] ; } -Addon POP3 : mail_daemon inbound_protocols : +Addon POP3 : MessageIO.cpp pop3.cpp SimpleMailProtocol.cpp Modified: haiku/trunk/src/add-ons/mail_daemon/outbound_filters/fortune/Jamfile =================================================================== --- haiku/trunk/src/add-ons/mail_daemon/outbound_filters/fortune/Jamfile 2007-04-06 22:40:23 UTC (rev 20603) +++ haiku/trunk/src/add-ons/mail_daemon/outbound_filters/fortune/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) @@ -11,7 +11,7 @@ SubDirHdrs [ FDirName $(HAIKU_TOP) headers os add-ons mail_daemon ] ; -Addon Fortune : mail_daemon outbound_filters : +Addon Fortune : ConfigView.cpp filter.cpp ; Modified: haiku/trunk/src/add-ons/mail_daemon/outbound_protocols/smtp/Jamfile =================================================================== --- haiku/trunk/src/add-ons/mail_daemon/outbound_protocols/smtp/Jamfile 2007-04-06 22:40:23 UTC (rev 20603) +++ haiku/trunk/src/add-ons/mail_daemon/outbound_protocols/smtp/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) @@ -16,7 +16,7 @@ SubDirHdrs [ FDirName / boot home config include ] ; } -Addon SMTP : mail_daemon outbound_protocols : +Addon SMTP : smtp.cpp md5c.c ; Modified: haiku/trunk/src/add-ons/mail_daemon/system_filters/inbox/Jamfile =================================================================== --- haiku/trunk/src/add-ons/mail_daemon/system_filters/inbox/Jamfile 2007-04-06 22:40:23 UTC (rev 20603) +++ haiku/trunk/src/add-ons/mail_daemon/system_filters/inbox/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) @@ -11,7 +11,7 @@ SubDirHdrs [ FDirName $(HAIKU_TOP) headers os add-ons mail_daemon ] ; -Addon Inbox : mail_daemon system_filters : +Addon Inbox : filter.cpp ; LinkAgainst Inbox : Modified: haiku/trunk/src/add-ons/mail_daemon/system_filters/notifier/Jamfile =================================================================== --- haiku/trunk/src/add-ons/mail_daemon/system_filters/notifier/Jamfile 2007-04-06 22:40:23 UTC (rev 20603) +++ haiku/trunk/src/add-ons/mail_daemon/system_filters/notifier/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) @@ -11,7 +11,7 @@ SubDirHdrs [ FDirName $(HAIKU_TOP) headers os add-ons mail_daemon ] ; -Addon New\ Mail\ Notification : mail_daemon system_filters : +Addon New\ Mail\ Notification : filter.cpp ConfigView.cpp ; LinkAgainst New\ Mail\ Notification : Modified: haiku/trunk/src/add-ons/mail_daemon/system_filters/outbox/Jamfile =================================================================== --- haiku/trunk/src/add-ons/mail_daemon/system_filters/outbox/Jamfile 2007-04-06 22:40:23 UTC (rev 20603) +++ haiku/trunk/src/add-ons/mail_daemon/system_filters/outbox/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) @@ -11,7 +11,7 @@ SubDirHdrs [ FDirName $(HAIKU_TOP) headers os add-ons mail_daemon ] ; -Addon Outbox : mail_daemon system_filters : +Addon Outbox : filter.cpp ; LinkAgainst Outbox : Modified: haiku/trunk/src/add-ons/mail_daemon/system_filters/parser/Jamfile =================================================================== --- haiku/trunk/src/add-ons/mail_daemon/system_filters/parser/Jamfile 2007-04-06 22:40:23 UTC (rev 20603) +++ haiku/trunk/src/add-ons/mail_daemon/system_filters/parser/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) @@ -11,7 +11,7 @@ SubDirHdrs [ FDirName $(HAIKU_TOP) headers os add-ons mail_daemon ] ; -Addon Message\ Parser : mail_daemon system_filters : +Addon Message\ Parser : filter.cpp ; LinkAgainst Message\ Parser : Modified: haiku/trunk/src/add-ons/media/media-add-ons/demultiplexer/Jamfile =================================================================== --- haiku/trunk/src/add-ons/media/media-add-ons/demultiplexer/Jamfile 2007-04-06 22:40:23 UTC (rev 20603) +++ haiku/trunk/src/add-ons/media/media-add-ons/demultiplexer/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) @@ -2,11 +2,10 @@ UsePrivateHeaders demultiplexer ; -Addon demultiplexer.media_addon : media : +Addon demultiplexer.media_addon : MediaDemultiplexerNode.cpp MediaDemultiplexerAddOn.cpp MediaOutputInfo.cpp misc.cpp - : true : be media ; Modified: haiku/trunk/src/add-ons/media/media-add-ons/esound_sink/Jamfile =================================================================== --- haiku/trunk/src/add-ons/media/media-add-ons/esound_sink/Jamfile 2007-04-06 22:40:23 UTC (rev 20603) +++ haiku/trunk/src/add-ons/media/media-add-ons/esound_sink/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) @@ -6,11 +6,10 @@ SubDirC++Flags -fmultiple-symbol-spaces ; } -Addon ESDSink.media_addon : media : +Addon ESDSink.media_addon : ESDEndpoint.cpp ESDSinkAddOn.cpp ESDSinkNode.cpp - : false : be media network ; Modified: haiku/trunk/src/add-ons/media/media-add-ons/legacy/Jamfile =================================================================== --- haiku/trunk/src/add-ons/media/media-add-ons/legacy/Jamfile 2007-04-06 22:40:23 UTC (rev 20603) +++ haiku/trunk/src/add-ons/media/media-add-ons/legacy/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) @@ -2,11 +2,10 @@ UsePrivateHeaders media ; -Addon legacy.media_addon : media : +Addon legacy.media_addon : LegacyAudioConsumer.cpp LegacyAudioDevice.cpp LegacyAudioProducer.cpp LegacyMediaAddOn.cpp - : false : be media ; Modified: haiku/trunk/src/add-ons/media/media-add-ons/mixer/Jamfile =================================================================== --- haiku/trunk/src/add-ons/media/media-add-ons/mixer/Jamfile 2007-04-06 22:40:23 UTC (rev 20603) +++ haiku/trunk/src/add-ons/media/media-add-ons/mixer/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) @@ -2,7 +2,7 @@ SetSubDirSupportedPlatformsBeOSCompatible ; -Addon mixer.media_addon : media : +Addon mixer.media_addon : AudioMixer.cpp ByteSwap.cpp MixerAddOn.cpp @@ -12,7 +12,6 @@ MixerSettings.cpp MixerUtils.cpp Resampler.cpp - : false : be media ; Modified: haiku/trunk/src/add-ons/media/media-add-ons/multi_audio/Jamfile =================================================================== --- haiku/trunk/src/add-ons/media/media-add-ons/multi_audio/Jamfile 2007-04-06 22:40:23 UTC (rev 20603) +++ haiku/trunk/src/add-ons/media/media-add-ons/multi_audio/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) @@ -6,11 +6,10 @@ SubDirC++Flags -fmultiple-symbol-spaces ; } -Addon hmulti_audio.media_addon : media : +Addon hmulti_audio.media_addon : MultiAudioAddOn.cpp MultiAudioDevice.cpp MultiAudioNode.cpp - : false : be media ; Modified: haiku/trunk/src/add-ons/media/media-add-ons/radeon/Jamfile =================================================================== --- haiku/trunk/src/add-ons/media/media-add-ons/radeon/Jamfile 2007-04-06 22:40:23 UTC (rev 20603) +++ haiku/trunk/src/add-ons/media/media-add-ons/radeon/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) @@ -4,7 +4,7 @@ UsePrivateHeaders [ FDirName graphics common ] ; UsePrivateHeaders [ FDirName graphics radeon ] ; -Addon radeon.media_addon : media : +Addon radeon.media_addon : RadeonAddOn.cpp RadeonProducer.cpp CC.cpp Modified: haiku/trunk/src/add-ons/media/media-add-ons/reader/Jamfile =================================================================== --- haiku/trunk/src/add-ons/media/media-add-ons/reader/Jamfile 2007-04-06 22:40:23 UTC (rev 20603) +++ haiku/trunk/src/add-ons/media/media-add-ons/reader/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) @@ -2,13 +2,12 @@ UsePrivateHeaders media ; -Addon reader.media_addon : media : +Addon reader.media_addon : ../AbstractFileInterfaceNode.cpp ../AbstractFileInterfaceAddOn.cpp MediaReader.cpp MediaReaderAddOn.cpp misc.cpp + : be media : true ; - -LinkAgainst reader.media_addon : be media ; Modified: haiku/trunk/src/add-ons/media/media-add-ons/tone_producer_demo/Jamfile =================================================================== --- haiku/trunk/src/add-ons/media/media-add-ons/tone_producer_demo/Jamfile 2007-04-06 22:40:23 UTC (rev 20603) +++ haiku/trunk/src/add-ons/media/media-add-ons/tone_producer_demo/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) @@ -1,8 +1,7 @@ SubDir HAIKU_TOP src add-ons media media-add-ons tone_producer_demo ; -Addon tone_producer_demo.media_addon : media : +Addon tone_producer_demo.media_addon : ToneProducerAddOn.cpp ToneProducer.cpp + : be media ; - -LinkAgainst tone_producer_demo.media_addon : be media ; Modified: haiku/trunk/src/add-ons/media/media-add-ons/usb_vision/Jamfile =================================================================== --- haiku/trunk/src/add-ons/media/media-add-ons/usb_vision/Jamfile 2007-04-06 22:40:23 UTC (rev 20603) +++ haiku/trunk/src/add-ons/media/media-add-ons/usb_vision/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) @@ -4,10 +4,9 @@ UsePrivateHeaders usb_vision ; -Addon usb_vision.media_addon : media : +Addon usb_vision.media_addon : AddOn.cpp Producer.cpp TunerLocale.cpp + : be media $(TARGET_LIBSTDC++) ; - -LinkAgainst usb_vision.media_addon : be media $(TARGET_LIBSTDC++) ; Modified: haiku/trunk/src/add-ons/media/media-add-ons/usb_webcam/Jamfile =================================================================== --- haiku/trunk/src/add-ons/media/media-add-ons/usb_webcam/Jamfile 2007-04-06 22:40:23 UTC (rev 20603) +++ haiku/trunk/src/add-ons/media/media-add-ons/usb_webcam/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) @@ -64,7 +64,7 @@ USBWebcamHeaderGen [ FGristFiles CamInternalColorSpaceTransforms.h ] : B_WEBCAM_DECLARE_CSTRANSFORM : $(csTransformsSources) ; -Addon usb_webcam.media_addon : media : +Addon usb_webcam.media_addon : $(addonSources) $(csTransformsSources) $(sensorsSources) @@ -79,10 +79,9 @@ CamRoster.cpp CamSensor.cpp CamStreamingDeframer.cpp + : be media $(usbKitLibraryName) ; -LinkAgainst usb_webcam.media_addon : be media $(usbKitLibraryName) ; - # force dependancies Includes [ FGristFiles CamRoster.cpp ] : [ FGristFiles CamInternalAddons.h ] ; Includes [ FGristFiles CamDevice.cpp ] : [ FGristFiles CamInternalSensors.h ] ; Modified: haiku/trunk/src/add-ons/media/media-add-ons/video_producer_demo/Jamfile =================================================================== --- haiku/trunk/src/add-ons/media/media-add-ons/video_producer_demo/Jamfile 2007-04-06 22:40:23 UTC (rev 20603) +++ haiku/trunk/src/add-ons/media/media-add-ons/video_producer_demo/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) @@ -1,8 +1,7 @@ SubDir HAIKU_TOP src add-ons media media-add-ons video_producer_demo ; -Addon video_producer_demo.media_addon : media : +Addon video_producer_demo.media_addon : AddOn.cpp Producer.cpp + : be media ; - -LinkAgainst video_producer_demo.media_addon : be media ; Modified: haiku/trunk/src/add-ons/media/media-add-ons/writer/Jamfile =================================================================== --- haiku/trunk/src/add-ons/media/media-add-ons/writer/Jamfile 2007-04-06 22:40:23 UTC (rev 20603) +++ haiku/trunk/src/add-ons/media/media-add-ons/writer/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) @@ -2,13 +2,12 @@ UsePrivateHeaders media ; -Addon writer.media_addon : media : +Addon writer.media_addon : ../AbstractFileInterfaceNode.cpp ../AbstractFileInterfaceAddOn.cpp MediaWriter.cpp MediaWriterAddOn.cpp misc.cpp + : be media : true ; - -LinkAgainst writer.media_addon : be media ; [... truncated: 1427 lines follow ...] From bonefish at mail.berlios.de Sat Apr 7 03:42:49 2007 From: bonefish at mail.berlios.de (bonefish at BerliOS) Date: Sat, 7 Apr 2007 03:42:49 +0200 Subject: [Haiku-commits] r20605 - in haiku/trunk: build/jam src/add-ons/translators/bmp src/add-ons/translators/gif src/add-ons/translators/ico src/add-ons/translators/jpeg src/add-ons/translators/jpeg2000 src/add-ons/translators/libtiff src/add-ons/translators/png src/add-ons/translators/ppm src/add-ons/translators/raw src/add-ons/translators/rtf src/add-ons/translators/sgi src/add-ons/translators/stxt src/add-ons/translators/tga src/add-ons/translators/tiff src/add-ons/translators/wonderbrush Message-ID: <200704070142.l371gnef011105@sheep.berlios.de> Author: bonefish Date: 2007-04-07 03:42:47 +0200 (Sat, 07 Apr 2007) New Revision: 20605 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20605&view=rev Modified: haiku/trunk/build/jam/MainBuildRules haiku/trunk/src/add-ons/translators/bmp/Jamfile haiku/trunk/src/add-ons/translators/gif/Jamfile haiku/trunk/src/add-ons/translators/ico/Jamfile haiku/trunk/src/add-ons/translators/jpeg/Jamfile haiku/trunk/src/add-ons/translators/jpeg2000/Jamfile haiku/trunk/src/add-ons/translators/libtiff/Jamfile haiku/trunk/src/add-ons/translators/png/Jamfile haiku/trunk/src/add-ons/translators/ppm/Jamfile haiku/trunk/src/add-ons/translators/raw/Jamfile haiku/trunk/src/add-ons/translators/rtf/Jamfile haiku/trunk/src/add-ons/translators/sgi/Jamfile haiku/trunk/src/add-ons/translators/stxt/Jamfile haiku/trunk/src/add-ons/translators/tga/Jamfile haiku/trunk/src/add-ons/translators/tiff/Jamfile haiku/trunk/src/add-ons/translators/wonderbrush/Jamfile Log: Added an "isExecutable" parameter to the Translator rule. All translators pass "true" (was used before), but I suppose most of them don't really need it. Modified: haiku/trunk/build/jam/MainBuildRules =================================================================== --- haiku/trunk/build/jam/MainBuildRules 2007-04-07 01:27:19 UTC (rev 20604) +++ haiku/trunk/build/jam/MainBuildRules 2007-04-07 01:42:47 UTC (rev 20605) @@ -122,12 +122,10 @@ AddSharedObjectGlueCode $(target) : $(isExecutable) ; } -rule Translator target : sources : libraries +rule Translator target : sources : libraries : isExecutable { - # Translator : : ; - # TODO: Although they currently all are, translators don't need to be - # executable. Introduce a flag as for Addon. - Addon $(target) : $(sources) : $(libraries) : true ; + # Translator : : : ; + Addon $(target) : $(sources) : $(libraries) : $(isExecutable) ; } rule ScreenSaver target : sources : libraries Modified: haiku/trunk/src/add-ons/translators/bmp/Jamfile =================================================================== --- haiku/trunk/src/add-ons/translators/bmp/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) +++ haiku/trunk/src/add-ons/translators/bmp/Jamfile 2007-04-07 01:42:47 UTC (rev 20605) @@ -17,6 +17,7 @@ BMPView.cpp : be translation + : true ; Package haiku-translationkit-cvs : Modified: haiku/trunk/src/add-ons/translators/gif/Jamfile =================================================================== --- haiku/trunk/src/add-ons/translators/gif/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) +++ haiku/trunk/src/add-ons/translators/gif/Jamfile 2007-04-07 01:42:47 UTC (rev 20605) @@ -17,6 +17,7 @@ SFHash.cpp : be translation + : true ; Package haiku-translationkit-cvs : Modified: haiku/trunk/src/add-ons/translators/ico/Jamfile =================================================================== --- haiku/trunk/src/add-ons/translators/ico/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) +++ haiku/trunk/src/add-ons/translators/ico/Jamfile 2007-04-07 01:42:47 UTC (rev 20605) @@ -18,6 +18,7 @@ TranslatorWindow.cpp : be translation + : true ; Package haiku-translationkit-cvs : Modified: haiku/trunk/src/add-ons/translators/jpeg/Jamfile =================================================================== --- haiku/trunk/src/add-ons/translators/jpeg/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) +++ haiku/trunk/src/add-ons/translators/jpeg/Jamfile 2007-04-07 01:42:47 UTC (rev 20605) @@ -87,6 +87,7 @@ $(jpeg_files) : be translation + : true ; Package haiku-translationkit-cvs : Modified: haiku/trunk/src/add-ons/translators/jpeg2000/Jamfile =================================================================== --- haiku/trunk/src/add-ons/translators/jpeg2000/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) +++ haiku/trunk/src/add-ons/translators/jpeg2000/Jamfile 2007-04-07 01:42:47 UTC (rev 20605) @@ -67,6 +67,7 @@ $(jasper_files) : be translation + : true ; Package haiku-translationkit-cvs : Modified: haiku/trunk/src/add-ons/translators/libtiff/Jamfile =================================================================== --- haiku/trunk/src/add-ons/translators/libtiff/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) +++ haiku/trunk/src/add-ons/translators/libtiff/Jamfile 2007-04-07 01:42:47 UTC (rev 20605) @@ -60,7 +60,8 @@ TIFFTranslator.cpp TIFFView.cpp - : be translation z + : be translation z + : true ; Package haiku-translationkit-cvs : Modified: haiku/trunk/src/add-ons/translators/png/Jamfile =================================================================== --- haiku/trunk/src/add-ons/translators/png/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) +++ haiku/trunk/src/add-ons/translators/png/Jamfile 2007-04-07 01:42:47 UTC (rev 20605) @@ -20,6 +20,7 @@ PNGView.cpp : be translation libpng.a z + : true ; Package haiku-translationkit-cvs : Modified: haiku/trunk/src/add-ons/translators/ppm/Jamfile =================================================================== --- haiku/trunk/src/add-ons/translators/ppm/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) +++ haiku/trunk/src/add-ons/translators/ppm/Jamfile 2007-04-07 01:42:47 UTC (rev 20605) @@ -5,6 +5,7 @@ Translator PPMTranslator : PPMMain.cpp PPMTranslator.cpp colorspace.cpp : be translation + : true ; Package haiku-translationkit-cvs : Modified: haiku/trunk/src/add-ons/translators/raw/Jamfile =================================================================== --- haiku/trunk/src/add-ons/translators/raw/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) +++ haiku/trunk/src/add-ons/translators/raw/Jamfile 2007-04-07 01:42:47 UTC (rev 20605) @@ -18,6 +18,7 @@ TranslatorWindow.cpp : be translation + : true ; Package haiku-translationkit-cvs : Modified: haiku/trunk/src/add-ons/translators/rtf/Jamfile =================================================================== --- haiku/trunk/src/add-ons/translators/rtf/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) +++ haiku/trunk/src/add-ons/translators/rtf/Jamfile 2007-04-07 01:42:47 UTC (rev 20605) @@ -21,6 +21,7 @@ TranslatorWindow.cpp : be translation + : true ; Package haiku-translationkit-cvs : Modified: haiku/trunk/src/add-ons/translators/sgi/Jamfile =================================================================== --- haiku/trunk/src/add-ons/translators/sgi/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) +++ haiku/trunk/src/add-ons/translators/sgi/Jamfile 2007-04-07 01:42:47 UTC (rev 20605) @@ -18,6 +18,7 @@ SGIView.cpp : be translation + : true ; Package haiku-translationkit-cvs : Modified: haiku/trunk/src/add-ons/translators/stxt/Jamfile =================================================================== --- haiku/trunk/src/add-ons/translators/stxt/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) +++ haiku/trunk/src/add-ons/translators/stxt/Jamfile 2007-04-07 01:42:47 UTC (rev 20605) @@ -21,6 +21,7 @@ STXTView.cpp : be translation libtextencoding.so + : true ; Package haiku-translationkit-cvs : Modified: haiku/trunk/src/add-ons/translators/tga/Jamfile =================================================================== --- haiku/trunk/src/add-ons/translators/tga/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) +++ haiku/trunk/src/add-ons/translators/tga/Jamfile 2007-04-07 01:42:47 UTC (rev 20605) @@ -18,6 +18,7 @@ TGAView.cpp : be translation + : true ; Package haiku-translationkit-cvs : Modified: haiku/trunk/src/add-ons/translators/tiff/Jamfile =================================================================== --- haiku/trunk/src/add-ons/translators/tiff/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) +++ haiku/trunk/src/add-ons/translators/tiff/Jamfile 2007-04-07 01:42:47 UTC (rev 20605) @@ -18,4 +18,5 @@ TIFFWindow.cpp : be translation + : true ; Modified: haiku/trunk/src/add-ons/translators/wonderbrush/Jamfile =================================================================== --- haiku/trunk/src/add-ons/translators/wonderbrush/Jamfile 2007-04-07 01:27:19 UTC (rev 20604) +++ haiku/trunk/src/add-ons/translators/wonderbrush/Jamfile 2007-04-07 01:42:47 UTC (rev 20605) @@ -30,6 +30,7 @@ lab_convert.cpp : be translation z + : true ; Package haiku-translationkit-cvs : From hugosantos at gmail.com Sat Apr 7 13:16:24 2007 From: hugosantos at gmail.com (Hugo Santos) Date: Sat, 7 Apr 2007 12:16:24 +0100 Subject: [Haiku-commits] r20590 - in haiku/trunk/src/add-ons/kernel/network/protocols: ipv4 udp In-Reply-To: <20070406221747.1240.2@stippis.mshome.net> References: <729471565-BeMail@laptop> <20070406221747.1240.2@stippis.mshome.net> Message-ID: <9c46321e0704070416q23c9d9e8uadace05acc9d5b7f@mail.gmail.com> Although i've been fixing some small bugs here and there, i didn't change enough of UDP to have a difference in NFS' performance. I would attribute this success to Oliver. :-) Hugo On 4/6/07, Stephan Assmus wrote: > > On 2007-04-06 at 17:57:01 [+0200], Fran?ois Revol wrote: > > Indeed it now works nice: > > http://revolf.free.fr/beos/shots/shot_haiku_nfs_002_working.png > > > > No more hangup after 20 seconds, playing the mp3 file did work :) > > > > Just left some minor issues with paths (probably non working > > get_vnode_name). > > > > Congrats on UDP :) > > Pretty neat! :-) Hugo rocks! > > Best regards, > -Stephan > _______________________________________________ > Haiku-commits mailing list > Haiku-commits at lists.berlios.de > https://lists.berlios.de/mailman/listinfo/haiku-commits > From bonefish at mail.berlios.de Sat Apr 7 21:01:22 2007 From: bonefish at mail.berlios.de (bonefish at BerliOS) Date: Sat, 7 Apr 2007 21:01:22 +0200 Subject: [Haiku-commits] r20606 - haiku/trunk/src/build/libroot Message-ID: <200704071901.l37J1McI014294@sheep.berlios.de> Author: bonefish Date: 2007-04-07 21:01:21 +0200 (Sat, 07 Apr 2007) New Revision: 20606 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20606&view=rev Added: haiku/trunk/src/build/libroot/fs_descriptors.cpp haiku/trunk/src/build/libroot/fs_descriptors.h haiku/trunk/src/build/libroot/fs_impl.h Removed: haiku/trunk/src/build/libroot/fs_attr_impl.h Modified: haiku/trunk/src/build/libroot/Jamfile haiku/trunk/src/build/libroot/fs.cpp haiku/trunk/src/build/libroot/fs_attr.cpp Log: libroot_build.so: * Reorganized sources a bit: - The descriptor support is in a separate file now. - Disentangled the attribute support from the other stuff. * Removed broken xattr use for attribute support. Modified: haiku/trunk/src/build/libroot/Jamfile =================================================================== --- haiku/trunk/src/build/libroot/Jamfile 2007-04-07 01:42:47 UTC (rev 20605) +++ haiku/trunk/src/build/libroot/Jamfile 2007-04-07 19:01:21 UTC (rev 20606) @@ -26,6 +26,7 @@ errors.cpp fs.cpp fs_attr.cpp + fs_descriptors.cpp misc.cpp sem.cpp thread.cpp Modified: haiku/trunk/src/build/libroot/fs.cpp =================================================================== --- haiku/trunk/src/build/libroot/fs.cpp 2007-04-07 01:42:47 UTC (rev 20605) +++ haiku/trunk/src/build/libroot/fs.cpp 2007-04-07 19:01:21 UTC (rev 20606) @@ -1,6 +1,8 @@ #include +#include "fs_impl.h" + #include #include #include @@ -17,296 +19,21 @@ #include // for B_STAT_* flags #include -#include "fs_attr_impl.h" +#include "fs_descriptors.h" #include "NodeRef.h" using namespace std; using namespace BPrivate; -static const int kVirtualDescriptorStart = 10000; -static status_t get_path(dev_t device, ino_t node, const char *name, string &path); +static status_t get_path(dev_t device, ino_t node, const char *name, + string &path); -namespace BPrivate { - class Descriptor; -} -using namespace BPrivate; -typedef map DescriptorMap; -static DescriptorMap sDescriptors; - -namespace BPrivate { - -// Descriptor -struct Descriptor { - int fd; - - virtual ~Descriptor() - { - } - - virtual status_t Close() = 0; - virtual status_t Dup(Descriptor *&clone) = 0; - virtual status_t GetStat(bool traverseLink, struct stat *st) = 0; - - virtual status_t GetNodeRef(NodeRef &ref) - { - struct stat st; - status_t error = GetStat(false, &st); - if (error != B_OK) - return error; - - ref = NodeRef(st); - - return B_OK; - } -}; - -// FileDescriptor -struct FileDescriptor : Descriptor { - FileDescriptor(int fd) - { - this->fd = fd; - } - - virtual ~FileDescriptor() - { - Close(); - } - - virtual status_t Close() - { - if (fd >= 0) { - int oldFD = fd; - fd = -1; - if (close(oldFD) < 0) - return errno; - } - - return B_OK; - } - - virtual status_t Dup(Descriptor *&clone) - { - int dupFD = dup(fd); - if (dupFD < 0) - return errno; - - clone = new FileDescriptor(dupFD); - return B_OK; - } - - virtual status_t GetStat(bool traverseLink, struct stat *st) - { - if (fstat(fd, st) < 0) - return errno; - return B_OK; - } -}; - -// DirectoryDescriptor -struct DirectoryDescriptor : Descriptor { - DIR *dir; - NodeRef ref; - - DirectoryDescriptor(DIR *dir, const NodeRef &ref) - { - this->dir = dir; - this->ref = ref; - } - - virtual ~DirectoryDescriptor() - { - Close(); - } - - virtual status_t Close() - { - if (dir) { - DIR *oldDir = dir; - dir = NULL; - if (closedir(oldDir) < 0) - return errno; - } - - return B_OK; - } - - virtual status_t Dup(Descriptor *&clone) - { - string path; - status_t error = get_path(fd, NULL, path); - if (error != B_OK) - return error; - - DIR *dupDir = opendir(path.c_str()); - if (!dupDir) - return errno; - - clone = new DirectoryDescriptor(dupDir, ref); - return B_OK; - } - - virtual status_t GetStat(bool traverseLink, struct stat *st) - { - // get a usable path - string realPath; - status_t error = get_path(fd, NULL, realPath); - if (error != B_OK) - return error; - - // stat - int result; - result = stat(realPath.c_str(), st); - - if (result < 0) - return errno; - - return B_OK; - } - - virtual status_t GetNodeRef(NodeRef &ref) - { - ref = this->ref; - - return B_OK; - } -}; - -// SymlinkDescriptor -struct SymlinkDescriptor : Descriptor { - string path; - - SymlinkDescriptor(const char *path) - { - this->path = path; - } - - virtual status_t Close() - { - return B_OK; - } - - virtual status_t Dup(Descriptor *&clone) - { - clone = new SymlinkDescriptor(path.c_str()); - return B_OK; - } - - virtual status_t GetStat(bool traverseLink, struct stat *st) - { - // stat - int result; - if (traverseLink) - result = stat(path.c_str(), st); - else - result = lstat(path.c_str(), st); - - if (result < 0) - return errno; - - return B_OK; - } -}; - -// AttrDirDescriptor -struct AttrDirDescriptor : DirectoryDescriptor { - - AttrDirDescriptor(DIR *dir, const NodeRef &ref) - : DirectoryDescriptor(dir, ref) - { - } - - virtual ~AttrDirDescriptor() - { - Close(); - } - - virtual status_t Close() - { - if (dir) { - DIR *oldDir = dir; - dir = NULL; - if (fs_close_attr_dir(oldDir) < 0) - return errno; - } - - return B_OK; - } - - virtual status_t Dup(Descriptor *&clone) - { - // we don't allow dup()int attr dir descriptors - return B_FILE_ERROR; - } - - virtual status_t GetStat(bool traverseLink, struct stat *st) - { - // we don't allow stat()int attr dir descriptors - return B_FILE_ERROR; - } - - virtual status_t GetNodeRef(NodeRef &ref) - { - ref = this->ref; - - return B_OK; - } -}; - -} // namespace BPrivate - -// get_descriptor -static Descriptor * -get_descriptor(int fd) -{ - DescriptorMap::iterator it = sDescriptors.find(fd); - if (it == sDescriptors.end()) - return NULL; - return it->second; -} - -static int -add_descriptor(Descriptor *descriptor) -{ - int fd = -1; - if (FileDescriptor *file = dynamic_cast(descriptor)) { - fd = file->fd; - } else { - // find a free slot - for (fd = kVirtualDescriptorStart; - sDescriptors.find(fd) != sDescriptors.end(); - fd++) { - } - } - - sDescriptors[fd] = descriptor; - descriptor->fd = fd; - - return fd; -} - -// delete_descriptor -static status_t -delete_descriptor(int fd) -{ - DescriptorMap::iterator it = sDescriptors.find(fd); - if (it == sDescriptors.end()) - return B_FILE_ERROR; - - status_t error = it->second->Close(); - delete it->second; - sDescriptors.erase(it); - - return error; -} - - -// #pragma mark - - // find_dir_entry static status_t -find_dir_entry(DIR *dir, const char *path, NodeRef ref, string &name, bool skipDot) +find_dir_entry(DIR *dir, const char *path, NodeRef ref, string &name, + bool skipDot) { // find the entry bool found = false; @@ -1195,125 +922,6 @@ // #pragma mark - -// _kern_open_attr_dir -int -_kern_open_attr_dir(int fd, const char *path) -{ - // get node ref for the node - struct stat st; - status_t error = _kern_read_stat(fd, path, false, &st, - sizeof(struct stat)); - if (error != B_OK) { - errno = error; - return -1; - } - NodeRef ref(st); - - // If a path was given, get a usable path. - string realPath; - if (path) { - error = get_path(fd, path, realPath); - if (error != B_OK) - return error; - } - - // open the attr dir - DIR *dir = open_attr_dir(ref, (path ? realPath.c_str() : NULL), - (path ? -1 : fd)); - if (!dir) - return errno; - - // create descriptor - AttrDirDescriptor *descriptor = new AttrDirDescriptor(dir, ref); - return add_descriptor(descriptor); -} - -// get_attribute_path -static status_t -get_attribute_path(int fd, const char *attribute, string &attrPath, - string &typePath) -{ - // stat the file to get a NodeRef - struct stat st; - status_t error = _kern_read_stat(fd, NULL, false, &st, sizeof(st)); - if (error != B_OK) - return error; - NodeRef ref(st); - - // Try to get a path. If we can't get a path, this is must be a "real" - // (i.e. system) file descriptor, which is just as well. - string path; - bool pathValid = (get_path(fd, NULL, path) == B_OK); - - // get the attribute path - return get_attribute_path(ref, (pathValid ? path.c_str() : NULL), - (pathValid ? -1 : fd), attribute, attrPath, typePath); -} - -// _kern_rename_attr -status_t -_kern_rename_attr(int fromFile, const char *fromName, int toFile, - const char *toName) -{ - if (!fromName || !toName) - return B_BAD_VALUE; - - // get the attribute paths - string fromAttrPath; - string fromTypePath; - status_t error = get_attribute_path(fromFile, fromName, fromAttrPath, - fromTypePath); - if (error != B_OK) - return error; - - string toAttrPath; - string toTypePath; - error = get_attribute_path(toFile, toName, toAttrPath, toTypePath); - if (error != B_OK) - return error; - - // rename the attribute and type files - if (rename(fromAttrPath.c_str(), toAttrPath.c_str()) < 0) - return errno; - - if (rename(fromTypePath.c_str(), toTypePath.c_str()) < 0) { - // renaming the type file failed: try to rename back the attribute file - error = errno; - - rename(toAttrPath.c_str(), fromAttrPath.c_str()); - - return error; - } - - return B_OK; -} - -// _kern_remove_attr -status_t -_kern_remove_attr(int fd, const char *name) -{ - if (!name) - return B_BAD_VALUE; - - // get the attribute path - string attrPath; - string typePath; - status_t error = get_attribute_path(fd, name, attrPath, typePath); - if (error != B_OK) - return error; - - // remove the attribute - if (unlink(attrPath.c_str()) < 0) - return errno; - - unlink(typePath.c_str()); - - return B_OK; -} - - -// #pragma mark - - // read_pos ssize_t read_pos(int fd, off_t pos, void *buffer, size_t bufferSize) Modified: haiku/trunk/src/build/libroot/fs_attr.cpp =================================================================== --- haiku/trunk/src/build/libroot/fs_attr.cpp 2007-04-07 01:42:47 UTC (rev 20605) +++ haiku/trunk/src/build/libroot/fs_attr.cpp 2007-04-07 19:01:21 UTC (rev 20606) @@ -9,11 +9,6 @@ # include #endif -// Defined, if the host platform has extended attribute support. -// Unfortunately I don't seem to have extended attribute support under -// SuSE Linux 9.2 (kernel 2.6.8-...) with ReiserFS 3.6. -//#define HAS_EXTENDED_ATTRIBUTE_SUPPORT 1 - #include #include #include @@ -26,14 +21,10 @@ #include -#include "fs_attr_impl.h" +#include "fs_impl.h" +#include "fs_descriptors.h" -#ifdef HAS_EXTENDED_ATTRIBUTE_SUPPORT -#include -static const char *kAttributeDirMarkAttributeName = "_has_haiku_attr_dir"; -#endif - using namespace std; using namespace BPrivate; @@ -133,87 +124,6 @@ return attrDirPath; } -// has_attribute_dir_mark -static bool -has_attribute_dir_mark(const char *path, int fd) -{ - #ifdef HAS_EXTENDED_ATTRIBUTE_SUPPORT - - uint8 value; - if (path) { - return (lgetxattr(path, kAttributeDirMarkAttributeName, &value, 1) - > 0); - } else { - return (fgetxattr(fd, kAttributeDirMarkAttributeName, &value, 1) - > 0); - } - - #else // !HAS_EXTENDED_ATTRIBUTE_SUPPORT - - // No extended attribute support. We can't mark the file and thus - // have to handle it as marked. - return true; - - #endif -} - -// set_attribute_dir_mark -static status_t -set_attribute_dir_mark(const char *path, int fd) -{ - #ifdef HAS_EXTENDED_ATTRIBUTE_SUPPORT - - uint8 value = 1; - if (path) { - if (lsetxattr(path, kAttributeDirMarkAttributeName, &value, 1, 0) - < 0) { - fprintf(stderr, "set_attribute_dir_mark(): lsetxattr() " - "failed on \"%s\"\n", path); - return errno; - } - } else { - if (fsetxattr(fd, kAttributeDirMarkAttributeName, &value, 1, 0) - < 0) { - fprintf(stderr, "set_attribute_dir_mark(): fsetxattr() " - "failed on FD \"%d\"\n", fd); - return errno; - } - } - - #endif - - return B_OK; -} - -// empty_attribute_dir -static status_t -empty_attribute_dir(const char *path) -{ - DIR *dir = opendir(path); - if (!dir) - return errno; - - while (dirent *entry = readdir(dir)) { - if (strcmp(entry->d_name, ".") == 0 || strcmp(entry->d_name, "..") == 0) - continue; - - string entryPath(path); - entryPath += '/'; - entryPath += entry->d_name; - - // We assume the attribute dir contains files only (we only create - // files) and thus use unlink(). - if (unlink(entryPath.c_str()) < 0) { - status_t error = errno; - closedir(dir); - return error; - } - } - - closedir(dir); - return B_OK; -} - // ensure_attribute_dir_exists static status_t ensure_attribute_dir_exists(NodeRef ref, const char *path, int fd) @@ -235,37 +145,19 @@ return B_FILE_ERROR; } - // already exists: Check whether the file is marked. If not, this - // is a stale attribute directory from a deleted node that had the - // same node ID as this one. - if (has_attribute_dir_mark(path, fd)) - return B_OK; - - // empty the attribute dir - error = empty_attribute_dir(attrDirPath.c_str()); - if (error != B_OK) { - fprintf(stderr, "ensure_attribute_dir_exists(): Attribute " - "directory for node %lld exists, the node has no mark, and " - "emptying the attribute directory failed\n", - ref.node); - return error; - } - - // mark the file - return set_attribute_dir_mark(path, fd); + return B_OK; } // doesn't exist yet: create it if (mkdir(attrDirPath.c_str(), S_IRWXU | S_IRWXG | S_IRWXO) < 0) return errno; - // mark the file - return set_attribute_dir_mark(path, fd); + return B_OK; } // open_attr_dir -DIR * -BPrivate::open_attr_dir(NodeRef ref, const char *path, int fd) +static DIR * +open_attr_dir(NodeRef ref, const char *path, int fd) { // make sure the directory exists status_t error = ensure_attribute_dir_exists(ref, path, fd); @@ -280,8 +172,8 @@ } // get_attribute_path -status_t -BPrivate::get_attribute_path(NodeRef ref, const char *path, int fd, +static status_t +get_attribute_path(NodeRef ref, const char *path, int fd, const char *attribute, string &attrPath, string &typePath) { if (!attribute || strlen(attribute) == 0) @@ -317,6 +209,37 @@ return get_attribute_path(ref, NULL, fd, attribute, attrPath, typePath); } + +#ifndef BUILDING_FS_SHELL + +// get_attribute_path_virtual_fd +static status_t +get_attribute_path_virtual_fd(int fd, const char *attribute, string &attrPath, + string &typePath) +{ + // stat the file to get a NodeRef + struct stat st; + status_t error = _kern_read_stat(fd, NULL, false, &st, sizeof(st)); + if (error != B_OK) + return error; + NodeRef ref(st); + + // Try to get a path. If we can't get a path, this is must be a "real" + // (i.e. system) file descriptor, which is just as well. + string path; + bool pathValid = (get_path(fd, NULL, path) == B_OK); + + // get the attribute path + return get_attribute_path(ref, (pathValid ? path.c_str() : NULL), + (pathValid ? -1 : fd), attribute, attrPath, typePath); +} + +#endif // ! BUILDING_FS_SHELL + + +// # pragma mark - Public API + + // fs_open_attr_dir DIR * fs_open_attr_dir(const char *path) @@ -586,3 +509,106 @@ return 0; } + +// #pragma mark - Private Syscalls + + +#ifndef BUILDING_FS_SHELL + +// _kern_open_attr_dir +int +_kern_open_attr_dir(int fd, const char *path) +{ + // get node ref for the node + struct stat st; + status_t error = _kern_read_stat(fd, path, false, &st, + sizeof(struct stat)); + if (error != B_OK) { + errno = error; + return -1; + } + NodeRef ref(st); + + // If a path was given, get a usable path. + string realPath; + if (path) { + error = get_path(fd, path, realPath); + if (error != B_OK) + return error; + } + + // open the attr dir + DIR *dir = open_attr_dir(ref, (path ? realPath.c_str() : NULL), + (path ? -1 : fd)); + if (!dir) + return errno; + + // create descriptor + AttrDirDescriptor *descriptor = new AttrDirDescriptor(dir, ref); + return add_descriptor(descriptor); +} + +// _kern_rename_attr +status_t +_kern_rename_attr(int fromFile, const char *fromName, int toFile, + const char *toName) +{ + if (!fromName || !toName) + return B_BAD_VALUE; + + // get the attribute paths + string fromAttrPath; + string fromTypePath; + status_t error = get_attribute_path_virtual_fd(fromFile, fromName, + fromAttrPath, fromTypePath); + if (error != B_OK) + return error; + + string toAttrPath; + string toTypePath; + error = get_attribute_path_virtual_fd(toFile, toName, toAttrPath, + toTypePath); + if (error != B_OK) + return error; + + // rename the attribute and type files + if (rename(fromAttrPath.c_str(), toAttrPath.c_str()) < 0) + return errno; + + if (rename(fromTypePath.c_str(), toTypePath.c_str()) < 0) { + // renaming the type file failed: try to rename back the attribute file + error = errno; + + rename(toAttrPath.c_str(), fromAttrPath.c_str()); + + return error; + } + + return B_OK; +} + +// _kern_remove_attr +status_t +_kern_remove_attr(int fd, const char *name) +{ + if (!name) + return B_BAD_VALUE; + + // get the attribute path + string attrPath; + string typePath; + status_t error = get_attribute_path_virtual_fd(fd, name, attrPath, + typePath); + if (error != B_OK) + return error; + + // remove the attribute + if (unlink(attrPath.c_str()) < 0) + return errno; + + unlink(typePath.c_str()); + + return B_OK; +} + +#endif // ! BUILDING_FS_SHELL Deleted: haiku/trunk/src/build/libroot/fs_attr_impl.h Added: haiku/trunk/src/build/libroot/fs_descriptors.cpp =================================================================== --- haiku/trunk/src/build/libroot/fs_descriptors.cpp 2007-04-07 01:42:47 UTC (rev 20605) +++ haiku/trunk/src/build/libroot/fs_descriptors.cpp 2007-04-07 19:01:21 UTC (rev 20606) @@ -0,0 +1,319 @@ + +#include + +#include "fs_descriptors.h" + +#include + +#include +#include + +#include + +#include "fs_impl.h" + +using std::map; + +static const int kVirtualDescriptorStart = 10000; + +typedef map DescriptorMap; +static DescriptorMap sDescriptors; + +namespace BPrivate { + + +// #pragma mark - Descriptor + + +// constructor +Descriptor::~Descriptor() +{ +} + +// GetNodeRef +status_t +Descriptor::GetNodeRef(NodeRef &ref) +{ + struct stat st; + status_t error = GetStat(false, &st); + if (error != B_OK) + return error; + + ref = NodeRef(st); + + return B_OK; +} + + +// #pragma mark - FileDescriptor + + +// constructor +FileDescriptor::FileDescriptor(int fd) +{ + this->fd = fd; +} + +// destructor +FileDescriptor::~FileDescriptor() +{ + Close(); +} + +// Close +status_t +FileDescriptor::Close() +{ + if (fd >= 0) { + int oldFD = fd; + fd = -1; + if (close(oldFD) < 0) + return errno; + } + + return B_OK; +} + +// Dup +status_t +FileDescriptor::Dup(Descriptor *&clone) +{ + int dupFD = dup(fd); + if (dupFD < 0) + return errno; + + clone = new FileDescriptor(dupFD); + return B_OK; +} + +// GetStat +status_t +FileDescriptor::GetStat(bool traverseLink, struct stat *st) +{ + if (fstat(fd, st) < 0) + return errno; + return B_OK; +} + + +// #pragma mark - DirectoryDescriptor + + +// constructor +DirectoryDescriptor::DirectoryDescriptor(DIR *dir, const NodeRef &ref) +{ + this->dir = dir; + this->ref = ref; +} + +// destructor +DirectoryDescriptor::~DirectoryDescriptor() +{ + Close(); +} + +// Close +status_t +DirectoryDescriptor::Close() +{ + if (dir) { + DIR *oldDir = dir; + dir = NULL; + if (closedir(oldDir) < 0) + return errno; + } + + return B_OK; +} + +// Dup +status_t +DirectoryDescriptor::Dup(Descriptor *&clone) +{ + string path; + status_t error = get_path(fd, NULL, path); + if (error != B_OK) + return error; + + DIR *dupDir = opendir(path.c_str()); + if (!dupDir) + return errno; + + clone = new DirectoryDescriptor(dupDir, ref); + return B_OK; +} + +// GetStat +status_t +DirectoryDescriptor::GetStat(bool traverseLink, struct stat *st) +{ + // get a usable path + string realPath; + status_t error = get_path(fd, NULL, realPath); + if (error != B_OK) + return error; + + // stat + int result; + result = stat(realPath.c_str(), st); + + if (result < 0) + return errno; + + return B_OK; +} + +// GetNodeRef +status_t +DirectoryDescriptor::GetNodeRef(NodeRef &ref) +{ + ref = this->ref; + + return B_OK; +} + + +// #pragma mark - SymlinkDescriptor + + +// constructor +SymlinkDescriptor::SymlinkDescriptor(const char *path) +{ + this->path = path; +} + +// Close +status_t +SymlinkDescriptor::Close() +{ + return B_OK; +} + +// Dup +status_t +SymlinkDescriptor::Dup(Descriptor *&clone) +{ + clone = new SymlinkDescriptor(path.c_str()); + return B_OK; +} + +// GetStat +status_t +SymlinkDescriptor::GetStat(bool traverseLink, struct stat *st) +{ + // stat + int result; + if (traverseLink) + result = stat(path.c_str(), st); + else + result = lstat(path.c_str(), st); + + if (result < 0) + return errno; + + return B_OK; +} + + +// #pragma mark - AttrDirDescriptor [... truncated: 217 lines follow ...] From bonefish at mail.berlios.de Sun Apr 8 04:01:09 2007 From: bonefish at mail.berlios.de (bonefish at BerliOS) Date: Sun, 8 Apr 2007 04:01:09 +0200 Subject: [Haiku-commits] r20607 - haiku/trunk/headers/build/os/support Message-ID: <200704080201.l38219n8003008@sheep.berlios.de> Author: bonefish Date: 2007-04-08 04:01:07 +0200 (Sun, 08 Apr 2007) New Revision: 20607 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20607&view=rev Modified: haiku/trunk/headers/build/os/support/Errors.h Log: Added ENOATTR. Modified: haiku/trunk/headers/build/os/support/Errors.h =================================================================== --- haiku/trunk/headers/build/os/support/Errors.h 2007-04-07 19:01:21 UTC (rev 20606) +++ haiku/trunk/headers/build/os/support/Errors.h 2007-04-08 02:01:07 UTC (rev 20607) @@ -224,6 +224,7 @@ #define HAIKU_ELOOP B_LINK_LIMIT #define HAIKU_ENOEXEC B_NOT_AN_EXECUTABLE #define HAIKU_EPIPE B_BUSTED_PIPE +#define HAIKU_ENOATTR B_ENTRY_NOT_FOUND #ifndef BUILDING_HAIKU_ERROR_MAPPER #undef E2BIG @@ -395,6 +396,7 @@ #define ELOOP HAIKU_ELOOP #define ENOEXEC HAIKU_ENOEXEC #define EPIPE HAIKU_EPIPE + #define ENOATTR HAIKU_ENOATTR #undef errno #define errno (*_haiku_build_errno()) From bonefish at mail.berlios.de Sun Apr 8 04:04:22 2007 From: bonefish at mail.berlios.de (bonefish at BerliOS) Date: Sun, 8 Apr 2007 04:04:22 +0200 Subject: [Haiku-commits] r20608 - haiku/trunk/src/build/libroot Message-ID: <200704080204.l3824MLp003202@sheep.berlios.de> Author: bonefish Date: 2007-04-08 04:04:21 +0200 (Sun, 08 Apr 2007) New Revision: 20608 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20608&view=rev Modified: haiku/trunk/src/build/libroot/errors.cpp Log: Assigning values to errno would not work; the next invocation would overwrite them with the host platform errno again. We do now track changes and use a hopefully reasonable strategy for updating the host errno. Modified: haiku/trunk/src/build/libroot/errors.cpp =================================================================== --- haiku/trunk/src/build/libroot/errors.cpp 2007-04-08 02:01:07 UTC (rev 20607) +++ haiku/trunk/src/build/libroot/errors.cpp 2007-04-08 02:04:21 UTC (rev 20608) @@ -159,8 +159,24 @@ int * _haiku_build_errno() { + static int previousErrno = 0; static int localErrno = 0; - localErrno = to_haiku_error(errno); + static int previousLocalErrno = 0; + + // If the localErrno has been changed and the real errno has not changed + // in the meantime, we update errno itself, so that the local update will + // be reflected. If errno has changed we always update localErrno. + int currentErrno = errno; + if (currentErrno == previousErrno) { + if (localErrno != previousLocalErrno) { + errno = previousErrno = to_host_error(localErrno); + previousLocalErrno = localErrno; + } + } else { + previousErrno = currentErrno; + previousLocalErrno = localErrno = to_haiku_error(errno); + } + return &localErrno; } From bonefish at mail.berlios.de Sun Apr 8 04:19:03 2007 From: bonefish at mail.berlios.de (bonefish at BerliOS) Date: Sun, 8 Apr 2007 04:19:03 +0200 Subject: [Haiku-commits] r20609 - in haiku/trunk: . build/jam src/build/libroot Message-ID: <200704080219.l382J3gv004277@sheep.berlios.de> Author: bonefish Date: 2007-04-08 04:19:01 +0200 (Sun, 08 Apr 2007) New Revision: 20609 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20609&view=rev Added: haiku/trunk/src/build/libroot/fs_attr_generic.cpp haiku/trunk/src/build/libroot/fs_attr_xattr.cpp Modified: haiku/trunk/build/jam/BuildSetup haiku/trunk/configure haiku/trunk/src/build/libroot/fs_attr.cpp haiku/trunk/src/build/libroot/fs_descriptors.cpp haiku/trunk/src/build/libroot/fs_descriptors.h Log: Under Linux it is now possible to emulate the BeOS attribute support via xattrs. It can be enabled with the configure switch "--use-xattr". Note that the amount of data stored in attributes may be limited by the used file system -- e.g. AFAIK ext3 has a limit of one block (usually 4 KB) for all attributes of a file, which might not suffice. XFS should be fine, as should ReiserFS 3.6 (or any FS which stores attributes in hidden files). Modified: haiku/trunk/build/jam/BuildSetup =================================================================== --- haiku/trunk/build/jam/BuildSetup 2007-04-08 02:04:21 UTC (rev 20608) +++ haiku/trunk/build/jam/BuildSetup 2007-04-08 02:19:01 UTC (rev 20609) @@ -482,6 +482,12 @@ HOST_DEFINES += _LARGEFILE_SOURCE _LARGEFILE64_SOURCE _FILE_OFFSET_BITS=64 ; + + # On Linux with xattr support we can use it for our attribute emulation, + # which is somewhat more robust. + if $(HAIKU_HOST_USE_XATTR) = 1 { + HOST_DEFINES += HAIKU_HOST_USE_XATTR ; + } } # define the executable MIME type Modified: haiku/trunk/configure =================================================================== --- haiku/trunk/configure 2007-04-08 02:04:21 UTC (rev 20608) +++ haiku/trunk/configure 2007-04-08 02:19:01 UTC (rev 20609) @@ -39,6 +39,10 @@ valid targets=r5,bone,dano,haiku --use-gcc-pipe Build with GCC option -pipe. Speeds up the build process, but uses more memory. + --use-xattr Use Linux xattr support for BeOS attribute + emulation. Warning: Make sure your file system + supports sufficient attribute sizes (4 KB per + file for all attributes won't suffice). environment variables: HAIKU_AR The static library archiver. Defaults to "ar". @@ -207,6 +211,7 @@ include_gpl_addons=0 target=haiku use_gcc_pipe=0 +use_xattr=0 crossToolsPrefix= buildCrossTools= buildCrossToolsScript="$sourceDir/build/scripts/build_cross_tools" @@ -248,6 +253,7 @@ --include-gpl-addons) include_gpl_addons=1; shift 1;; --target=*) target=`echo $1 | cut -d'=' -f2-`; shift 1;; --use-gcc-pipe) use_gcc_pipe=1; shift 1;; + --use-xattr) use_xattr=1; shift 1;; *) echo Invalid argument: \`$1\'; exit 1;; esac done @@ -318,9 +324,10 @@ TARGET_PLATFORM ?= "${target}" ; HOST_PLATFORM ?= "${buildPlatform}" ; -BOCHS_DEBUG_HACK ?= "${bochs_debug}" ; -INCLUDE_GPL_ADDONS ?= "${include_gpl_addons}" ; -HAIKU_USE_GCC_PIPE ?= "${use_gcc_pipe}" ; +BOCHS_DEBUG_HACK ?= "${bochs_debug}" ; +INCLUDE_GPL_ADDONS ?= "${include_gpl_addons}" ; +HAIKU_USE_GCC_PIPE ?= "${use_gcc_pipe}" ; +HAIKU_HOST_USE_XATTR ?= "${use_xattr}" ; HAIKU_GCC_RAW_VERSION ?= ${haikuGCCVersion} ; HAIKU_GCC_MACHINE ?= ${haikuGCCMachine} ; Modified: haiku/trunk/src/build/libroot/fs_attr.cpp =================================================================== --- haiku/trunk/src/build/libroot/fs_attr.cpp 2007-04-08 02:04:21 UTC (rev 20608) +++ haiku/trunk/src/build/libroot/fs_attr.cpp 2007-04-08 02:19:01 UTC (rev 20609) @@ -1,614 +1,5 @@ - -#ifdef BUILDING_FS_SHELL -# include "compat.h" -# define B_OK 0 -# define B_BAD_VALUE EINVAL -# define B_FILE_ERROR EBADF +#ifdef HAIKU_HOST_USE_XATTR +# include "fs_attr_xattr.cpp" #else -# include -# include +# include "fs_attr_generic.cpp" #endif - -#include -#include -#include -#include -#include -#include -#include - -#include - -#include - -#include "fs_impl.h" -#include "fs_descriptors.h" - - -using namespace std; -using namespace BPrivate; - -static const char *sAttributeDirBasePath = HAIKU_BUILD_ATTRIBUTES_DIR; - -// init_attribute_dir_base_dir -static status_t -init_attribute_dir_base_dir() -{ - static bool initialized = false; - static status_t initError; - - if (initialized) - return initError; - - // stat the dir - struct stat st; - initError = B_OK; - if (lstat(sAttributeDirBasePath, &st) == 0) { - if (!S_ISDIR(st.st_mode)) { - // the attribute dir base dir is no directory - fprintf(stderr, "init_attribute_dir_base_dir(): The Attribute " - "directory base directory exists, but is no directory!\n"); - initError = B_FILE_ERROR; - } - - } else { - // doesn't exist yet: create it - if (mkdir(sAttributeDirBasePath, S_IRWXU | S_IRWXG | S_IRWXO) < 0) - initError = errno; - } - - initialized = true; - return initError; -} - -// escape_attr_name -static string -escape_attr_name(const char *name) -{ - string escapedName("_"); - while (*name != '\0') { - // we replace '/' with "_s" and '_' with "__" - if (*name == '/') - escapedName += "_s"; - else if (*name == '_') - escapedName += "__"; - else - escapedName += *name; - - name++; - } - - return escapedName; -} - -// deescape_attr_name -static string -deescape_attr_name(const char *name) -{ - if (name[0] != '_') { - debugger("deescape_attr_name(): name doesn't start with '_'!\n"); - return "___"; - } - name++; - - string deescapedName; - while (*name != '\0') { - if (*name == '_') { - name++; - if (*name == 's') { - deescapedName += '/'; - } else if (*name == '_') { - deescapedName += '_'; - } else { - debugger("deescape_attr_name(): name contains invalid escaped " - "sequence!\n"); - name--; - } - } else - deescapedName += *name; - - name++; - } - - return deescapedName; -} - -// get_attribute_dir_path -static string -get_attribute_dir_path(NodeRef ref) -{ - string attrDirPath(sAttributeDirBasePath); - char buffer[32]; - sprintf(buffer, "/%lld", (int64)ref.node); - attrDirPath += buffer; - return attrDirPath; -} - -// ensure_attribute_dir_exists -static status_t -ensure_attribute_dir_exists(NodeRef ref, const char *path, int fd) -{ - // init the base directory here - status_t error = init_attribute_dir_base_dir(); - if (error != B_OK) - return error; - - // stat the dir - string attrDirPath(get_attribute_dir_path(ref)); - struct stat st; - if (lstat(attrDirPath.c_str(), &st) == 0) { - if (!S_ISDIR(st.st_mode)) { - // the attribute dir is no directory - fprintf(stderr, "ensure_attribute_dir_exists(): Attribute " - "directory for node %lld exists, but is no directory!\n", - ref.node); - return B_FILE_ERROR; - } - - return B_OK; - } - - // doesn't exist yet: create it - if (mkdir(attrDirPath.c_str(), S_IRWXU | S_IRWXG | S_IRWXO) < 0) - return errno; - - return B_OK; -} - -// open_attr_dir -static DIR * -open_attr_dir(NodeRef ref, const char *path, int fd) -{ - // make sure the directory exists - status_t error = ensure_attribute_dir_exists(ref, path, fd); - if (error != B_OK) { - errno = error; - return NULL; - } - - // open it - string dirPath(get_attribute_dir_path(ref)); - return opendir(dirPath.c_str()); -} - -// get_attribute_path -static status_t -get_attribute_path(NodeRef ref, const char *path, int fd, - const char *attribute, string &attrPath, string &typePath) -{ - if (!attribute || strlen(attribute) == 0) - return B_BAD_VALUE; - - // make sure the attribute dir for the node exits - status_t error = ensure_attribute_dir_exists(ref, path, fd); - if (error != B_OK) { - errno = error; - return -1; - } - - // construct the attribute path - attrPath = get_attribute_dir_path(ref) + '/'; - string attrName(escape_attr_name(attribute)); - typePath = attrPath + "t" + attrName; - attrPath += attrName; - - return B_OK; -} - -// get_attribute_path -static status_t -get_attribute_path(int fd, const char *attribute, string &attrPath, - string &typePath) -{ - // stat the file to get a NodeRef - struct stat st; - if (fstat(fd, &st) < 0) - return errno; - NodeRef ref(st); - - return get_attribute_path(ref, NULL, fd, attribute, attrPath, typePath); -} - - -#ifndef BUILDING_FS_SHELL - -// get_attribute_path_virtual_fd -static status_t -get_attribute_path_virtual_fd(int fd, const char *attribute, string &attrPath, - string &typePath) -{ - // stat the file to get a NodeRef - struct stat st; - status_t error = _kern_read_stat(fd, NULL, false, &st, sizeof(st)); - if (error != B_OK) - return error; - NodeRef ref(st); - - // Try to get a path. If we can't get a path, this is must be a "real" - // (i.e. system) file descriptor, which is just as well. - string path; - bool pathValid = (get_path(fd, NULL, path) == B_OK); - - // get the attribute path - return get_attribute_path(ref, (pathValid ? path.c_str() : NULL), - (pathValid ? -1 : fd), attribute, attrPath, typePath); -} - -#endif // ! BUILDING_FS_SHELL - - -// # pragma mark - Public API - - -// fs_open_attr_dir -DIR * -fs_open_attr_dir(const char *path) -{ - struct stat st; - if (lstat(path, &st)) - return NULL; - - return open_attr_dir(NodeRef(st), path, -1); -} - -// fs_fopen_attr_dir -DIR * -fs_fopen_attr_dir(int fd) -{ - struct stat st; - -#ifdef BUILDING_FS_SHELL - - if (fstat(fd, &st) < 0) - return NULL; - - return open_attr_dir(NodeRef(st), NULL, fd); - -#else - - status_t error = _kern_read_stat(fd, NULL, false, &st, - sizeof(struct stat)); - if (error != B_OK) { - errno = error; - return NULL; - } - - // Try to get a path. If we can't get a path, this is must be a "real" - // (i.e. system) file descriptor, which is just as well. - string path; - bool pathValid = (get_path(fd, NULL, path) == B_OK); - - // get the attribute path - return open_attr_dir(NodeRef(st), (pathValid ? path.c_str() : NULL), - (pathValid ? -1 : fd)); - -#endif -} - -// fs_close_attr_dir -int -fs_close_attr_dir(DIR *dir) -{ - return closedir(dir); -} - -// fs_read_attr_dir -struct dirent * -fs_read_attr_dir(DIR *dir) -{ - struct dirent *entry = NULL; - while (true) { - // read the next entry - entry = readdir(dir); - if (!entry) - return NULL; - - // ignore administrative entries; the - if (entry->d_name[0] == '_') { - string attrName = deescape_attr_name(entry->d_name); - strcpy(entry->d_name, attrName.c_str()); - return entry; - } - } -} - -// fs_rewind_attr_dir -void -fs_rewind_attr_dir(DIR *dir) -{ - rewinddir(dir); -} - -// fs_open_attr -int -fs_open_attr(int fd, const char *attribute, uint32 type, int openMode) -{ - if (!attribute) { - errno = B_BAD_VALUE; - return -1; - } - - // get the attribute path - string attrPath; - string typePath; - status_t error = get_attribute_path(fd, attribute, attrPath, typePath); - if (error != B_OK) { - errno = error; - return -1; - } - - // check, if the attribute already exists - struct stat st; - bool exists = (lstat(attrPath.c_str(), &st) == 0); - - // open the attribute - int attrFD = open(attrPath.c_str(), openMode, S_IRWXU | S_IRWXG | S_IRWXO); - if (attrFD < 0) - return -1; - - // set the type, if the attribute didn't exist yet - if (!exists) { - // create a file prefixed "t" - int typeFD = creat(typePath.c_str(), S_IRWXU | S_IRWXG | S_IRWXO); - if (typeFD >= 0) { - // write the type into the file - if (write(typeFD, &type, sizeof(type)) < 0) - error = errno; - - close(typeFD); - - } else - error = errno; - - // remove type and attribute file, if something went wrong - if (error != B_OK) { - if (typeFD > 0) { - unlink(typePath.c_str()); - } - - close(attrFD); - unlink(attrPath.c_str()); - - errno = error; - return -1; - } - } - - return attrFD; -} - -// fs_close_attr -int -fs_close_attr(int fd) -{ - return close(fd); -} - -// fs_read_attr -ssize_t -fs_read_attr(int fd, const char *attribute, uint32 type, off_t pos, - void *buffer, size_t readBytes) -{ - // open the attribute - int attrFD = fs_open_attr(fd, attribute, type, O_RDONLY); - if (attrFD < 0) - return attrFD; - - // read - ssize_t bytesRead = read_pos(attrFD, pos, buffer, readBytes); - status_t error = errno; - - // close the attribute - fs_close_attr(attrFD); - - if (bytesRead < 0) { - errno = error; - return -1; - } - - return bytesRead; -} - -// fs_write_attr -ssize_t -fs_write_attr(int fd, const char *attribute, uint32 type, off_t pos, - const void *buffer, size_t readBytes) -{ - // open the attribute - int attrFD = fs_open_attr(fd, attribute, type, - O_WRONLY | O_CREAT | O_TRUNC); - if (attrFD < 0) - return attrFD; - - // read - ssize_t bytesWritten = write_pos(attrFD, pos, buffer, readBytes); - status_t error = errno; - - // close the attribute - fs_close_attr(attrFD); - - if (bytesWritten < 0) { - errno = error; - return -1; - } - - return bytesWritten; -} - -// fs_remove_attr -int -fs_remove_attr(int fd, const char *attribute) -{ - if (!attribute) { - errno = B_BAD_VALUE; - return -1; - } - - // get the attribute path - string attrPath; - string typePath; - status_t error = get_attribute_path(fd, attribute, attrPath, typePath); - if (error != B_OK) { - errno = error; - return -1; - } - - // remove the attribute - if (unlink(attrPath.c_str()) < 0) - return -1; - - unlink(typePath.c_str()); - - return B_OK; -} - -// fs_stat_attr -int -fs_stat_attr(int fd, const char *attribute, struct attr_info *attrInfo) -{ - if (!attribute || !attrInfo) { - errno = B_BAD_VALUE; - return -1; - } - - // get the attribute path - string attrPath; - string typePath; - status_t error = get_attribute_path(fd, attribute, attrPath, typePath); - if (error != B_OK) { - errno = error; - return -1; - } - - // stat the attribute file to get the size of the attribute - struct stat st; - if (lstat(attrPath.c_str(), &st) < 0) - return -1; - - attrInfo->size = st.st_size; - - // now open the attribute type file and read the attribute's type - int typeFD = open(typePath.c_str(), O_RDONLY); - if (typeFD < 0) - return -1; - - ssize_t bytesRead = read(typeFD, &attrInfo->type, sizeof(attrInfo->type)); - if (bytesRead < 0) - error = errno; - else if (bytesRead < (ssize_t)sizeof(attrInfo->type)) - error = B_FILE_ERROR; - - close(typeFD); - - // fail on error - if (error != B_OK) { - errno = error; - return -1; - } - - return 0; -} - - -// #pragma mark - Private Syscalls - - -#ifndef BUILDING_FS_SHELL - -// _kern_open_attr_dir -int -_kern_open_attr_dir(int fd, const char *path) -{ - // get node ref for the node - struct stat st; - status_t error = _kern_read_stat(fd, path, false, &st, - sizeof(struct stat)); - if (error != B_OK) { - errno = error; - return -1; - } - NodeRef ref(st); - - // If a path was given, get a usable path. - string realPath; - if (path) { - error = get_path(fd, path, realPath); - if (error != B_OK) - return error; - } - - // open the attr dir - DIR *dir = open_attr_dir(ref, (path ? realPath.c_str() : NULL), - (path ? -1 : fd)); - if (!dir) - return errno; - - // create descriptor - AttrDirDescriptor *descriptor = new AttrDirDescriptor(dir, ref); - return add_descriptor(descriptor); -} - -// _kern_rename_attr -status_t -_kern_rename_attr(int fromFile, const char *fromName, int toFile, - const char *toName) -{ - if (!fromName || !toName) - return B_BAD_VALUE; - - // get the attribute paths - string fromAttrPath; - string fromTypePath; - status_t error = get_attribute_path_virtual_fd(fromFile, fromName, - fromAttrPath, fromTypePath); - if (error != B_OK) - return error; - - string toAttrPath; - string toTypePath; - error = get_attribute_path_virtual_fd(toFile, toName, toAttrPath, - toTypePath); - if (error != B_OK) - return error; - - // rename the attribute and type files - if (rename(fromAttrPath.c_str(), toAttrPath.c_str()) < 0) - return errno; - - if (rename(fromTypePath.c_str(), toTypePath.c_str()) < 0) { - // renaming the type file failed: try to rename back the attribute file - error = errno; - - rename(toAttrPath.c_str(), fromAttrPath.c_str()); - - return error; - } - - return B_OK; -} - -// _kern_remove_attr -status_t -_kern_remove_attr(int fd, const char *name) -{ - if (!name) - return B_BAD_VALUE; - - // get the attribute path - string attrPath; - string typePath; - status_t error = get_attribute_path_virtual_fd(fd, name, attrPath, - typePath); - if (error != B_OK) - return error; - - // remove the attribute - if (unlink(attrPath.c_str()) < 0) - return errno; - - unlink(typePath.c_str()); - - return B_OK; -} - -#endif // ! BUILDING_FS_SHELL Copied: haiku/trunk/src/build/libroot/fs_attr_generic.cpp (from rev 20606, haiku/trunk/src/build/libroot/fs_attr.cpp) Added: haiku/trunk/src/build/libroot/fs_attr_xattr.cpp =================================================================== --- haiku/trunk/src/build/libroot/fs_attr_xattr.cpp 2007-04-08 02:04:21 UTC (rev 20608) +++ haiku/trunk/src/build/libroot/fs_attr_xattr.cpp 2007-04-08 02:19:01 UTC (rev 20609) @@ -0,0 +1,638 @@ + +#ifdef BUILDING_FS_SHELL +# include "compat.h" +# define B_OK 0 +# define B_BAD_VALUE EINVAL +# define B_FILE_ERROR EBADF +# define B_ERROR EINVAL +# define B_ENTRY_NOT_FOUND ENOENT +# define B_NO_MEMORY ENOMEM +#else +# include +# include + +# include "fs_impl.h" +# include "fs_descriptors.h" +#endif + +#include +#include +#include +#include +#include +#include +#include + +#include + +#include +#include + +#include + +namespace BPrivate {} +using namespace BPrivate; +using std::map; +using std::string; + +// the namespace all attributes live in +static const char* kAttributeNamespace = "user."; +static const int kAttributeNamespaceLen = 5; + +// the maximum length of an attribute listing we support +static const int kMaxAttributeListingLength = 10240; + +// the maximum attribute length we support +static const int kMaxAttributeLength = 10240 * 4; + + + +namespace { + +class AttributeDirectory; + +typedef map AttrDirMap; +static AttrDirMap sAttributeDirectories; + +// LongDirent +struct LongDirent : dirent { + char name[B_FILE_NAME_LENGTH]; +}; + +// AttributeHeader +struct AttributeHeader { + uint32 type; +}; + +// AttributeDirectory +class AttributeDirectory { +public: + AttributeDirectory() + : fFileFD(-1), + fFakeDir(NULL), + fListing(NULL), + fListingLength(-1), + fListingIndex(0) + { + } + + ~AttributeDirectory() + { + if (fFileFD >= 0) + close(fFileFD); + + if (fFakeDir) { + AttrDirMap::iterator it = sAttributeDirectories.find(fFakeDir); + if (it != sAttributeDirectories.end()) + sAttributeDirectories.erase(it); + + closedir(fFakeDir); + } + + free(fListing); + } + + static AttributeDirectory* Get(DIR* dir) + { + AttrDirMap::iterator it = sAttributeDirectories.find(dir); + if (it == sAttributeDirectories.end()) + return NULL; + return it->second; + } + + status_t Init(const char* path, int fileFD) + { + // open a fake DIR + if (!fFakeDir) { + fFakeDir = opendir("."); + if (!fFakeDir) + return B_ERROR; + + sAttributeDirectories[fFakeDir] = this; + } + + if (path) { + // A path was given -- check, if it's a symlink. If so we need to + // keep the path, otherwise we open a FD. + struct stat st; + if (lstat(path, &st)) + return B_ENTRY_NOT_FOUND; + + if (S_ISLNK(st.st_mode)) { + fFileFD = -1; + fPath = path; + } else { + fFileFD = open(path, O_RDONLY); + if (fFileFD < 0) + return errno; + fPath = ""; + } + } else { + // FD was given -- dup it. + fFileFD = dup(fileFD); + if (fFileFD < 0) + return errno; + fPath = ""; + } + + fListingLength = -1; + fListingIndex = 0; + + return B_OK; + } + + DIR* FakeDir() const { return fFakeDir; } + + status_t ReadDir(struct dirent** _entry) + { + // make sure we have a current listing + status_t error = _CheckListing(); + if (error != B_OK) + return error; + + // keep going until we find an entry or hit the end of dir + while (fListingIndex < fListingLength) { + // get next entry name + const char* name = fListing + fListingIndex; + int nameLen = strlen(name); + fListingIndex += nameLen + 1; + + // check the attribute namespace + if (strncmp(name, kAttributeNamespace, kAttributeNamespaceLen) != 0) + continue; + name += kAttributeNamespaceLen; + nameLen -= kAttributeNamespaceLen; + + if (nameLen == 0) { + // Uh, weird attribute. + return B_ERROR; + } + + // prepare the dirent + strcpy(fDirent.d_name, name); + fDirent.d_ino = 0; +// TODO: We need the node ID! + + *_entry = &fDirent; + return B_OK; + } + + // end of dir + *_entry = NULL; + return B_OK; + } + + void RewindDir() + { + fListingIndex = 0; + } + +private: + status_t _CheckListing() + { + if (fListing && fListingLength >= 0) + return B_OK; + + char listing[kMaxAttributeListingLength]; + + // get the listing + ssize_t length; + if (fFileFD >= 0) { + length = flistxattr(fFileFD, listing, kMaxAttributeListingLength); + } else { + length = llistxattr(fPath.c_str(), listing, + kMaxAttributeListingLength); + } + if (length < 0) + return errno; + + // clone the on-stack listing + char* newListing = (char*)realloc(fListing, length); + if (!newListing) + return B_NO_MEMORY; + memcpy(newListing, listing, length); + + fListing = newListing; + fListingLength = length; + fListingIndex = 0; + + return B_OK; + } + +private: + int fFileFD; + string fPath; + DIR* fFakeDir; + LongDirent fDirent; + char* fListing; + int fListingLength; + int fListingIndex; +}; + +// LocalFD +class LocalFD { +public: + LocalFD() + { + } + + ~LocalFD() + { + } + + status_t Init(int fd) + { +#ifndef BUILDING_FS_SHELL + Descriptor* descriptor = get_descriptor(fd); + if (descriptor && !descriptor->IsSystemFD()) { + // we need to get a path + fFD = -1; + return descriptor->GetPath(fPath); + } +#endif + + fFD = fd; + fPath = ""; + return B_OK; + } + + int FD() const + { + return fFD; + } + + const char* Path() const + { + return (fFD < 0 ? fPath.c_str() : NULL); + } + +private: + string fPath; + int fFD; +}; + +} // unnamed namspace + + +// # pragma mark - Public API + + +// fs_open_attr_dir +DIR * +fs_open_attr_dir(const char *path) +{ + AttributeDirectory* attrDir = new AttributeDirectory; + + status_t error = attrDir->Init(path, -1); + if (error != B_OK) { + errno = error; + delete attrDir; + return NULL; + } + + return attrDir->FakeDir(); +} + +// fs_fopen_attr_dir +DIR * +fs_fopen_attr_dir(int fd) +{ + AttributeDirectory* attrDir = new AttributeDirectory; + + status_t error = attrDir->Init(NULL, fd); + if (error != B_OK) { + errno = error; + delete attrDir; + return NULL; [... truncated: 438 lines follow ...] From bonefish at mail.berlios.de Sun Apr 8 04:21:11 2007 From: bonefish at mail.berlios.de (bonefish at BerliOS) Date: Sun, 8 Apr 2007 04:21:11 +0200 Subject: [Haiku-commits] r20610 - haiku/trunk/build/jam Message-ID: <200704080221.l382LBJ7004715@sheep.berlios.de> Author: bonefish Date: 2007-04-08 04:21:10 +0200 (Sun, 08 Apr 2007) New Revision: 20610 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20610&view=rev Modified: haiku/trunk/build/jam/MiscRules Log: The ":" to identify a target for the "run" feature must be at the beginning of the string; it was formerly matched anywhere. Modified: haiku/trunk/build/jam/MiscRules =================================================================== --- haiku/trunk/build/jam/MiscRules 2007-04-08 02:19:01 UTC (rev 20609) +++ haiku/trunk/build/jam/MiscRules 2007-04-08 02:21:10 UTC (rev 20610) @@ -186,7 +186,7 @@ local i ; for i in $(commandLine) { # targets are marked by the ":" prefix - local target = [ Match :(.*) : $(i) ] ; + local target = [ Match ^:(.*) : $(i) ] ; if $(target) { targets += $(target) ; targetVarName = $(targetVarName)X ; From hugosantos at mail.berlios.de Sun Apr 8 07:50:35 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Sun, 8 Apr 2007 07:50:35 +0200 Subject: [Haiku-commits] r20611 - haiku/trunk/src/add-ons/kernel/network/stack Message-ID: <200704080550.l385oZss001513@sheep.berlios.de> Author: hugosantos Date: 2007-04-08 07:50:25 +0200 (Sun, 08 Apr 2007) New Revision: 20611 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20611&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp haiku/trunk/src/add-ons/kernel/network/stack/domains.cpp haiku/trunk/src/add-ons/kernel/network/stack/domains.h haiku/trunk/src/add-ons/kernel/network/stack/interfaces.cpp haiku/trunk/src/add-ons/kernel/network/stack/interfaces.h haiku/trunk/src/add-ons/kernel/network/stack/routes.cpp Log: introduced net_device_interface level locking. Modified: haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp 2007-04-08 02:21:10 UTC (rev 20610) +++ haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp 2007-04-08 05:50:25 UTC (rev 20611) @@ -45,9 +45,13 @@ net_device *device = interface->device; status_t status = B_OK; - while ((device->flags & IFF_UP) != 0) { + BenaphoreLocker rx_lock(interface->rx_lock); + + while (device->flags & IFF_UP) { net_buffer *buffer; + rx_lock.Unlock(); status = device->module->receive_data(device, &buffer); + rx_lock.Lock(); if (status == B_OK) { //dprintf("received buffer of %ld bytes length\n", buffer->size); @@ -100,10 +104,6 @@ // and the receive_data() above should have been // interrupted. One check should be enough, specially // considering the snooze above. - // - // TODO: make sure that when receive_data() returns - // after closing the new device->flags are - // already visible in all processors. } return status; @@ -180,6 +180,52 @@ } +static status_t +datalink_control_interface(net_domain_private *domain, int32 option, + void *value, size_t *_length, size_t expected, bool getByName) +{ + if (*_length < expected) + return B_BAD_VALUE; + + ifreq request; + memset(&request, 0, sizeof(request)); + + if (user_memcpy(&request, value, expected) < B_OK) + return B_BAD_ADDRESS; + + BenaphoreLocker _(domain->lock); + net_interface *interface = NULL; + + if (getByName) + interface = find_interface(domain, request.ifr_name); + else + interface = find_interface(domain, request.ifr_index); + + status_t status = (interface == NULL) ? ENODEV : B_OK; + + switch (option) { + case SIOCGIFINDEX: + if (interface) + request.ifr_index = interface->index; + else + request.ifr_index = 0; + break; + + case SIOCGIFNAME: + if (interface) + strlcpy(request.ifr_name, interface->name, IF_NAMESIZE); + else + status = B_BAD_VALUE; // TODO should be ENXIO? + break; + } + + if (status < B_OK) + return status; + + return user_memcpy(value, &request, sizeof(ifreq)); +} + + // #pragma mark - datalink module @@ -195,51 +241,20 @@ switch (option) { case SIOCGIFINDEX: - { - // get index of interface - struct ifreq request; - if (user_memcpy(&request, value, IF_NAMESIZE) < B_OK) - return B_BAD_ADDRESS; - - benaphore_lock(&domain->lock); - - net_interface *interface = find_interface(domain, - request.ifr_name); - if (interface != NULL) - request.ifr_index = interface->index; - else - request.ifr_index = 0; - - benaphore_unlock(&domain->lock); - - if (request.ifr_index == 0) - return ENODEV; - - return user_memcpy(value, &request, sizeof(struct ifreq)); - } + return datalink_control_interface(domain, option, value, _length, + IF_NAMESIZE, true); case SIOCGIFNAME: + return datalink_control_interface(domain, option, value, _length, + sizeof(ifreq), false); + + case SIOCDIFADDR: + case SIOCSIFFLAGS: { - // get name of interface via index struct ifreq request; if (user_memcpy(&request, value, sizeof(struct ifreq)) < B_OK) return B_BAD_ADDRESS; - benaphore_lock(&domain->lock); - status_t status = B_OK; - - net_interface *interface = find_interface(domain, - request.ifr_index); - if (interface != NULL) - strlcpy(request.ifr_name, interface->name, IF_NAMESIZE); - else - status = B_BAD_VALUE; - - benaphore_unlock(&domain->lock); - - if (status < B_OK) - return status; - - return user_memcpy(value, &request, sizeof(struct ifreq)); + return domain_interface_control(domain, option, &request); } case SIOCAIFADDR: @@ -251,22 +266,7 @@ return add_interface_to_domain(domain, request); } - case SIOCDIFADDR: - { - // remove interface address - struct ifreq request; - if (user_memcpy(&request, value, sizeof(struct ifreq)) < B_OK) - return B_BAD_ADDRESS; - BenaphoreLocker _(domain->lock); - - net_interface *interface = find_interface(domain, - request.ifr_name); - if (interface == NULL) - return ENODEV; - return remove_interface_from_domain(interface); - } - case SIOCGIFCOUNT: { // count number of interfaces @@ -314,46 +314,20 @@ default: { // try to pass the request to an existing interface - struct ifreq request; if (user_memcpy(&request, value, sizeof(struct ifreq)) < B_OK) return B_BAD_ADDRESS; BenaphoreLocker _(domain->lock); - status_t status = B_OK; net_interface *interface = find_interface(domain, request.ifr_name); - if (interface != NULL) { - // filter out bringing the interface up or down - if (option == SIOCSIFFLAGS) { - if (((uint32)request.ifr_flags & IFF_UP) - != (interface->flags & IFF_UP)) { - if ((interface->flags & IFF_UP) != 0) { - interface_set_down(interface); - } else { - // bring it up - status = interface->first_info->interface_up( - interface->first_protocol); - if (status == B_OK) { - interface->flags |= IFF_UP - | (interface->device->media & IFM_ACTIVE - ? IFF_LINK : 0); - } - } - } + if (interface == NULL) + return B_BAD_VALUE; - if (status == B_OK) - interface->flags |= request.ifr_flags & ~(IFF_UP | IFF_LINK); - } else { - // pass the request into the datalink protocol stack - status = interface->first_info->control( - interface->first_protocol, option, value, *_length); - } - } else - status = B_BAD_VALUE; - - return status; + // pass the request into the datalink protocol stack + return interface->first_info->control( + interface->first_protocol, option, value, *_length); } } return B_BAD_VALUE; Modified: haiku/trunk/src/add-ons/kernel/network/stack/domains.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/domains.cpp 2007-04-08 02:21:10 UTC (rev 20610) +++ haiku/trunk/src/add-ons/kernel/network/stack/domains.cpp 2007-04-08 05:50:25 UTC (rev 20611) @@ -10,6 +10,7 @@ #include "domains.h" #include "interfaces.h" #include "utility.h" +#include "stack_private.h" #include @@ -21,6 +22,7 @@ #include #include #include +#include #define TRACE_DOMAINS @@ -196,6 +198,64 @@ } +status_t +domain_interface_control(net_domain_private *domain, int32 option, + ifreq *request) +{ + const char *name = request->ifr_name; + status_t status = B_OK; + + net_device_interface *device = get_device_interface(name, false); + if (device == NULL) + return ENODEV; + else { + // The locking protocol dictates that if both the RX lock + // and domain locks are required, we MUST obtain the RX + // lock before the domain lock. This order MUST NOT ever + // be reversed under the penalty of deadlock. + BenaphoreLocker _1(device->rx_lock); + BenaphoreLocker _2(domain->lock); + + net_interface *interface = find_interface(domain, name); + if (interface != NULL) { + switch (option) { + case SIOCDIFADDR: + remove_interface_from_domain(interface); + break; + + case SIOCSIFFLAGS: + if (((uint32)request->ifr_flags & IFF_UP) + != (interface->flags & IFF_UP)) { + if (interface->flags & IFF_UP) { + interface_set_down(interface); + } else { + status = interface->first_info->interface_up( + interface->first_protocol); + if (status == B_OK) { + interface->flags |= IFF_UP; + // TODO this doesn't belong here + if (interface->device->media & IFM_ACTIVE) + interface->flags |= IFF_LINK; + } + } + } + + if (status == B_OK) + interface->flags |= request->ifr_flags & ~(IFF_UP | IFF_LINK); + break; + } + } + } + + // If the SIOCDIFADDR call above removed the last interface + // associated with the device interface, this put_() will + // effectively remove the interface + put_device_interface(device); + + return status; +} + + void domain_interfaces_link_changed(net_device *device) { Modified: haiku/trunk/src/add-ons/kernel/network/stack/domains.h =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/domains.h 2007-04-08 02:21:10 UTC (rev 20610) +++ haiku/trunk/src/add-ons/kernel/network/stack/domains.h 2007-04-08 05:50:25 UTC (rev 20611) @@ -39,6 +39,8 @@ void domain_interfaces_link_changed(net_device *device); void domain_interface_went_down(net_interface *); void domain_removed_device_interface(net_device_interface *); +status_t domain_interface_control(net_domain_private *domain, int32 option, + struct ifreq *request); net_domain *get_domain(int family); status_t register_domain(int family, const char *name, Modified: haiku/trunk/src/add-ons/kernel/network/stack/interfaces.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/interfaces.cpp 2007-04-08 02:21:10 UTC (rev 20610) +++ haiku/trunk/src/add-ons/kernel/network/stack/interfaces.cpp 2007-04-08 05:50:25 UTC (rev 20611) @@ -325,6 +325,9 @@ interface->module->uninit_device(interface->device); put_module(interface->module->info.name); + + benaphore_destroy(&interface->rx_lock); + delete interface; } @@ -355,7 +358,7 @@ If the interface does not yet exist, a new one is created. */ struct net_device_interface * -get_device_interface(const char *name) +get_device_interface(const char *name, bool create) { BenaphoreLocker locker(sInterfaceLock); @@ -367,6 +370,9 @@ // try to recreate interface - it just got removed } + if (!create) + return NULL; + void *cookie = open_module_list("network/devices"); if (cookie == NULL) return NULL; @@ -387,23 +393,25 @@ // create new module interface for this interface = new (std::nothrow) net_device_interface; if (interface != NULL) { - interface->name = device->name; - interface->module = module; - interface->device = device; - interface->up_count = 0; - interface->ref_count = 1; - interface->deframe_func = NULL; - interface->deframe_ref_count = 0; + if (benaphore_init(&interface->rx_lock, "rx lock") >= B_OK) { + interface->name = device->name; + interface->module = module; + interface->device = device; + interface->up_count = 0; + interface->ref_count = 1; + interface->deframe_func = NULL; + interface->deframe_ref_count = 0; - device->index = ++sDeviceIndex; - device->module = module; + device->index = ++sDeviceIndex; + device->module = module; - sInterfaces.Add(interface); - return interface; - } else - module->uninit_device(device); + sInterfaces.Add(interface); + return interface; + } + delete interface; + } + module->uninit_device(device); } - put_module(moduleName); } } @@ -415,6 +423,19 @@ void down_device_interface(net_device_interface *interface) { + // RX lock must be held when calling down_device_interface. + // Known callers are `interface_protocol_down' which gets + // here via one of the following paths: + // + // - domain_interface_control() [rx lock held, domain lock held] + // interface_set_down() + // interface_protocol_down() + // + // - domain_interface_control() [rx lock held, domain lock held] + // remove_interface_from_domain() + // delete_interface() + // interface_set_down() + net_device *device = interface->device; dprintf("down_device_interface(%s)\n", interface->name); @@ -422,13 +443,17 @@ device->flags &= ~IFF_UP; interface->module->down(device); - // TODO: there is a race condition between the previous - // ->down and device->module->receive_data which - // locks us here waiting for the reader_thread + thread_id reader_thread = interface->reader_thread; + // one of the callers must hold a reference to the net_device_interface + // usually it is one of the net_interfaces. + benaphore_unlock(&interface->rx_lock); + // make sure the reader thread is gone before shutting down the interface status_t status; - wait_for_thread(interface->reader_thread, &status); + wait_for_thread(reader_thread, &status); + + benaphore_lock(&interface->rx_lock); } @@ -449,6 +474,8 @@ if (interface == NULL) return ENODEV; + BenaphoreLocker _(interface->rx_lock); + if (--interface->deframe_ref_count == 0) interface->deframe_func = NULL; @@ -476,6 +503,8 @@ if (interface == NULL) return ENODEV; + BenaphoreLocker _(interface->rx_lock); + if (interface->deframe_func != NULL && interface->deframe_func != deframeFunc) return B_ERROR; @@ -508,6 +537,8 @@ if (interface == NULL) return ENODEV; + BenaphoreLocker _(interface->rx_lock); + // see if such a handler already for this device DeviceHandlerList::Iterator iterator = interface->receive_funcs.GetIterator(); @@ -542,6 +573,8 @@ if (interface == NULL) return ENODEV; + BenaphoreLocker _(interface->rx_lock); + // search for the handler DeviceHandlerList::Iterator iterator = interface->receive_funcs.GetIterator(); @@ -571,6 +604,8 @@ if (interface == NULL) return ENODEV; + BenaphoreLocker _(interface->rx_lock); + // Add new monitor net_device_monitor *monitor = new (std::nothrow) net_device_monitor; @@ -595,6 +630,8 @@ if (interface == NULL) return ENODEV; + BenaphoreLocker _(interface->rx_lock); + // search for the monitor DeviceMonitorList::Iterator iterator = interface->monitor_funcs.GetIterator(); @@ -644,6 +681,8 @@ // This is very complex, refer to delete_interface() for // further details. + BenaphoreLocker _(interface->rx_lock); + // this will possibly call: // remove_interface_from_domain() [domain gets locked] // delete_interface() Modified: haiku/trunk/src/add-ons/kernel/network/stack/interfaces.h =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/interfaces.h 2007-04-08 02:21:10 UTC (rev 20610) +++ haiku/trunk/src/add-ons/kernel/network/stack/interfaces.h 2007-04-08 05:50:25 UTC (rev 20611) @@ -44,6 +44,8 @@ DeviceMonitorList monitor_funcs; DeviceHandlerList receive_funcs; + + benaphore rx_lock; }; typedef DoublyLinkedList DeviceInterfaceList; @@ -78,7 +80,8 @@ status_t list_device_interfaces(void *buffer, size_t *_bufferSize); void put_device_interface(struct net_device_interface *interface); struct net_device_interface *get_device_interface(uint32 index); -struct net_device_interface *get_device_interface(const char *name); +struct net_device_interface *get_device_interface(const char *name, + bool create = true); void down_device_interface(net_device_interface *interface); // devices Modified: haiku/trunk/src/add-ons/kernel/network/stack/routes.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/routes.cpp 2007-04-08 02:21:10 UTC (rev 20610) +++ haiku/trunk/src/add-ons/kernel/network/stack/routes.cpp 2007-04-08 05:50:25 UTC (rev 20611) @@ -506,9 +506,19 @@ while (iterator.HasNext()) { net_route *route = iterator.Next(); - // TODO handle refcounting, if the route needs to linger - // for some reason we should set interface or - // something of the sorts that invalidates it's reference + // TODO If we are removing the interface this will bork. + // Consider the following case: + // [thread 1] ipv4_send_data() + // [thread 1] get_route() [domain locked, unlocked] <- route + // [thread 2] ... [domain locked] + // [thread 2] invalidate_routes() + // [thread 2] remove_route() <- route + // [thread 1] ... ipv4_send_data() accesses `route'. Bork bork. + // + // We could either add per-route locks (expensive) or + // lock the domain throughout the send_data() routine. + // These are the easy solutions, need to think about this. -hugo + if (route->interface == interface) remove_route(domain, route); } From hugosantos at mail.berlios.de Sun Apr 8 07:50:49 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Sun, 8 Apr 2007 07:50:49 +0200 Subject: [Haiku-commits] r20612 - in haiku/trunk/src/add-ons/kernel/network: devices/ethernet devices/loopback stack Message-ID: <200704080550.l385onEd001538@sheep.berlios.de> Author: hugosantos Date: 2007-04-08 07:50:36 +0200 (Sun, 08 Apr 2007) New Revision: 20612 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20612&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/devices/ethernet/ethernet.cpp haiku/trunk/src/add-ons/kernel/network/devices/loopback/loopback.cpp haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp haiku/trunk/src/add-ons/kernel/network/stack/domains.cpp haiku/trunk/src/add-ons/kernel/network/stack/domains.h haiku/trunk/src/add-ons/kernel/network/stack/interfaces.cpp Log: moved IFF_LINK handling to the device module (ethernet in this case). Now domain interfaces only keep specific flags such as IFF_UP and the configuration flags. IFF_LINK, IFF_BROADCAST etc are maintained exclusively by the device. Modified: haiku/trunk/src/add-ons/kernel/network/devices/ethernet/ethernet.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/devices/ethernet/ethernet.cpp 2007-04-08 05:50:25 UTC (rev 20611) +++ haiku/trunk/src/add-ons/kernel/network/devices/ethernet/ethernet.cpp 2007-04-08 05:50:36 UTC (rev 20612) @@ -67,6 +67,11 @@ device->link_quality = state.quality; device->link_speed = state.speed; + if (device->media & IFM_ACTIVE) + device->flags |= IFF_LINK; + else + device->flags &= ~IFF_LINK; + dprintf("%s: media change, media 0x%0x quality %u speed %u\n", device->name, (unsigned int)device->media, (unsigned int)device->link_quality, @@ -132,7 +137,7 @@ memset(device, 0, sizeof(ethernet_device)); strcpy(device->name, name); - device->flags = IFF_BROADCAST; + device->flags = IFF_BROADCAST | IFF_LINK; device->type = IFT_ETHER; device->mtu = 1500; device->media = IFM_ACTIVE | IFM_ETHER; Modified: haiku/trunk/src/add-ons/kernel/network/devices/loopback/loopback.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/devices/loopback/loopback.cpp 2007-04-08 05:50:25 UTC (rev 20611) +++ haiku/trunk/src/add-ons/kernel/network/devices/loopback/loopback.cpp 2007-04-08 05:50:36 UTC (rev 20612) @@ -15,6 +15,7 @@ #include #include +#include #include #include #include @@ -85,9 +86,10 @@ memset(device, 0, sizeof(loopback_device)); strcpy(device->name, name); - device->flags = IFF_LOOPBACK; + device->flags = IFF_LOOPBACK | IFF_LINK; device->type = IFT_LOOP; device->mtu = 16384; + device->media = IFM_ACTIVE; *_device = device; return B_OK; Modified: haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp 2007-04-08 05:50:25 UTC (rev 20611) +++ haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp 2007-04-08 05:50:36 UTC (rev 20612) @@ -619,7 +619,7 @@ { // get flags struct ifreq request; - request.ifr_flags = interface->flags; + request.ifr_flags = interface->flags | interface->device->flags; return user_memcpy(&((struct ifreq *)argument)->ifr_flags, &request.ifr_flags, sizeof(request.ifr_flags)); Modified: haiku/trunk/src/add-ons/kernel/network/stack/domains.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/domains.cpp 2007-04-08 05:50:25 UTC (rev 20611) +++ haiku/trunk/src/add-ons/kernel/network/stack/domains.cpp 2007-04-08 05:50:36 UTC (rev 20612) @@ -219,30 +219,30 @@ net_interface *interface = find_interface(domain, name); if (interface != NULL) { switch (option) { - case SIOCDIFADDR: - remove_interface_from_domain(interface); - break; + case SIOCDIFADDR: + remove_interface_from_domain(interface); + break; - case SIOCSIFFLAGS: - if (((uint32)request->ifr_flags & IFF_UP) - != (interface->flags & IFF_UP)) { - if (interface->flags & IFF_UP) { - interface_set_down(interface); - } else { - status = interface->first_info->interface_up( - interface->first_protocol); - if (status == B_OK) { - interface->flags |= IFF_UP; - // TODO this doesn't belong here - if (interface->device->media & IFM_ACTIVE) - interface->flags |= IFF_LINK; + case SIOCSIFFLAGS: + { + uint32 requestFlags = request->ifr_flags; + request->ifr_flags &= ~(IFF_UP | IFF_LINK | IFF_BROADCAST); + + if ((requestFlags & IFF_UP) != (interface->flags & IFF_UP)) { + if (requestFlags & IFF_UP) { + status = interface->first_info->interface_up( + interface->first_protocol); + if (status == B_OK) + interface->flags |= IFF_UP; + } else { + interface_set_down(interface); } } - } - if (status == B_OK) - interface->flags |= request->ifr_flags & ~(IFF_UP | IFF_LINK); - break; + if (status == B_OK) + interface->flags |= request->ifr_flags; + break; + } } } } @@ -257,38 +257,6 @@ void -domain_interfaces_link_changed(net_device *device) -{ - // TODO: notify listeners about this! - - BenaphoreLocker locker(sDomainLock); - - net_domain_private *domain = NULL; - while (true) { - domain = (net_domain_private *)list_get_next_item(&sDomains, domain); - if (domain == NULL) - break; - - BenaphoreLocker locker(domain->lock); - - net_interface *interface = NULL; - while (true) { - interface = (net_interface *)list_get_next_item(&domain->interfaces, - interface); - if (interface == NULL) - break; - - if (interface->device == device) { - // update IFF_LINK flag - interface->flags = (interface->flags & ~IFF_LINK) - | (device->media & IFM_ACTIVE ? IFF_LINK : 0); - } - } - } -} - - -void domain_interface_went_down(net_interface *interface) { // the domain should be locked here. always check Modified: haiku/trunk/src/add-ons/kernel/network/stack/domains.h =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/domains.h 2007-04-08 05:50:25 UTC (rev 20611) +++ haiku/trunk/src/add-ons/kernel/network/stack/domains.h 2007-04-08 05:50:36 UTC (rev 20612) @@ -36,7 +36,6 @@ status_t list_domain_interfaces(void *buffer, size_t *_bufferSize); status_t add_interface_to_domain(net_domain *domain, struct ifreq& request); status_t remove_interface_from_domain(net_interface *interface); -void domain_interfaces_link_changed(net_device *device); void domain_interface_went_down(net_interface *); void domain_removed_device_interface(net_device_interface *); status_t domain_interface_control(net_domain_private *domain, int32 option, Modified: haiku/trunk/src/add-ons/kernel/network/stack/interfaces.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/interfaces.cpp 2007-04-08 05:50:25 UTC (rev 20611) +++ haiku/trunk/src/add-ons/kernel/network/stack/interfaces.cpp 2007-04-08 05:50:36 UTC (rev 20612) @@ -141,7 +141,7 @@ interface->mask = NULL; interface->index = ++sInterfaceIndex; - interface->flags = deviceInterface->device->flags & ~IFF_UP; + interface->flags = 0; interface->type = 0; interface->mtu = deviceInterface->device->mtu; interface->metric = 0; @@ -169,8 +169,7 @@ if ((interface->flags & IFF_UP) == 0) return; - // TODO: IFF_LINK should belong in device only - interface->flags &= ~(IFF_UP | IFF_LINK); + interface->flags &= ~IFF_UP; interface->first_info->interface_down(interface->first_protocol); } @@ -658,7 +657,6 @@ status_t device_link_changed(net_device *device) { - domain_interfaces_link_changed(device); return B_OK; } From hugosantos at mail.berlios.de Sun Apr 8 07:50:55 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Sun, 8 Apr 2007 07:50:55 +0200 Subject: [Haiku-commits] r20613 - haiku/trunk/src/add-ons/kernel/network/stack Message-ID: <200704080550.l385otIl001580@sheep.berlios.de> Author: hugosantos Date: 2007-04-08 07:50:49 +0200 (Sun, 08 Apr 2007) New Revision: 20613 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20613&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp Log: updated some locking related comments. Modified: haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp 2007-04-08 05:50:36 UTC (rev 20612) +++ haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp 2007-04-08 05:50:49 UTC (rev 20613) @@ -56,7 +56,6 @@ //dprintf("received buffer of %ld bytes length\n", buffer->size); // feed device monitors - // TODO: locking! DeviceMonitorList::Iterator iterator = interface->monitor_funcs.GetIterator(); while (iterator.HasNext()) { @@ -67,7 +66,6 @@ int32 type = interface->deframe_func(device, buffer); if (type >= 0) { // find handler for this packet - // TODO: locking! DeviceHandlerList::Iterator iterator = interface->receive_funcs.GetIterator(); status = B_ERROR; @@ -470,8 +468,12 @@ interface_protocol *protocol = (interface_protocol *)_protocol; net_interface_private *interface = (net_interface_private *)protocol->interface; - // feed device monitors - // TODO: locking! + // TODO: Need to think about this locking. We can't obtain the + // RX Lock here (nor would it make sense) as the ARP + // module calls send_data() with it's lock held (similiar + // to the domain lock, which would violate the locking + // protocol). + DeviceMonitorList::Iterator iterator = interface->device_interface->monitor_funcs.GetIterator(); while (iterator.HasNext()) { @@ -491,7 +493,7 @@ ((net_interface_private *)protocol->interface)->device_interface; net_device *device = protocol->device; - // TODO: locking! + // This function is called with the RX lock held. if (deviceInterface->up_count != 0) { deviceInterface->up_count++; @@ -526,7 +528,7 @@ net_device_interface *deviceInterface = ((net_interface_private *)protocol->interface)->device_interface; - // TODO: locking! + // This function is called with the RX lock held. if (deviceInterface->up_count == 0) return; From hugosantos at gmail.com Sun Apr 8 08:04:30 2007 From: hugosantos at gmail.com (Hugo Santos) Date: Sun, 8 Apr 2007 07:04:30 +0100 Subject: [Haiku-commits] r20611 - haiku/trunk/src/add-ons/kernel/network/stack In-Reply-To: <200704080550.l385oZss001513@sheep.berlios.de> References: <200704080550.l385oZss001513@sheep.berlios.de> Message-ID: <9c46321e0704072304h698262b9o76985212e1c4bda3@mail.gmail.com> Hi all, I would like additional pairs of eyes (or one eye if you are patched pirate, yar!) checking for problems in this commit. I spent a couple days thinking about the approach i should take here with locking, and this was my third iteration. It isn't very pretty but is working here without problems, let me know if you guys find any races or have better suggestions. A bit of background. In order to protect the visibility of changed flags (crucial to get the device_reader thread to go down on time) and both the monitors and readers lists i introduced an RX lock in net_device_interface which protects the RX path in the device_reader function. In order to avoid all deadlocks i enforce a strict locking policy in all callers which involve any of this data: any of the "inner locks" (domain locks, etc) must be obtained with the RX lock held if it will be required (for instance, when setting the interface down). I tried to add as many comments as i thought were required regarding the locking and who helds what so people don't change it in a way that breaks it. There is a still an issue with the locking which i point out in a later commit, in interface_protocol_send_data the monitors list is accessed, but we can't obtain the RX lock as it would break the locking protocol. I plan to fix this in a future commit, but meanwhile i saw some pending TODOs in the ARP module that seem important. Removing interfaces is now working, but not if there is activity -- removing routes on interface removal is still not safe as i point out in one of the big comments. Let me know of your comments, Hugo On 4/8/07, hugosantos at mail.berlios.de wrote: > Author: hugosantos > Date: 2007-04-08 07:50:25 +0200 (Sun, 08 Apr 2007) > New Revision: 20611 > ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20611&view=rev > > Modified: > haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp > haiku/trunk/src/add-ons/kernel/network/stack/domains.cpp > haiku/trunk/src/add-ons/kernel/network/stack/domains.h > haiku/trunk/src/add-ons/kernel/network/stack/interfaces.cpp > haiku/trunk/src/add-ons/kernel/network/stack/interfaces.h > haiku/trunk/src/add-ons/kernel/network/stack/routes.cpp > Log: > introduced net_device_interface level locking. > > > Modified: haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp > =================================================================== > --- haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp 2007-04-08 02:21:10 UTC (rev 20610) > +++ haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp 2007-04-08 05:50:25 UTC (rev 20611) > @@ -45,9 +45,13 @@ > net_device *device = interface->device; > status_t status = B_OK; > > - while ((device->flags & IFF_UP) != 0) { > + BenaphoreLocker rx_lock(interface->rx_lock); > + > + while (device->flags & IFF_UP) { > net_buffer *buffer; > + rx_lock.Unlock(); > status = device->module->receive_data(device, &buffer); > + rx_lock.Lock(); > if (status == B_OK) { > //dprintf("received buffer of %ld bytes length\n", buffer->size); > > @@ -100,10 +104,6 @@ > // and the receive_data() above should have been > // interrupted. One check should be enough, specially > // considering the snooze above. > - // > - // TODO: make sure that when receive_data() returns > - // after closing the new device->flags are > - // already visible in all processors. > } > > return status; > @@ -180,6 +180,52 @@ > } > > > +static status_t > +datalink_control_interface(net_domain_private *domain, int32 option, > + void *value, size_t *_length, size_t expected, bool getByName) > +{ > + if (*_length < expected) > + return B_BAD_VALUE; > + > + ifreq request; > + memset(&request, 0, sizeof(request)); > + > + if (user_memcpy(&request, value, expected) < B_OK) > + return B_BAD_ADDRESS; > + > + BenaphoreLocker _(domain->lock); > + net_interface *interface = NULL; > + > + if (getByName) > + interface = find_interface(domain, request.ifr_name); > + else > + interface = find_interface(domain, request.ifr_index); > + > + status_t status = (interface == NULL) ? ENODEV : B_OK; > + > + switch (option) { > + case SIOCGIFINDEX: > + if (interface) > + request.ifr_index = interface->index; > + else > + request.ifr_index = 0; > + break; > + > + case SIOCGIFNAME: > + if (interface) > + strlcpy(request.ifr_name, interface->name, IF_NAMESIZE); > + else > + status = B_BAD_VALUE; // TODO should be ENXIO? > + break; > + } > + > + if (status < B_OK) > + return status; > + > + return user_memcpy(value, &request, sizeof(ifreq)); > +} > + > + > // #pragma mark - datalink module > > > @@ -195,51 +241,20 @@ > > switch (option) { > case SIOCGIFINDEX: > - { > - // get index of interface > - struct ifreq request; > - if (user_memcpy(&request, value, IF_NAMESIZE) < B_OK) > - return B_BAD_ADDRESS; > - > - benaphore_lock(&domain->lock); > - > - net_interface *interface = find_interface(domain, > - request.ifr_name); > - if (interface != NULL) > - request.ifr_index = interface->index; > - else > - request.ifr_index = 0; > - > - benaphore_unlock(&domain->lock); > - > - if (request.ifr_index == 0) > - return ENODEV; > - > - return user_memcpy(value, &request, sizeof(struct ifreq)); > - } > + return datalink_control_interface(domain, option, value, _length, > + IF_NAMESIZE, true); > case SIOCGIFNAME: > + return datalink_control_interface(domain, option, value, _length, > + sizeof(ifreq), false); > + > + case SIOCDIFADDR: > + case SIOCSIFFLAGS: > { > - // get name of interface via index > struct ifreq request; > if (user_memcpy(&request, value, sizeof(struct ifreq)) < B_OK) > return B_BAD_ADDRESS; > > - benaphore_lock(&domain->lock); > - status_t status = B_OK; > - > - net_interface *interface = find_interface(domain, > - request.ifr_index); > - if (interface != NULL) > - strlcpy(request.ifr_name, interface->name, IF_NAMESIZE); > - else > - status = B_BAD_VALUE; > - > - benaphore_unlock(&domain->lock); > - > - if (status < B_OK) > - return status; > - > - return user_memcpy(value, &request, sizeof(struct ifreq)); > + return domain_interface_control(domain, option, &request); > } > > case SIOCAIFADDR: > @@ -251,22 +266,7 @@ > > return add_interface_to_domain(domain, request); > } > - case SIOCDIFADDR: > - { > - // remove interface address > - struct ifreq request; > - if (user_memcpy(&request, value, sizeof(struct ifreq)) < B_OK) > - return B_BAD_ADDRESS; > > - BenaphoreLocker _(domain->lock); > - > - net_interface *interface = find_interface(domain, > - request.ifr_name); > - if (interface == NULL) > - return ENODEV; > - return remove_interface_from_domain(interface); > - } > - > case SIOCGIFCOUNT: > { > // count number of interfaces > @@ -314,46 +314,20 @@ > default: > { > // try to pass the request to an existing interface > - > struct ifreq request; > if (user_memcpy(&request, value, sizeof(struct ifreq)) < B_OK) > return B_BAD_ADDRESS; > > BenaphoreLocker _(domain->lock); > - status_t status = B_OK; > > net_interface *interface = find_interface(domain, > request.ifr_name); > - if (interface != NULL) { > - // filter out bringing the interface up or down > - if (option == SIOCSIFFLAGS) { > - if (((uint32)request.ifr_flags & IFF_UP) > - != (interface->flags & IFF_UP)) { > - if ((interface->flags & IFF_UP) != 0) { > - interface_set_down(interface); > - } else { > - // bring it up > - status = interface->first_info->interface_up( > - interface->first_protocol); > - if (status == B_OK) { > - interface->flags |= IFF_UP > - | (interface->device->media & IFM_ACTIVE > - ? IFF_LINK : 0); > - } > - } > - } > + if (interface == NULL) > + return B_BAD_VALUE; > > - if (status == B_OK) > - interface->flags |= request.ifr_flags & ~(IFF_UP | IFF_LINK); > - } else { > - // pass the request into the datalink protocol stack > - status = interface->first_info->control( > - interface->first_protocol, option, value, *_length); > - } > - } else > - status = B_BAD_VALUE; > - > - return status; > + // pass the request into the datalink protocol stack > + return interface->first_info->control( > + interface->first_protocol, option, value, *_length); > } > } > return B_BAD_VALUE; > > Modified: haiku/trunk/src/add-ons/kernel/network/stack/domains.cpp > =================================================================== > --- haiku/trunk/src/add-ons/kernel/network/stack/domains.cpp 2007-04-08 02:21:10 UTC (rev 20610) > +++ haiku/trunk/src/add-ons/kernel/network/stack/domains.cpp 2007-04-08 05:50:25 UTC (rev 20611) > @@ -10,6 +10,7 @@ > #include "domains.h" > #include "interfaces.h" > #include "utility.h" > +#include "stack_private.h" > > #include > > @@ -21,6 +22,7 @@ > #include > #include > #include > +#include > > > #define TRACE_DOMAINS > @@ -196,6 +198,64 @@ > } > > > +status_t > +domain_interface_control(net_domain_private *domain, int32 option, > + ifreq *request) > +{ > + const char *name = request->ifr_name; > + status_t status = B_OK; > + > + net_device_interface *device = get_device_interface(name, false); > + if (device == NULL) > + return ENODEV; > + else { > + // The locking protocol dictates that if both the RX lock > + // and domain locks are required, we MUST obtain the RX > + // lock before the domain lock. This order MUST NOT ever > + // be reversed under the penalty of deadlock. > + BenaphoreLocker _1(device->rx_lock); > + BenaphoreLocker _2(domain->lock); > + > + net_interface *interface = find_interface(domain, name); > + if (interface != NULL) { > + switch (option) { > + case SIOCDIFADDR: > + remove_interface_from_domain(interface); > + break; > + > + case SIOCSIFFLAGS: > + if (((uint32)request->ifr_flags & IFF_UP) > + != (interface->flags & IFF_UP)) { > + if (interface->flags & IFF_UP) { > + interface_set_down(interface); > + } else { > + status = interface->first_info->interface_up( > + interface->first_protocol); > + if (status == B_OK) { > + interface->flags |= IFF_UP; > + // TODO this doesn't belong here > + if (interface->device->media & IFM_ACTIVE) > + interface->flags |= IFF_LINK; > + } > + } > + } > + > + if (status == B_OK) > + interface->flags |= request->ifr_flags & ~(IFF_UP | IFF_LINK); > + break; > + } > + } > + } > + > + // If the SIOCDIFADDR call above removed the last interface > + // associated with the device interface, this put_() will > + // effectively remove the interface > + put_device_interface(device); > + > + return status; > +} > + > + > void > domain_interfaces_link_changed(net_device *device) > { > > Modified: haiku/trunk/src/add-ons/kernel/network/stack/domains.h > =================================================================== > --- haiku/trunk/src/add-ons/kernel/network/stack/domains.h 2007-04-08 02:21:10 UTC (rev 20610) > +++ haiku/trunk/src/add-ons/kernel/network/stack/domains.h 2007-04-08 05:50:25 UTC (rev 20611) > @@ -39,6 +39,8 @@ > void domain_interfaces_link_changed(net_device *device); > void domain_interface_went_down(net_interface *); > void domain_removed_device_interface(net_device_interface *); > +status_t domain_interface_control(net_domain_private *domain, int32 option, > + struct ifreq *request); > > net_domain *get_domain(int family); > status_t register_domain(int family, const char *name, > > Modified: haiku/trunk/src/add-ons/kernel/network/stack/interfaces.cpp > =================================================================== > --- haiku/trunk/src/add-ons/kernel/network/stack/interfaces.cpp 2007-04-08 02:21:10 UTC (rev 20610) > +++ haiku/trunk/src/add-ons/kernel/network/stack/interfaces.cpp 2007-04-08 05:50:25 UTC (rev 20611) > @@ -325,6 +325,9 @@ > > interface->module->uninit_device(interface->device); > put_module(interface->module->info.name); > + > + benaphore_destroy(&interface->rx_lock); > + delete interface; > } > > > @@ -355,7 +358,7 @@ > If the interface does not yet exist, a new one is created. > */ > struct net_device_interface * > -get_device_interface(const char *name) > +get_device_interface(const char *name, bool create) > { > BenaphoreLocker locker(sInterfaceLock); > > @@ -367,6 +370,9 @@ > // try to recreate interface - it just got removed > } > > + if (!create) > + return NULL; > + > void *cookie = open_module_list("network/devices"); > if (cookie == NULL) > return NULL; > @@ -387,23 +393,25 @@ > // create new module interface for this > interface = new (std::nothrow) net_device_interface; > if (interface != NULL) { > - interface->name = device->name; > - interface->module = module; > - interface->device = device; > - interface->up_count = 0; > - interface->ref_count = 1; > - interface->deframe_func = NULL; > - interface->deframe_ref_count = 0; > + if (benaphore_init(&interface->rx_lock, "rx lock") >= B_OK) { > + interface->name = device->name; > + interface->module = module; > + interface->device = device; > + interface->up_count = 0; > + interface->ref_count = 1; > + interface->deframe_func = NULL; > + interface->deframe_ref_count = 0; > > - device->index = ++sDeviceIndex; > - device->module = module; > + device->index = ++sDeviceIndex; > + device->module = module; > > - sInterfaces.Add(interface); > - return interface; > - } else > - module->uninit_device(device); > + sInterfaces.Add(interface); > + return interface; > + } > + delete interface; > + } > + module->uninit_device(device); > } > - > put_module(moduleName); > } > } > @@ -415,6 +423,19 @@ > void > down_device_interface(net_device_interface *interface) > { > + // RX lock must be held when calling down_device_interface. > + // Known callers are `interface_protocol_down' which gets > + // here via one of the following paths: > + // > + // - domain_interface_control() [rx lock held, domain lock held] > + // interface_set_down() > + // interface_protocol_down() > + // > + // - domain_interface_control() [rx lock held, domain lock held] > + // remove_interface_from_domain() > + // delete_interface() > + // interface_set_down() > + > net_device *device = interface->device; > > dprintf("down_device_interface(%s)\n", interface->name); > @@ -422,13 +443,17 @@ > device->flags &= ~IFF_UP; > interface->module->down(device); > > - // TODO: there is a race condition between the previous > - // ->down and device->module->receive_data which > - // locks us here waiting for the reader_thread > + thread_id reader_thread = interface->reader_thread; > > + // one of the callers must hold a reference to the net_device_interface > + // usually it is one of the net_interfaces. > + benaphore_unlock(&interface->rx_lock); > + > // make sure the reader thread is gone before shutting down the interface > status_t status; > - wait_for_thread(interface->reader_thread, &status); > + wait_for_thread(reader_thread, &status); > + > + benaphore_lock(&interface->rx_lock); > } > > > @@ -449,6 +474,8 @@ > if (interface == NULL) > return ENODEV; > > + BenaphoreLocker _(interface->rx_lock); > + > if (--interface->deframe_ref_count == 0) > interface->deframe_func = NULL; > > @@ -476,6 +503,8 @@ > if (interface == NULL) > return ENODEV; > > + BenaphoreLocker _(interface->rx_lock); > + > if (interface->deframe_func != NULL && interface->deframe_func != deframeFunc) > return B_ERROR; > > @@ -508,6 +537,8 @@ > if (interface == NULL) > return ENODEV; > > + BenaphoreLocker _(interface->rx_lock); > + > // see if such a handler already for this device > > DeviceHandlerList::Iterator iterator = interface->receive_funcs.GetIterator(); > @@ -542,6 +573,8 @@ > if (interface == NULL) > return ENODEV; > > + BenaphoreLocker _(interface->rx_lock); > + > // search for the handler > > DeviceHandlerList::Iterator iterator = interface->receive_funcs.GetIterator(); > @@ -571,6 +604,8 @@ > if (interface == NULL) > return ENODEV; > > + BenaphoreLocker _(interface->rx_lock); > + > // Add new monitor > > net_device_monitor *monitor = new (std::nothrow) net_device_monitor; > @@ -595,6 +630,8 @@ > if (interface == NULL) > return ENODEV; > > + BenaphoreLocker _(interface->rx_lock); > + > // search for the monitor > > DeviceMonitorList::Iterator iterator = interface->monitor_funcs.GetIterator(); > @@ -644,6 +681,8 @@ > // This is very complex, refer to delete_interface() for > // further details. > > + BenaphoreLocker _(interface->rx_lock); > + > // this will possibly call: > // remove_interface_from_domain() [domain gets locked] > // delete_interface() > > Modified: haiku/trunk/src/add-ons/kernel/network/stack/interfaces.h > =================================================================== > --- haiku/trunk/src/add-ons/kernel/network/stack/interfaces.h 2007-04-08 02:21:10 UTC (rev 20610) > +++ haiku/trunk/src/add-ons/kernel/network/stack/interfaces.h 2007-04-08 05:50:25 UTC (rev 20611) > @@ -44,6 +44,8 @@ > > DeviceMonitorList monitor_funcs; > DeviceHandlerList receive_funcs; > + > + benaphore rx_lock; > }; > > typedef DoublyLinkedList DeviceInterfaceList; > @@ -78,7 +80,8 @@ > status_t list_device_interfaces(void *buffer, size_t *_bufferSize); > void put_device_interface(struct net_device_interface *interface); > struct net_device_interface *get_device_interface(uint32 index); > -struct net_device_interface *get_device_interface(const char *name); > +struct net_device_interface *get_device_interface(const char *name, > + bool create = true); > void down_device_interface(net_device_interface *interface); > > // devices > > Modified: haiku/trunk/src/add-ons/kernel/network/stack/routes.cpp > =================================================================== > --- haiku/trunk/src/add-ons/kernel/network/stack/routes.cpp 2007-04-08 02:21:10 UTC (rev 20610) > +++ haiku/trunk/src/add-ons/kernel/network/stack/routes.cpp 2007-04-08 05:50:25 UTC (rev 20611) > @@ -506,9 +506,19 @@ > while (iterator.HasNext()) { > net_route *route = iterator.Next(); > > - // TODO handle refcounting, if the route needs to linger > - // for some reason we should set interface or > - // something of the sorts that invalidates it's reference > + // TODO If we are removing the interface this will bork. > + // Consider the following case: > + // [thread 1] ipv4_send_data() > + // [thread 1] get_route() [domain locked, unlocked] <- route > + // [thread 2] ... [domain locked] > + // [thread 2] invalidate_routes() > + // [thread 2] remove_route() <- route > + // [thread 1] ... ipv4_send_data() accesses `route'. Bork bork. > + // > + // We could either add per-route locks (expensive) or > + // lock the domain throughout the send_data() routine. > + // These are the easy solutions, need to think about this. -hugo > + > if (route->interface == interface) > remove_route(domain, route); > } > > _______________________________________________ > Haiku-commits mailing list > Haiku-commits at lists.berlios.de > https://lists.berlios.de/mailman/listinfo/haiku-commits > From hugosantos at mail.berlios.de Sun Apr 8 11:16:06 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Sun, 8 Apr 2007 11:16:06 +0200 Subject: [Haiku-commits] r20614 - in haiku/trunk: headers/private/net src/add-ons/kernel/network/stack Message-ID: <200704080916.l389G6pK010206@sheep.berlios.de> Author: hugosantos Date: 2007-04-08 11:15:52 +0200 (Sun, 08 Apr 2007) New Revision: 20614 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20614&view=rev Modified: haiku/trunk/headers/private/net/net_stack.h haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp haiku/trunk/src/add-ons/kernel/network/stack/interfaces.cpp haiku/trunk/src/add-ons/kernel/network/stack/interfaces.h haiku/trunk/src/add-ons/kernel/network/stack/link.cpp haiku/trunk/src/add-ons/kernel/network/stack/utility.cpp haiku/trunk/src/add-ons/kernel/network/stack/utility.h Log: Prepared net_device_monitor to accept device removal events. - Introduced public net_device_monitor. - Changed the link protocol to maintain a lock per instance instead of inside the FIFO. Now all of the link instance data is protected. - Adapted the link protocol to use net_device_monitor. - Introduced a private Fifo class which doesn't maintain it's own lock. - Maybe we should add something like a public net_protocol_implementation which maintains a fifo and a benaphore? With the fifo using the structure's lock instead of maintaining it's own. Modified: haiku/trunk/headers/private/net/net_stack.h =================================================================== --- haiku/trunk/headers/private/net/net_stack.h 2007-04-08 05:50:49 UTC (rev 20613) +++ haiku/trunk/headers/private/net/net_stack.h 2007-04-08 09:15:52 UTC (rev 20614) @@ -37,6 +37,21 @@ typedef int32 (*net_deframe_func)(struct net_device *device, struct net_buffer *buffer); typedef status_t (*net_receive_func)(void *cookie, struct net_buffer *buffer); +enum { + B_DEVICE_GOING_UP = 1, + B_DEVICE_GOING_DOWN, + B_DEVICE_BEING_REMOVED, +}; + +struct net_device_monitor { + struct list_link link; + void *cookie; + + status_t (*receive)(struct net_device_monitor *monitor, + struct net_buffer *buffer); + void (*event)(struct net_device_monitor *monitor, int32 event); +}; + struct net_stack_module_info { module_info info; @@ -68,9 +83,9 @@ status_t (*unregister_device_handler)(struct net_device *device, int32 type); status_t (*register_device_monitor)(struct net_device *device, - net_receive_func receiveFunc, void *cookie); + struct net_device_monitor *monitor); status_t (*unregister_device_monitor)(struct net_device *device, - net_receive_func receiveFunc, void *cookie); + struct net_device_monitor *monitor); status_t (*device_link_changed)(struct net_device *device); status_t (*device_removed)(struct net_device *device); Modified: haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp 2007-04-08 05:50:49 UTC (rev 20613) +++ haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp 2007-04-08 09:15:52 UTC (rev 20614) @@ -60,7 +60,7 @@ = interface->monitor_funcs.GetIterator(); while (iterator.HasNext()) { net_device_monitor *monitor = iterator.Next(); - monitor->func(monitor->cookie, buffer); + monitor->receive(monitor, buffer); } int32 type = interface->deframe_func(device, buffer); @@ -478,7 +478,7 @@ interface->device_interface->monitor_funcs.GetIterator(); while (iterator.HasNext()) { net_device_monitor *monitor = iterator.Next(); - monitor->func(monitor->cookie, buffer); + monitor->receive(monitor, buffer); } return protocol->device_module->send_data(protocol->device, buffer); Modified: haiku/trunk/src/add-ons/kernel/network/stack/interfaces.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/interfaces.cpp 2007-04-08 05:50:49 UTC (rev 20613) +++ haiku/trunk/src/add-ons/kernel/network/stack/interfaces.cpp 2007-04-08 09:15:52 UTC (rev 20614) @@ -593,9 +593,11 @@ status_t -register_device_monitor(struct net_device *device, - net_receive_func receiveFunc, void *cookie) +register_device_monitor(net_device *device, net_device_monitor *monitor) { + if (monitor->receive == NULL || monitor->event == NULL) + return B_BAD_VALUE; + BenaphoreLocker locker(sInterfaceLock); // find device interface for this device @@ -604,23 +606,13 @@ return ENODEV; BenaphoreLocker _(interface->rx_lock); - - // Add new monitor - - net_device_monitor *monitor = new (std::nothrow) net_device_monitor; - if (monitor == NULL) - return B_NO_MEMORY; - - monitor->func = receiveFunc; - monitor->cookie = cookie; interface->monitor_funcs.Add(monitor); return B_OK; } status_t -unregister_device_monitor(struct net_device *device, - net_receive_func receiveFunc, void *cookie) +unregister_device_monitor(net_device *device, net_device_monitor *monitor) { BenaphoreLocker locker(sInterfaceLock); @@ -635,12 +627,8 @@ DeviceMonitorList::Iterator iterator = interface->monitor_funcs.GetIterator(); while (iterator.HasNext()) { - net_device_monitor *monitor = iterator.Next(); - - if (monitor->cookie == cookie && monitor->func == receiveFunc) { - // found it + if (iterator.Next() == monitor) { iterator.Remove(); - delete monitor; return B_OK; } } Modified: haiku/trunk/src/add-ons/kernel/network/stack/interfaces.h =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/interfaces.h 2007-04-08 05:50:49 UTC (rev 20613) +++ haiku/trunk/src/add-ons/kernel/network/stack/interfaces.h 2007-04-08 09:15:52 UTC (rev 20614) @@ -21,14 +21,11 @@ void *cookie; }; -struct net_device_monitor : public DoublyLinkedListLinkImpl { - net_receive_func func; - void *cookie; -}; - typedef DoublyLinkedList DeviceHandlerList; -typedef DoublyLinkedList DeviceMonitorList; +typedef DoublyLinkedList > DeviceMonitorList; + struct net_device_interface : DoublyLinkedListLinkImpl { //struct list_link link; const char *name; @@ -93,9 +90,9 @@ net_receive_func receiveFunc, void *cookie); status_t unregister_device_handler(struct net_device *device, int32 type); status_t register_device_monitor(struct net_device *device, - net_receive_func receiveFunc, void *cookie); + struct net_device_monitor *monitor); status_t unregister_device_monitor(struct net_device *device, - net_receive_func receiveFunc, void *cookie); + struct net_device_monitor *monitor); status_t device_link_changed(net_device *device); status_t device_removed(net_device *device); Modified: haiku/trunk/src/add-ons/kernel/network/stack/link.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/link.cpp 2007-04-08 05:50:49 UTC (rev 20613) +++ haiku/trunk/src/add-ons/kernel/network/stack/link.cpp 2007-04-08 09:15:52 UTC (rev 20614) @@ -16,6 +16,9 @@ #include +#include +#include + #include #include @@ -25,61 +28,196 @@ #include -struct link_protocol : net_protocol { - net_fifo fifo; - char registered_interface[IF_NAMESIZE]; - bool registered_monitor; +class LinkProtocol : public net_protocol { +public: + LinkProtocol(); + ~LinkProtocol(); + + status_t InitCheck() const; + + status_t StartMonitoring(const char *); + status_t StopMonitoring(); + + ssize_t ReadData(size_t numBytes, uint32 flags, net_buffer **_buffer); + ssize_t ReadAvail() const; + +private: + status_t _Enqueue(net_buffer *buffer); + status_t _Unregister(); + + mutable benaphore fLock; + Fifo fFifo; + + net_device_monitor fMonitor; + net_device_interface *fMonitoredDevice; + + static status_t _MonitorData(net_device_monitor *monitor, net_buffer *buffer); + static void _MonitorEvent(net_device_monitor *monitor, int32 event); }; struct net_domain *sDomain; -static status_t -link_monitor_data(void *cookie, net_buffer *packet) +LinkProtocol::LinkProtocol() + : fFifo("packet monitor fifo", 65536) { - link_protocol *protocol = (link_protocol *)cookie; + benaphore_init(&fLock, "packet monitor lock"); - return fifo_socket_enqueue_buffer(&protocol->fifo, protocol->socket, - B_SELECT_READ, packet); + fMonitor.cookie = this; + fMonitor.receive = _MonitorData; + fMonitor.event = _MonitorEvent; + fMonitoredDevice = NULL; } +LinkProtocol::~LinkProtocol() +{ + if (fMonitoredDevice) { + unregister_device_monitor(fMonitoredDevice->device, &fMonitor); + put_device_interface(fMonitoredDevice); + } + + benaphore_destroy(&fLock); +} + + +status_t +LinkProtocol::InitCheck() const +{ + return fLock.sem >= 0 && fFifo.InitCheck(); +} + + +status_t +LinkProtocol::StartMonitoring(const char *deviceName) +{ + BenaphoreLocker _(fLock); + + if (fMonitoredDevice) + return B_BUSY; + + net_device_interface *interface = get_device_interface(deviceName); + if (interface == NULL) + return ENODEV; + + status_t status = register_device_monitor(interface->device, &fMonitor); + if (status < B_OK) { + put_device_interface(interface); + return status; + } + + fMonitoredDevice = interface; + return B_OK; +} + + +status_t +LinkProtocol::StopMonitoring() +{ + BenaphoreLocker _(fLock); + + // TODO compare our device with the supplied device name? + return _Unregister(); +} + + +ssize_t +LinkProtocol::ReadData(size_t numBytes, uint32 flags, net_buffer **_buffer) +{ + BenaphoreLocker _(fLock); + + if (fMonitoredDevice == NULL) { + if (fFifo.current_bytes == 0) + return ENODEV; + } + + net_buffer *buffer; + status_t status = fFifo.Dequeue(&fLock, flags, socket->receive.timeout, + &buffer); + if (status < B_OK) + return status; + + *_buffer = buffer; + return B_OK; +} + + +ssize_t +LinkProtocol::ReadAvail() const +{ + BenaphoreLocker _(fLock); + if (fMonitoredDevice == NULL) + return ECONNRESET; + return fFifo.current_bytes; +} + + +status_t +LinkProtocol::_Unregister() +{ + if (fMonitoredDevice == NULL) + return B_BAD_VALUE; + + status_t status = unregister_device_monitor(fMonitoredDevice->device, + &fMonitor); + put_device_interface(fMonitoredDevice); + fMonitoredDevice = NULL; + + return status; +} + + +status_t +LinkProtocol::_Enqueue(net_buffer *buffer) +{ + BenaphoreLocker _(fLock); + return fFifo.EnqueueAndNotify(buffer, socket, B_SELECT_READ); +} + + +status_t +LinkProtocol::_MonitorData(net_device_monitor *monitor, net_buffer *packet) +{ + return ((LinkProtocol *)monitor->cookie)->_Enqueue(packet); +} + + +void +LinkProtocol::_MonitorEvent(net_device_monitor *monitor, int32 event) +{ + LinkProtocol *protocol = (LinkProtocol *)monitor->cookie; + + // We currently maintain the monitor while the device is down + if (event == B_DEVICE_BEING_REMOVED) { + BenaphoreLocker _(protocol->fLock); + + protocol->_Unregister(); + notify_socket(protocol->socket, B_SELECT_READ, ECONNRESET); + } +} + + // #pragma mark - net_protocol * link_init_protocol(net_socket *socket) { - link_protocol *protocol = new (std::nothrow) link_protocol; - if (protocol == NULL) - return NULL; - - if (init_fifo(&protocol->fifo, "packet monitor socket", 65536) < B_OK) { + LinkProtocol *protocol = new (std::nothrow) LinkProtocol(); + if (protocol && protocol->InitCheck() < B_OK) { delete protocol; return NULL; } - protocol->registered_monitor = false; return protocol; } status_t -link_uninit_protocol(net_protocol *_protocol) +link_uninit_protocol(net_protocol *protocol) { - link_protocol *protocol = (link_protocol *)_protocol; - - if (protocol->registered_monitor) { - net_device_interface *interface = get_device_interface(protocol->registered_interface); - if (interface != NULL) { - unregister_device_monitor(interface->device, link_monitor_data, protocol); - put_device_interface(interface); - } - } - - uninit_fifo(&protocol->fifo); - delete protocol; + delete (LinkProtocol *)protocol; return B_OK; } @@ -123,8 +261,10 @@ link_control(net_protocol *_protocol, int level, int option, void *value, size_t *_length) { - link_protocol *protocol = (link_protocol *)_protocol; + LinkProtocol *protocol = (LinkProtocol *)_protocol; + // TODO All of this common functionality should be elsewhere + switch (option) { case SIOCGIFINDEX: { @@ -203,58 +343,15 @@ case SIOCSPACKETCAP: { - // start packet monitoring - - if (protocol->registered_monitor) - return B_BUSY; - struct ifreq request; if (user_memcpy(&request, value, IF_NAMESIZE) < B_OK) return B_BAD_ADDRESS; - net_device_interface *interface = get_device_interface(request.ifr_name); - status_t status; - if (interface != NULL) { - status = register_device_monitor(interface->device, - link_monitor_data, protocol); - if (status == B_OK) { - // we're now registered - strlcpy(protocol->registered_interface, request.ifr_name, IF_NAMESIZE); - protocol->registered_monitor = true; - } - put_device_interface(interface); - } else - status = ENODEV; - - return status; + return protocol->StartMonitoring(request.ifr_name); } case SIOCCPACKETCAP: - { - // stop packet monitoring - - if (!protocol->registered_monitor) - return B_BAD_VALUE; - - struct ifreq request; - if (user_memcpy(&request, value, IF_NAMESIZE) < B_OK) - return B_BAD_ADDRESS; - - net_device_interface *interface = get_device_interface(request.ifr_name); - status_t status; - if (interface != NULL) { - status = unregister_device_monitor(interface->device, - link_monitor_data, protocol); - if (status == B_OK) { - // we're now no longer registered - protocol->registered_monitor = false; - } - put_device_interface(interface); - } else - status = ENODEV; - - return status; - } + return protocol->StopMonitoring(); } return datalink_control(sDomain, option, value, _length); @@ -313,29 +410,17 @@ status_t -link_read_data(net_protocol *_protocol, size_t numBytes, uint32 flags, +link_read_data(net_protocol *protocol, size_t numBytes, uint32 flags, net_buffer **_buffer) { - link_protocol *protocol = (link_protocol *)_protocol; - - dprintf("link_read is waiting for data...\n"); - - net_buffer *buffer; - status_t status = fifo_dequeue_buffer(&protocol->fifo, - flags, protocol->socket->receive.timeout, &buffer); - if (status < B_OK) - return status; - - *_buffer = buffer; - return B_OK; + return ((LinkProtocol *)protocol)->ReadData(numBytes, flags, _buffer); } ssize_t -link_read_avail(net_protocol *_protocol) +link_read_avail(net_protocol *protocol) { - link_protocol *protocol = (link_protocol *)_protocol; - return protocol->fifo.current_bytes; + return ((LinkProtocol *)protocol)->ReadAvail(); } Modified: haiku/trunk/src/add-ons/kernel/network/stack/utility.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/utility.cpp 2007-04-08 05:50:49 UTC (rev 20613) +++ haiku/trunk/src/add-ons/kernel/network/stack/utility.cpp 2007-04-08 09:15:52 UTC (rev 20614) @@ -24,6 +24,126 @@ static bigtime_t sTimerTimeout; +template static inline status_t +base_fifo_init(FifoType *fifo, const char *name, size_t maxBytes) +{ + fifo->notify = create_sem(1, name); + fifo->max_bytes = maxBytes; + fifo->current_bytes = 0; + fifo->waiting = 0; + list_init(&fifo->buffers); + + return fifo->notify; +} + + +template static inline status_t +base_fifo_enqueue_buffer(FifoType *fifo, net_buffer *buffer) +{ + if (fifo->max_bytes > 0 && fifo->current_bytes + buffer->size > fifo->max_bytes) + return ENOBUFS; + + list_add_item(&fifo->buffers, buffer); + fifo->current_bytes += buffer->size; + + if (fifo->waiting > 0) { + fifo->waiting--; + release_sem_etc(fifo->notify, 1, B_DO_NOT_RESCHEDULE); + // we still hold the benaphore lock, so it makes no sense + // to reschedule after having released the sync semaphore + } + + return B_OK; +} + + +/*! + Gets the first buffer from the FIFO. If there is no buffer, it + will wait depending on the \a flags and \a timeout. + The following flags are supported (the rest is ignored): + MSG_DONTWAIT - ignores the timeout and never wait for a buffer; if your + socket is O_NONBLOCK, you should specify this flag. A \a timeout of + zero is equivalent to this flag, though. + MSG_PEEK - returns a clone of the buffer and keep the original + in the FIFO. +*/ +template static inline ssize_t +base_fifo_dequeue_buffer(FifoType *fifo, benaphore *lock, uint32 flags, + bigtime_t timeout, net_buffer **_buffer) +{ + // this function is called with `lock' held. + bool dontWait = (flags & MSG_DONTWAIT) != 0 || timeout == 0; + status_t status; + + while (true) { + net_buffer *buffer = (net_buffer *)list_get_first_item(&fifo->buffers); + if (buffer != NULL) { + if ((flags & MSG_PEEK) != 0) { + // we need to clone the buffer for inspection; we can't give a + // handle to a buffer that we're still using + buffer = gNetBufferModule.clone(buffer, false); + if (buffer == NULL) { + status = B_NO_MEMORY; + break; + } + } else { + list_remove_item(&fifo->buffers, buffer); + fifo->current_bytes -= buffer->size; + } + + *_buffer = buffer; + status = B_OK; + break; + } + + if (!dontWait) + fifo->waiting++; + + // we need to wait until a new buffer becomes available + benaphore_unlock(lock); + + if (dontWait) + return B_WOULD_BLOCK; + + status = acquire_sem_etc(fifo->notify, 1, + B_CAN_INTERRUPT | B_RELATIVE_TIMEOUT, timeout); + if (status < B_OK) + return status; + + // try again + benaphore_lock(lock); + } + + if ((flags & MSG_PEEK) != 0 && fifo->waiting > 0) { + // another thread is waiting for data, since we didn't eat the + // buffer, it gets it + fifo->waiting--; + release_sem_etc(fifo->notify, 1, B_DO_NOT_RESCHEDULE); + } + + return status; +} + + +template static inline status_t +base_fifo_clear(FifoType *fifo) +{ + while (true) { + net_buffer *buffer = (net_buffer *)list_remove_head_item(&fifo->buffers); + if (buffer == NULL) + break; + + gNetBufferModule.free(buffer); + } + + fifo->current_bytes = 0; + return B_OK; +} + + +// #pragma mark - + + void * UserBuffer::Copy(void *source, size_t length) { @@ -101,150 +221,111 @@ // #pragma mark - FIFOs -status_t -init_fifo(net_fifo *fifo, const char *name, size_t maxBytes) +Fifo::Fifo(const char *name, size_t maxBytes) { - status_t status = benaphore_init(&fifo->lock, name); - if (status < B_OK) - return status; + base_fifo_init(this, name, maxBytes); +} - fifo->notify = create_sem(1, name); - if (fifo->notify < B_OK) { - benaphore_destroy(&fifo->lock); - return fifo->notify; - } - fifo->max_bytes = maxBytes; - fifo->current_bytes = 0; - fifo->waiting = 0; +Fifo::~Fifo() +{ + Clear(); + delete_sem(notify); +} - list_init(&fifo->buffers); - return B_OK; +status_t +Fifo::InitCheck() const +{ + return !(notify < B_OK); } -void -uninit_fifo(net_fifo *fifo) +status_t +Fifo::Enqueue(net_buffer *buffer) { - clear_fifo(fifo); - - benaphore_destroy(&fifo->lock); - delete_sem(fifo->notify); + return base_fifo_enqueue_buffer(this, buffer); } -static status_t -_fifo_enqueue_buffer(net_fifo *fifo, net_buffer *buffer) +status_t +Fifo::EnqueueAndNotify(net_buffer *_buffer, net_socket *socket, uint8 event) { - if (fifo->max_bytes > 0 && fifo->current_bytes + buffer->size > fifo->max_bytes) - return ENOBUFS; + net_buffer *buffer = gNetBufferModule.clone(_buffer, false); + if (buffer == NULL) + return B_NO_MEMORY; - list_add_item(&fifo->buffers, buffer); - fifo->current_bytes += buffer->size; + status_t status = Enqueue(buffer); + if (status < B_OK) + gNetBufferModule.free(buffer); + else + notify_socket(socket, event, current_bytes); - if (fifo->waiting > 0) { - fifo->waiting--; - release_sem_etc(fifo->notify, 1, B_DO_NOT_RESCHEDULE); - // we still hold the benaphore lock, so it makes no sense - // to reschedule after having released the sync semaphore - } - - return B_OK; + return status; } -status_t -fifo_enqueue_buffer(net_fifo *fifo, net_buffer *buffer) + +ssize_t +Fifo::Dequeue(benaphore *lock, uint32 flags, bigtime_t timeout, + net_buffer **_buffer) { - BenaphoreLocker locker(fifo->lock); - return _fifo_enqueue_buffer(fifo, buffer); + return base_fifo_dequeue_buffer(this, lock, flags, timeout, _buffer); } -/*! - Gets the first buffer from the FIFO. If there is no buffer, it - will wait depending on the \a flags and \a timeout. - The following flags are supported (the rest is ignored): - MSG_DONTWAIT - ignores the timeout and never wait for a buffer; if your - socket is O_NONBLOCK, you should specify this flag. A \a timeout of - zero is equivalent to this flag, though. - MSG_PEEK - returns a clone of the buffer and keep the original - in the FIFO. -*/ ssize_t -fifo_dequeue_buffer(net_fifo *fifo, uint32 flags, bigtime_t timeout, - net_buffer **_buffer) +Fifo::Clear() { - benaphore_lock(&fifo->lock); - bool dontWait = (flags & MSG_DONTWAIT) != 0 || timeout == 0; - status_t status; + return base_fifo_clear(this); +} - while (true) { - net_buffer *buffer = (net_buffer *)list_get_first_item(&fifo->buffers); - if (buffer != NULL) { - if ((flags & MSG_PEEK) != 0) { - // we need to clone the buffer for inspection; we can't give a - // handle to a buffer that we're still using - buffer = gNetBufferModule.clone(buffer, false); - if (buffer == NULL) { - status = B_NO_MEMORY; - break; - } - } else { - list_remove_item(&fifo->buffers, buffer); - fifo->current_bytes -= buffer->size; - } - *_buffer = buffer; - status = B_OK; - break; - } +status_t +init_fifo(net_fifo *fifo, const char *name, size_t maxBytes) +{ + status_t status = benaphore_init(&fifo->lock, name); + if (status < B_OK) + return status; - if (!dontWait) - fifo->waiting++; + status = base_fifo_init(fifo, name, maxBytes); + if (status < B_OK) + benaphore_destroy(&fifo->lock); - // we need to wait until a new buffer becomes available - benaphore_unlock(&fifo->lock); + return status; +} - if (dontWait) - return B_WOULD_BLOCK; - status = acquire_sem_etc(fifo->notify, 1, - B_CAN_INTERRUPT | B_RELATIVE_TIMEOUT, timeout); - if (status < B_OK) - return status; +void +uninit_fifo(net_fifo *fifo) +{ + clear_fifo(fifo); - // try again - benaphore_lock(&fifo->lock); - } + benaphore_destroy(&fifo->lock); + delete_sem(fifo->notify); +} - if ((flags & MSG_PEEK) != 0 && fifo->waiting > 0) { - // another thread is waiting for data, since we didn't eat the - // buffer, it gets it - fifo->waiting--; - release_sem_etc(fifo->notify, 1, B_DO_NOT_RESCHEDULE); - } - benaphore_unlock(&fifo->lock); - return status; +status_t +fifo_enqueue_buffer(net_fifo *fifo, net_buffer *buffer) +{ + BenaphoreLocker locker(fifo->lock); + return base_fifo_enqueue_buffer(fifo, buffer); } +ssize_t fifo_dequeue_buffer(net_fifo *fifo, uint32 flags, bigtime_t timeout, + struct net_buffer **_buffer) +{ + BenaphoreLocker locker(fifo->lock); + return base_fifo_dequeue_buffer(fifo, &fifo->lock, flags, timeout, _buffer); +} + + status_t clear_fifo(net_fifo *fifo) { BenaphoreLocker locker(fifo->lock); - - while (true) { - net_buffer *buffer = (net_buffer *)list_remove_head_item(&fifo->buffers); - if (buffer == NULL) - break; - - gNetBufferModule.free(buffer); - } - - fifo->current_bytes = 0; - return B_OK; + return base_fifo_clear(fifo); } @@ -258,7 +339,7 @@ BenaphoreLocker locker(fifo->lock); - status_t status = _fifo_enqueue_buffer(fifo, buffer); + status_t status = base_fifo_enqueue_buffer(fifo, buffer); if (status < B_OK) gNetBufferModule.free(buffer); else Modified: haiku/trunk/src/add-ons/kernel/network/stack/utility.h =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/utility.h 2007-04-08 05:50:49 UTC (rev 20613) +++ haiku/trunk/src/add-ons/kernel/network/stack/utility.h 2007-04-08 09:15:52 UTC (rev 20614) @@ -26,6 +26,33 @@ }; +// internal Fifo class which doesn't maintain it's own lock +class Fifo { +public: + Fifo(const char *name, size_t maxBytes); + ~Fifo(); + + status_t InitCheck() const; + + status_t Enqueue(net_buffer *buffer); + status_t EnqueueAndNotify(net_buffer *_buffer, net_socket *socket, uint8 event); + + ssize_t Dequeue(benaphore *lock, uint32 flags, bigtime_t timeout, + net_buffer **_buffer); + status_t Clear(); + + bool IsEmpty() const { return current_bytes == 0; } + +//private: + // these field names are kept so we can use templatized + // functions together with net_fifo + sem_id notify; + int32 waiting; + size_t max_bytes; + size_t current_bytes; + struct list buffers; +}; + inline UserBuffer::UserBuffer(void *buffer, size_t size) : fBuffer((uint8 *)buffer), fBufferSize(size), From hugosantos at mail.berlios.de Sun Apr 8 11:30:09 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Sun, 8 Apr 2007 11:30:09 +0200 Subject: [Haiku-commits] r20615 - haiku/trunk/src/add-ons/kernel/network/stack Message-ID: <200704080930.l389U9Ih010711@sheep.berlios.de> Author: hugosantos Date: 2007-04-08 11:30:00 +0200 (Sun, 08 Apr 2007) New Revision: 20615 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20615&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/stack/interfaces.cpp Log: notify all monitors when a device is being removed. Modified: haiku/trunk/src/add-ons/kernel/network/stack/interfaces.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/interfaces.cpp 2007-04-08 09:15:52 UTC (rev 20614) +++ haiku/trunk/src/add-ons/kernel/network/stack/interfaces.cpp 2007-04-08 09:30:00 UTC (rev 20615) @@ -659,7 +659,9 @@ { BenaphoreLocker locker(sInterfaceLock); - net_device_interface *interface = find_device_interface(device->name); + // hold a reference to the device interface being removed + // so our put_() will (eventually) do the final cleanup + net_device_interface *interface = get_device_interface(device->name, false); if (interface == NULL) return ENODEV; @@ -675,9 +677,23 @@ // ... [see delete_interface()] domain_removed_device_interface(interface); + DeviceMonitorList::Iterator iterator = interface->monitor_funcs.GetIterator(); + while (iterator.HasNext()) { + // when we call Next() the next item in the list is obtained + // so it's safe for the "current" item to remove itself. + net_device_monitor *monitor = iterator.Next(); + + monitor->event(monitor, B_DEVICE_BEING_REMOVED); + } + + // By now all of the monitors must have removed themselves. If they + // didn't, they'll probably wait forever to be callback'ed again. + interface->monitor_funcs.RemoveAll(); + // TODO: make sure all readers are gone - // make sure all watchers are gone + put_device_interface(interface); + return B_OK; } From bonefish at mail.berlios.de Sun Apr 8 12:54:20 2007 From: bonefish at mail.berlios.de (bonefish at BerliOS) Date: Sun, 8 Apr 2007 12:54:20 +0200 Subject: [Haiku-commits] r20616 - haiku/trunk/src/add-ons/kernel/drivers/network/rtl8169 Message-ID: <200704081054.l38AsK2l021772@sheep.berlios.de> Author: bonefish Date: 2007-04-08 12:54:17 +0200 (Sun, 08 Apr 2007) New Revision: 20616 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20616&view=rev Modified: haiku/trunk/src/add-ons/kernel/drivers/network/rtl8169/Jamfile Log: Patch by Urias McCullough: Revived jam package for rtl8169. Modified: haiku/trunk/src/add-ons/kernel/drivers/network/rtl8169/Jamfile =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/network/rtl8169/Jamfile 2007-04-08 09:30:00 UTC (rev 20615) +++ haiku/trunk/src/add-ons/kernel/drivers/network/rtl8169/Jamfile 2007-04-08 10:54:17 UTC (rev 20616) @@ -15,15 +15,13 @@ util.c ; -# Package haiku-rtl8169-cvs : -# rtl8169 : -# boot home config add-ons kernel drivers bin ; -# Package haiku-rtl8169-cvs : -# rtl8169 : -# boot home config add-ons kernel drivers dev net ; -# Package haiku-rtl8169-cvs : -# rtl8169.settings : -# boot home config settings kernel drivers sample ; +Package haiku-rtl8169-svn : + rtl8169 : + boot home config add-ons kernel drivers bin ; +Package haiku-rtl8169-svn : + rtl8169.settings : + boot home config settings kernel drivers sample ; +PackageDriverSymLink haiku-rtl8169-svn : net rtl8169 ; Package haiku-networkingkit-cvs : rtl8169 : From stippi at mail.berlios.de Sun Apr 8 19:37:22 2007 From: stippi at mail.berlios.de (stippi at BerliOS) Date: Sun, 8 Apr 2007 19:37:22 +0200 Subject: [Haiku-commits] r20617 - haiku/trunk/src/kits/interface Message-ID: <200704081737.l38HbM7O000063@sheep.berlios.de> Author: stippi Date: 2007-04-08 19:37:22 +0200 (Sun, 08 Apr 2007) New Revision: 20617 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20617&view=rev Modified: haiku/trunk/src/kits/interface/View.cpp Log: * export SetDiskMode() symbol, thanks to "aldeck" for providing the BeBook link, fixes ticket #1140 Modified: haiku/trunk/src/kits/interface/View.cpp =================================================================== --- haiku/trunk/src/kits/interface/View.cpp 2007-04-08 10:54:17 UTC (rev 20616) +++ haiku/trunk/src/kits/interface/View.cpp 2007-04-08 17:37:22 UTC (rev 20617) @@ -1132,6 +1132,11 @@ BView::DrawAfterChildren(BRect r) { // HOOK function + + // NOTE: DrawAfterChildren is called if the corresponding + // flag is set, but it will currently not work as expected, + // since the app_server does not allow views to draw *on* + // their children STRACE(("\tHOOK: BView(%s)::DrawAfterChildren()\n", Name())); } @@ -3048,7 +3053,19 @@ void -BView::BeginPicture(BPicture *picture) +BView::SetDiskMode(char* filename, long offset) +{ + // TODO: implement + // One BeBook version has this to say about SetDiskMode(): + // + // "Begins recording a picture to the file with the given filename + // at the given offset. Subsequent drawing commands sent to the view + // will be written to the file until EndPicture() is called. The + // stored commands may be played from the file with DrawPicture()." +} + + +void BView::BeginPicture(BPicture *picture) { if (do_owner_check() && picture && picture->usurped == NULL) { picture->usurp(cpicture); @@ -4949,8 +4966,3 @@ } -/* TODO: - -implement SetDiskMode(). What's with this method? What does it do? test! - does it has something to do with DrawPictureAsync( filename* .. )? - -implement DrawAfterChildren() -*/ From stippi at mail.berlios.de Sun Apr 8 19:45:35 2007 From: stippi at mail.berlios.de (stippi at BerliOS) Date: Sun, 8 Apr 2007 19:45:35 +0200 Subject: [Haiku-commits] r20618 - haiku/trunk/src/kits/interface Message-ID: <200704081745.l38HjZMS000589@sheep.berlios.de> Author: stippi Date: 2007-04-08 19:45:35 +0200 (Sun, 08 Apr 2007) New Revision: 20618 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20618&view=rev Modified: haiku/trunk/src/kits/interface/StatusBar.cpp Log: * patch by aldeck, fixes ticket #1143 Modified: haiku/trunk/src/kits/interface/StatusBar.cpp =================================================================== --- haiku/trunk/src/kits/interface/StatusBar.cpp 2007-04-08 17:37:22 UTC (rev 20617) +++ haiku/trunk/src/kits/interface/StatusBar.cpp 2007-04-08 17:45:35 UTC (rev 20618) @@ -587,7 +587,7 @@ } -void +extern "C" void _ReservedStatusBar1__10BStatusBar(BStatusBar* self, float value, const char* text, const char* trailingText) { From hugosantos at mail.berlios.de Sun Apr 8 23:34:24 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Sun, 8 Apr 2007 23:34:24 +0200 Subject: [Haiku-commits] r20619 - haiku/trunk/src/add-ons/kernel/network/protocols/tcp Message-ID: <200704082134.l38LYOsY016351@sheep.berlios.de> Author: hugosantos Date: 2007-04-08 23:34:11 +0200 (Sun, 08 Apr 2007) New Revision: 20619 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20619&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp Log: Fixed a TCP issue reported by Stephan. Make sure we have enough PSH'ed bytes in the receive buffer before breaking the RX loop. Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-08 17:45:35 UTC (rev 20618) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-08 21:34:11 UTC (rev 20619) @@ -470,7 +470,7 @@ status_t TCPEndpoint::ReadData(size_t numBytes, uint32 flags, net_buffer** _buffer) { - TRACE("ReadData(%lu bytes)", numBytes); + TRACE("ReadData(%lu bytes, flags 0x%x)", numBytes, (unsigned int)flags); RecursiveLocker locker(fLock); @@ -510,9 +510,10 @@ if (timeout != B_INFINITE_TIMEOUT) timeout += system_time(); - while (fReceiveQueue.PushedData() == 0 + while ((fFlags & FLAG_NO_RECEIVE) == 0 && fReceiveQueue.Available() < dataNeeded - && (fFlags & FLAG_NO_RECEIVE) == 0) { + && (fReceiveQueue.PushedData() == 0 + || fReceiveQueue.Available() < fReceiveQueue.PushedData())) { locker.Unlock(); status_t status = acquire_sem_etc(fReceiveLock, 1, @@ -532,8 +533,8 @@ } } - TRACE("ReadData(): read %lu bytes, %lu are available", - numBytes, fReceiveQueue.Available()); + TRACE("ReadData(): read %lu bytes, %lu are available (flags 0x%x)", + numBytes, fReceiveQueue.Available(), (unsigned int)fFlags); if (numBytes < fReceiveQueue.Available()) release_sem_etc(fReceiveLock, 1, B_DO_NOT_RESCHEDULE); From hugosantos at mail.berlios.de Sun Apr 8 23:34:36 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Sun, 8 Apr 2007 23:34:36 +0200 Subject: [Haiku-commits] r20620 - in haiku/trunk: build/jam src/add-ons/kernel/network/datalink_protocols src/add-ons/kernel/network/datalink_protocols/arp src/add-ons/kernel/network/datalink_protocols/ipv4_datagram src/add-ons/kernel/network/stack Message-ID: <200704082134.l38LYa0Y016380@sheep.berlios.de> Author: hugosantos Date: 2007-04-08 23:34:21 +0200 (Sun, 08 Apr 2007) New Revision: 20620 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20620&view=rev Added: haiku/trunk/src/add-ons/kernel/network/datalink_protocols/ipv4_datagram/ haiku/trunk/src/add-ons/kernel/network/datalink_protocols/ipv4_datagram/Jamfile haiku/trunk/src/add-ons/kernel/network/datalink_protocols/ipv4_datagram/ipv4_datagram.cpp Modified: haiku/trunk/build/jam/HaikuImage haiku/trunk/src/add-ons/kernel/network/datalink_protocols/Jamfile haiku/trunk/src/add-ons/kernel/network/datalink_protocols/arp/arp.cpp haiku/trunk/src/add-ons/kernel/network/stack/stack.cpp Log: introduced an ipv4_datagram datalink_module to handle the registration of the IPv4 reader instead of doing it in the ARP module. Modified: haiku/trunk/build/jam/HaikuImage =================================================================== --- haiku/trunk/build/jam/HaikuImage 2007-04-08 21:34:11 UTC (rev 20619) +++ haiku/trunk/build/jam/HaikuImage 2007-04-08 21:34:21 UTC (rev 20620) @@ -66,7 +66,7 @@ ; BEOS_NETWORK_DEVICES = ethernet loopback ; -BEOS_NETWORK_DATALINK_PROTOCOLS = ethernet_frame arp loopback_frame ; +BEOS_NETWORK_DATALINK_PROTOCOLS = ethernet_frame arp loopback_frame ipv4_datagram ; #BEOS_NETWORK_PPP = ipcp modem pap pppoe ; BEOS_NETWORK_PROTOCOLS = ipv4 tcp udp icmp ; Modified: haiku/trunk/src/add-ons/kernel/network/datalink_protocols/Jamfile =================================================================== --- haiku/trunk/src/add-ons/kernel/network/datalink_protocols/Jamfile 2007-04-08 21:34:11 UTC (rev 20619) +++ haiku/trunk/src/add-ons/kernel/network/datalink_protocols/Jamfile 2007-04-08 21:34:21 UTC (rev 20620) @@ -2,4 +2,5 @@ SubInclude HAIKU_TOP src add-ons kernel network datalink_protocols arp ; SubInclude HAIKU_TOP src add-ons kernel network datalink_protocols ethernet_frame ; +SubInclude HAIKU_TOP src add-ons kernel network datalink_protocols ipv4_datagram ; SubInclude HAIKU_TOP src add-ons kernel network datalink_protocols loopback_frame ; Modified: haiku/trunk/src/add-ons/kernel/network/datalink_protocols/arp/arp.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/datalink_protocols/arp/arp.cpp 2007-04-08 21:34:11 UTC (rev 20619) +++ haiku/trunk/src/add-ons/kernel/network/datalink_protocols/arp/arp.cpp 2007-04-08 21:34:21 UTC (rev 20620) @@ -782,13 +782,6 @@ status_t status = sStackModule->register_device_handler(interface->device, ETHER_FRAME_TYPE | ETHER_TYPE_ARP, &arp_receive, NULL); - if (status == B_OK) { - // We also register the domain as a handler for deframed packets; - // while the ethernet_frame module is not really connected to our - // domain, we are. - status = sStackModule->register_domain_device_handler(interface->device, - ETHER_FRAME_TYPE | ETHER_TYPE_IP, interface->domain); - } if (status < B_OK) return status; Added: haiku/trunk/src/add-ons/kernel/network/datalink_protocols/ipv4_datagram/Jamfile =================================================================== --- haiku/trunk/src/add-ons/kernel/network/datalink_protocols/ipv4_datagram/Jamfile 2007-04-08 21:34:11 UTC (rev 20619) +++ haiku/trunk/src/add-ons/kernel/network/datalink_protocols/ipv4_datagram/Jamfile 2007-04-08 21:34:21 UTC (rev 20620) @@ -0,0 +1,25 @@ +SubDir HAIKU_TOP src add-ons kernel network datalink_protocols ipv4_datagram ; + +SetSubDirSupportedPlatformsBeOSCompatible ; + +if $(TARGET_PLATFORM) != haiku { + UseHeaders [ FStandardOSHeaders ] : true ; + # Needed for and maybe other stuff. + UseHeaders [ FDirName $(HAIKU_TOP) headers posix ] : true ; + # We need the public network headers also when not compiling for Haiku. + # Unfortunately we get more than we want, namely all POSIX headers. +} + +UsePrivateHeaders kernel net ; + +KernelAddon ipv4_datagram : + ipv4_datagram.cpp +; + +# Installation +HaikuInstall install-networking : /boot/home/config/add-ons/kernel/haiku_network/datalink_protocols + : ipv4_datagram ; + +Package haiku-networkingkit-cvs : + haiku : + boot home config add-ons kernel haiku_network datalink_protocols ; Added: haiku/trunk/src/add-ons/kernel/network/datalink_protocols/ipv4_datagram/ipv4_datagram.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/datalink_protocols/ipv4_datagram/ipv4_datagram.cpp 2007-04-08 21:34:11 UTC (rev 20619) +++ haiku/trunk/src/add-ons/kernel/network/datalink_protocols/ipv4_datagram/ipv4_datagram.cpp 2007-04-08 21:34:21 UTC (rev 20620) @@ -0,0 +1,131 @@ +/* + * Copyright 2007, Haiku, Inc. All Rights Reserved. + * Distributed under the terms of the MIT License. + * + * Authors: + * Hugo Santos, hugosantos at gmail.com + */ + + +#include +#include +#include +#include + +#include + +#include // for ETHER_TYPE_IP +#include + +#include + + +static net_stack_module_info *sStackModule; +// TODO ETHER_FRAME_TYPE doesn't belong there, we need Layer 2 +// independence. +static const int32 kIPv4FrameType = ETHER_FRAME_TYPE | ETHER_TYPE_IP; + + +static status_t +ipv4_datalink_init(net_interface *interface, net_datalink_protocol **_protocol) +{ + dprintf("ipv4_datalink_init(%s)\n", interface->name); + + if (interface->domain->family != AF_INET) + return B_BAD_TYPE; + + // While the loopback doesn't get a header to mux protocols, + // we let it do all of the registration work. + if (interface->device->type == IFT_LOOP) + return B_BAD_TYPE; + + net_datalink_protocol *protocol = new (std::nothrow) net_datalink_protocol; + if (protocol == NULL) + return B_NO_MEMORY; + + // We register ETHER_TYPE_IP as most datalink protocols use it + // to identify IP datagrams. In the future we may limit this. + + status_t status = sStackModule->register_domain_device_handler( + interface->device, kIPv4FrameType, interface->domain); + if (status < B_OK) + delete protocol; + else + *_protocol = protocol; + + return status; +} + + +static status_t +ipv4_datalink_uninit(net_datalink_protocol *protocol) +{ + sStackModule->unregister_device_handler(protocol->interface->device, + kIPv4FrameType); + delete protocol; + return B_OK; +} + + +static status_t +ipv4_datalink_send_data(net_datalink_protocol *protocol, net_buffer *buffer) +{ + return protocol->next->module->send_data(protocol->next, buffer); +} + + +static status_t +ipv4_datalink_up(net_datalink_protocol *protocol) +{ + return protocol->next->module->interface_up(protocol->next); +} + + +static void +ipv4_datalink_down(net_datalink_protocol *protocol) +{ + // TODO Clear routes here instead? + protocol->next->module->interface_down(protocol->next); +} + + +static status_t +ipv4_datalink_control(net_datalink_protocol *protocol, int32 op, + void *argument, size_t length) +{ + return protocol->next->module->control(protocol->next, op, argument, length); +} + + +static status_t +ipv4_datalink_std_ops(int32 op, ...) +{ + switch (op) { + case B_MODULE_INIT: + return get_module(NET_STACK_MODULE_NAME, (module_info **)&sStackModule); + + case B_MODULE_UNINIT: + return put_module(NET_STACK_MODULE_NAME); + } + + return B_ERROR; +} + +net_datalink_protocol_module_info gIPv4DataLinkModule = { + { + "network/datalink_protocols/ipv4_datagram/v1", + 0, + ipv4_datalink_std_ops + }, + ipv4_datalink_init, + ipv4_datalink_uninit, + ipv4_datalink_send_data, + ipv4_datalink_up, + ipv4_datalink_down, + ipv4_datalink_control, +}; + +module_info *modules[] = { + (module_info *)&gIPv4DataLinkModule, + NULL +}; Modified: haiku/trunk/src/add-ons/kernel/network/stack/stack.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/stack.cpp 2007-04-08 21:34:11 UTC (rev 20619) +++ haiku/trunk/src/add-ons/kernel/network/stack/stack.cpp 2007-04-08 21:34:21 UTC (rev 20620) @@ -795,6 +795,7 @@ register_domain_datalink_protocols(AF_INET, IFT_LOOP, "network/datalink_protocols/loopback_frame/v1", NULL); register_domain_datalink_protocols(AF_INET, IFT_ETHER, + "network/datalink_protocols/ipv4_datagram/v1", "network/datalink_protocols/arp/v1", "network/datalink_protocols/ethernet_frame/v1", NULL); From hugosantos at mail.berlios.de Mon Apr 9 00:01:00 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Mon, 9 Apr 2007 00:01:00 +0200 Subject: [Haiku-commits] r20621 - haiku/trunk/src/add-ons/kernel/network/stack Message-ID: <200704082201.l38M10LQ018562@sheep.berlios.de> Author: hugosantos Date: 2007-04-09 00:00:52 +0200 (Mon, 09 Apr 2007) New Revision: 20621 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20621&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp haiku/trunk/src/add-ons/kernel/network/stack/domains.cpp haiku/trunk/src/add-ons/kernel/network/stack/interfaces.cpp haiku/trunk/src/add-ons/kernel/network/stack/interfaces.h Log: whenever an interface is deleted, call put_domain_datalink_protocols() so all readers are unregistered. - Unfortunely this requires RX lock to become a recursive lock. Modified: haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp 2007-04-08 21:34:21 UTC (rev 20620) +++ haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp 2007-04-08 22:00:52 UTC (rev 20621) @@ -45,7 +45,7 @@ net_device *device = interface->device; status_t status = B_OK; - BenaphoreLocker rx_lock(interface->rx_lock); + RecursiveLocker rx_lock(interface->rx_lock); while (device->flags & IFF_UP) { net_buffer *buffer; Modified: haiku/trunk/src/add-ons/kernel/network/stack/domains.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/domains.cpp 2007-04-08 21:34:21 UTC (rev 20620) +++ haiku/trunk/src/add-ons/kernel/network/stack/domains.cpp 2007-04-08 22:00:52 UTC (rev 20621) @@ -213,7 +213,7 @@ // and domain locks are required, we MUST obtain the RX // lock before the domain lock. This order MUST NOT ever // be reversed under the penalty of deadlock. - BenaphoreLocker _1(device->rx_lock); + RecursiveLocker _1(device->rx_lock); BenaphoreLocker _2(domain->lock); net_interface *interface = find_interface(domain, name); Modified: haiku/trunk/src/add-ons/kernel/network/stack/interfaces.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/interfaces.cpp 2007-04-08 21:34:21 UTC (rev 20620) +++ haiku/trunk/src/add-ons/kernel/network/stack/interfaces.cpp 2007-04-08 22:00:52 UTC (rev 20621) @@ -190,6 +190,12 @@ // down_device_interface() -- if upcount reaches 0 interface_set_down(interface); + // This call requires the RX Lock to be a recursive + // lock since each uninit_protocol() call may call + // again into the stack to unregister a reader for + // instance, which tries to obtain the RX lock again. + put_domain_datalink_protocols(interface); + put_device_interface(interface->device_interface); free(interface->address); @@ -325,7 +331,7 @@ interface->module->uninit_device(interface->device); put_module(interface->module->info.name); - benaphore_destroy(&interface->rx_lock); + recursive_lock_destroy(&interface->rx_lock); delete interface; } @@ -392,7 +398,8 @@ // create new module interface for this interface = new (std::nothrow) net_device_interface; if (interface != NULL) { - if (benaphore_init(&interface->rx_lock, "rx lock") >= B_OK) { + if (recursive_lock_init(&interface->rx_lock, + "rx lock") >= B_OK) { interface->name = device->name; interface->module = module; interface->device = device; @@ -446,13 +453,13 @@ // one of the callers must hold a reference to the net_device_interface // usually it is one of the net_interfaces. - benaphore_unlock(&interface->rx_lock); + recursive_lock_unlock(&interface->rx_lock); // make sure the reader thread is gone before shutting down the interface status_t status; wait_for_thread(reader_thread, &status); - benaphore_lock(&interface->rx_lock); + recursive_lock_lock(&interface->rx_lock); } @@ -473,7 +480,7 @@ if (interface == NULL) return ENODEV; - BenaphoreLocker _(interface->rx_lock); + RecursiveLocker _(interface->rx_lock); if (--interface->deframe_ref_count == 0) interface->deframe_func = NULL; @@ -502,7 +509,7 @@ if (interface == NULL) return ENODEV; - BenaphoreLocker _(interface->rx_lock); + RecursiveLocker _(interface->rx_lock); if (interface->deframe_func != NULL && interface->deframe_func != deframeFunc) return B_ERROR; @@ -536,7 +543,7 @@ if (interface == NULL) return ENODEV; - BenaphoreLocker _(interface->rx_lock); + RecursiveLocker _(interface->rx_lock); // see if such a handler already for this device @@ -572,7 +579,7 @@ if (interface == NULL) return ENODEV; - BenaphoreLocker _(interface->rx_lock); + RecursiveLocker _(interface->rx_lock); // search for the handler @@ -605,7 +612,7 @@ if (interface == NULL) return ENODEV; - BenaphoreLocker _(interface->rx_lock); + RecursiveLocker _(interface->rx_lock); interface->monitor_funcs.Add(monitor); return B_OK; } @@ -621,7 +628,7 @@ if (interface == NULL) return ENODEV; - BenaphoreLocker _(interface->rx_lock); + RecursiveLocker _(interface->rx_lock); // search for the monitor @@ -669,7 +676,7 @@ // This is very complex, refer to delete_interface() for // further details. - BenaphoreLocker _(interface->rx_lock); + RecursiveLocker _(interface->rx_lock); // this will possibly call: // remove_interface_from_domain() [domain gets locked] @@ -690,7 +697,9 @@ // didn't, they'll probably wait forever to be callback'ed again. interface->monitor_funcs.RemoveAll(); - // TODO: make sure all readers are gone + // All of the readers should be gone as well since we are out of + // interfaces and `put_domain_datalink_protocols' is called for + // each delete_interface(). put_device_interface(interface); Modified: haiku/trunk/src/add-ons/kernel/network/stack/interfaces.h =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/interfaces.h 2007-04-08 21:34:21 UTC (rev 20620) +++ haiku/trunk/src/add-ons/kernel/network/stack/interfaces.h 2007-04-08 22:00:52 UTC (rev 20621) @@ -42,7 +42,7 @@ DeviceMonitorList monitor_funcs; DeviceHandlerList receive_funcs; - benaphore rx_lock; + recursive_lock rx_lock; }; typedef DoublyLinkedList DeviceInterfaceList; From hugosantos at mail.berlios.de Mon Apr 9 02:09:10 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Mon, 9 Apr 2007 02:09:10 +0200 Subject: [Haiku-commits] r20622 - haiku/trunk/src/add-ons/kernel/network/stack Message-ID: <200704090009.l3909AGr017751@sheep.berlios.de> Author: hugosantos Date: 2007-04-09 02:09:00 +0200 (Mon, 09 Apr 2007) New Revision: 20622 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20622&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/stack/interfaces.cpp haiku/trunk/src/add-ons/kernel/network/stack/link.cpp haiku/trunk/src/add-ons/kernel/network/stack/routes.cpp haiku/trunk/src/add-ons/kernel/network/stack/utility.cpp haiku/trunk/src/add-ons/kernel/network/stack/utility.h Log: packet capture sockets are now properly notified when the device is going down. - modified LinkProtocol::ReadData() a bit so it can safely react to external changes such as the device being monitored going down. - fixed an issue in invalidate_routes() where in some cases the default route was being kept. - fixed another issue related with the fifo implementation, the notifier semaphore was being created with count of 1, instead of 0. Modified: haiku/trunk/src/add-ons/kernel/network/stack/interfaces.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/interfaces.cpp 2007-04-08 22:00:52 UTC (rev 20621) +++ haiku/trunk/src/add-ons/kernel/network/stack/interfaces.cpp 2007-04-09 00:09:00 UTC (rev 20622) @@ -73,6 +73,20 @@ } +static void +notify_device_monitors(net_device_interface *interface, int32 event) +{ + DeviceMonitorList::Iterator iterator = interface->monitor_funcs.GetIterator(); + while (iterator.HasNext()) { + // when we call Next() the next item in the list is obtained + // so it's safe for the "current" item to remove itself. + net_device_monitor *monitor = iterator.Next(); + + monitor->event(monitor, event); + } +} + + // #pragma mark - interfaces @@ -449,6 +463,8 @@ device->flags &= ~IFF_UP; interface->module->down(device); + notify_device_monitors(interface, B_DEVICE_GOING_DOWN); + thread_id reader_thread = interface->reader_thread; // one of the callers must hold a reference to the net_device_interface @@ -684,15 +700,8 @@ // ... [see delete_interface()] domain_removed_device_interface(interface); - DeviceMonitorList::Iterator iterator = interface->monitor_funcs.GetIterator(); - while (iterator.HasNext()) { - // when we call Next() the next item in the list is obtained - // so it's safe for the "current" item to remove itself. - net_device_monitor *monitor = iterator.Next(); + notify_device_monitors(interface, B_DEVICE_BEING_REMOVED); - monitor->event(monitor, B_DEVICE_BEING_REMOVED); - } - // By now all of the monitors must have removed themselves. If they // didn't, they'll probably wait forever to be callback'ed again. interface->monitor_funcs.RemoveAll(); Modified: haiku/trunk/src/add-ons/kernel/network/stack/link.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/link.cpp 2007-04-08 22:00:52 UTC (rev 20621) +++ haiku/trunk/src/add-ons/kernel/network/stack/link.cpp 2007-04-09 00:09:00 UTC (rev 20622) @@ -127,19 +127,27 @@ { BenaphoreLocker _(fLock); - if (fMonitoredDevice == NULL) { - if (fFifo.current_bytes == 0) + bigtime_t timeout = socket->receive.timeout; + + if (timeout == 0) + flags |= MSG_DONTWAIT; + else if (timeout != B_INFINITE_TIMEOUT) + timeout += system_time(); + + while (fFifo.IsEmpty()) { + if (fMonitoredDevice == NULL) return ENODEV; + + status_t status = B_WOULD_BLOCK; + if ((flags & MSG_DONTWAIT) == 0) + status = fFifo.Wait(&fLock, timeout); + + if (status < B_OK) + return status; } - net_buffer *buffer; - status_t status = fFifo.Dequeue(&fLock, flags, socket->receive.timeout, - &buffer); - if (status < B_OK) - return status; - - *_buffer = buffer; - return B_OK; + *_buffer = fFifo.Dequeue(flags & MSG_PEEK); + return *_buffer ? B_OK : B_NO_MEMORY; } @@ -148,7 +156,7 @@ { BenaphoreLocker _(fLock); if (fMonitoredDevice == NULL) - return ECONNRESET; + return ENODEV; return fFifo.current_bytes; } @@ -188,12 +196,14 @@ { LinkProtocol *protocol = (LinkProtocol *)monitor->cookie; - // We currently maintain the monitor while the device is down - if (event == B_DEVICE_BEING_REMOVED) { + if (event == B_DEVICE_GOING_DOWN) { BenaphoreLocker _(protocol->fLock); protocol->_Unregister(); - notify_socket(protocol->socket, B_SELECT_READ, ECONNRESET); + if (protocol->fFifo.IsEmpty()) { + protocol->fFifo.WakeAll(); + notify_socket(protocol->socket, B_SELECT_READ, ENODEV); + } } } Modified: haiku/trunk/src/add-ons/kernel/network/stack/routes.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/routes.cpp 2007-04-08 22:00:52 UTC (rev 20621) +++ haiku/trunk/src/add-ons/kernel/network/stack/routes.cpp 2007-04-09 00:09:00 UTC (rev 20622) @@ -519,7 +519,7 @@ // lock the domain throughout the send_data() routine. // These are the easy solutions, need to think about this. -hugo - if (route->interface == interface) + if (route->interface->index == interface->index) remove_route(domain, route); } } Modified: haiku/trunk/src/add-ons/kernel/network/stack/utility.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/utility.cpp 2007-04-08 22:00:52 UTC (rev 20621) +++ haiku/trunk/src/add-ons/kernel/network/stack/utility.cpp 2007-04-09 00:09:00 UTC (rev 20622) @@ -24,10 +24,20 @@ static bigtime_t sTimerTimeout; +static inline void +fifo_notify_one_reader(int32 &waiting, sem_id sem) +{ + if (waiting > 0) { + waiting--; + release_sem_etc(sem, 1, B_DO_NOT_RESCHEDULE); + } +} + + template static inline status_t base_fifo_init(FifoType *fifo, const char *name, size_t maxBytes) { - fifo->notify = create_sem(1, name); + fifo->notify = create_sem(0, name); fifo->max_bytes = maxBytes; fifo->current_bytes = 0; fifo->waiting = 0; @@ -45,86 +55,12 @@ list_add_item(&fifo->buffers, buffer); fifo->current_bytes += buffer->size; + fifo_notify_one_reader(fifo->waiting, fifo->notify); - if (fifo->waiting > 0) { - fifo->waiting--; - release_sem_etc(fifo->notify, 1, B_DO_NOT_RESCHEDULE); - // we still hold the benaphore lock, so it makes no sense - // to reschedule after having released the sync semaphore - } - return B_OK; } -/*! - Gets the first buffer from the FIFO. If there is no buffer, it - will wait depending on the \a flags and \a timeout. - The following flags are supported (the rest is ignored): - MSG_DONTWAIT - ignores the timeout and never wait for a buffer; if your - socket is O_NONBLOCK, you should specify this flag. A \a timeout of - zero is equivalent to this flag, though. - MSG_PEEK - returns a clone of the buffer and keep the original - in the FIFO. -*/ -template static inline ssize_t -base_fifo_dequeue_buffer(FifoType *fifo, benaphore *lock, uint32 flags, - bigtime_t timeout, net_buffer **_buffer) -{ - // this function is called with `lock' held. - bool dontWait = (flags & MSG_DONTWAIT) != 0 || timeout == 0; - status_t status; - - while (true) { - net_buffer *buffer = (net_buffer *)list_get_first_item(&fifo->buffers); - if (buffer != NULL) { - if ((flags & MSG_PEEK) != 0) { - // we need to clone the buffer for inspection; we can't give a - // handle to a buffer that we're still using - buffer = gNetBufferModule.clone(buffer, false); - if (buffer == NULL) { - status = B_NO_MEMORY; - break; - } - } else { - list_remove_item(&fifo->buffers, buffer); - fifo->current_bytes -= buffer->size; - } - - *_buffer = buffer; - status = B_OK; - break; - } - - if (!dontWait) - fifo->waiting++; - - // we need to wait until a new buffer becomes available - benaphore_unlock(lock); - - if (dontWait) - return B_WOULD_BLOCK; - - status = acquire_sem_etc(fifo->notify, 1, - B_CAN_INTERRUPT | B_RELATIVE_TIMEOUT, timeout); - if (status < B_OK) - return status; - - // try again - benaphore_lock(lock); - } - - if ((flags & MSG_PEEK) != 0 && fifo->waiting > 0) { - // another thread is waiting for data, since we didn't eat the - // buffer, it gets it - fifo->waiting--; - release_sem_etc(fifo->notify, 1, B_DO_NOT_RESCHEDULE); - } - - return status; -} - - template static inline status_t base_fifo_clear(FifoType *fifo) { @@ -265,14 +201,37 @@ } -ssize_t -Fifo::Dequeue(benaphore *lock, uint32 flags, bigtime_t timeout, - net_buffer **_buffer) +status_t +Fifo::Wait(benaphore *lock, bigtime_t timeout) { - return base_fifo_dequeue_buffer(this, lock, flags, timeout, _buffer); + waiting++; + benaphore_unlock(lock); + status_t status = acquire_sem_etc(notify, 1, + B_CAN_INTERRUPT | B_ABSOLUTE_TIMEOUT, timeout); + benaphore_lock(lock); + return status; } +net_buffer * +Fifo::Dequeue(bool clone) +{ + net_buffer *buffer = (net_buffer *)list_get_first_item(&buffers); + + // assert(buffer != NULL); + + if (clone) { + buffer = gNetBufferModule.clone(buffer, false); + fifo_notify_one_reader(waiting, notify); + }else { + list_remove_item(&buffers, buffer); + current_bytes -= buffer->size; + } + + return buffer; +} + + ssize_t Fifo::Clear() { @@ -280,6 +239,13 @@ } +void +Fifo::WakeAll() +{ + release_sem_etc(notify, 0, B_RELEASE_ALL); +} + + status_t init_fifo(net_fifo *fifo, const char *name, size_t maxBytes) { @@ -313,11 +279,68 @@ } -ssize_t fifo_dequeue_buffer(net_fifo *fifo, uint32 flags, bigtime_t timeout, - struct net_buffer **_buffer) +/*! + Gets the first buffer from the FIFO. If there is no buffer, it + will wait depending on the \a flags and \a timeout. + The following flags are supported (the rest is ignored): + MSG_DONTWAIT - ignores the timeout and never wait for a buffer; if your + socket is O_NONBLOCK, you should specify this flag. A \a timeout of + zero is equivalent to this flag, though. + MSG_PEEK - returns a clone of the buffer and keep the original + in the FIFO. +*/ +ssize_t +fifo_dequeue_buffer(net_fifo *fifo, uint32 flags, bigtime_t timeout, + net_buffer **_buffer) { BenaphoreLocker locker(fifo->lock); - return base_fifo_dequeue_buffer(fifo, &fifo->lock, flags, timeout, _buffer); + bool dontWait = (flags & MSG_DONTWAIT) != 0 || timeout == 0; + status_t status; + + while (true) { + net_buffer *buffer = (net_buffer *)list_get_first_item(&fifo->buffers); + if (buffer != NULL) { + if ((flags & MSG_PEEK) != 0) { + // we need to clone the buffer for inspection; we can't give a + // handle to a buffer that we're still using + buffer = gNetBufferModule.clone(buffer, false); + if (buffer == NULL) { + status = B_NO_MEMORY; + break; + } + } else { + list_remove_item(&fifo->buffers, buffer); + fifo->current_bytes -= buffer->size; + } + + *_buffer = buffer; + status = B_OK; + break; + } + + if (!dontWait) + fifo->waiting++; + + locker.Unlock(); + + if (dontWait) + return B_WOULD_BLOCK; + + // we need to wait until a new buffer becomes available + status = acquire_sem_etc(fifo->notify, 1, + B_CAN_INTERRUPT | B_RELATIVE_TIMEOUT, timeout); + if (status < B_OK) + return status; + + locker.Lock(); + } + + // if another thread is waiting for data, since we didn't + // eat the buffer, it will get it + if (flags & MSG_PEEK) + fifo_notify_one_reader(fifo->waiting, fifo->notify); + + return status; } Modified: haiku/trunk/src/add-ons/kernel/network/stack/utility.h =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/utility.h 2007-04-08 22:00:52 UTC (rev 20621) +++ haiku/trunk/src/add-ons/kernel/network/stack/utility.h 2007-04-09 00:09:00 UTC (rev 20622) @@ -36,11 +36,12 @@ status_t Enqueue(net_buffer *buffer); status_t EnqueueAndNotify(net_buffer *_buffer, net_socket *socket, uint8 event); - - ssize_t Dequeue(benaphore *lock, uint32 flags, bigtime_t timeout, - net_buffer **_buffer); + status_t Wait(benaphore *lock, bigtime_t timeout); + net_buffer *Dequeue(bool clone); status_t Clear(); + void WakeAll(); + bool IsEmpty() const { return current_bytes == 0; } //private: From stippi at mail.berlios.de Mon Apr 9 10:30:31 2007 From: stippi at mail.berlios.de (stippi at BerliOS) Date: Mon, 9 Apr 2007 10:30:31 +0200 Subject: [Haiku-commits] r20623 - in haiku/trunk/src/apps/icon-o-matic: . generic/command generic/gui generic/gui/stateview import_export/svg shape shape/commands transformable Message-ID: <200704090830.l398UVGI028692@sheep.berlios.de> Author: stippi Date: 2007-04-09 10:30:28 +0200 (Mon, 09 Apr 2007) New Revision: 20623 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20623&view=rev Modified: haiku/trunk/src/apps/icon-o-matic/CanvasView.cpp haiku/trunk/src/apps/icon-o-matic/CanvasView.h haiku/trunk/src/apps/icon-o-matic/Jamfile haiku/trunk/src/apps/icon-o-matic/generic/command/Command.cpp haiku/trunk/src/apps/icon-o-matic/generic/command/Command.h haiku/trunk/src/apps/icon-o-matic/generic/command/CommandStack.cpp haiku/trunk/src/apps/icon-o-matic/generic/gui/stateview/Manipulator.cpp haiku/trunk/src/apps/icon-o-matic/generic/gui/stateview/Manipulator.h haiku/trunk/src/apps/icon-o-matic/generic/gui/stateview/MultipleManipulatorState.cpp haiku/trunk/src/apps/icon-o-matic/generic/gui/stateview/MultipleManipulatorState.h haiku/trunk/src/apps/icon-o-matic/generic/gui/stateview/StateView.cpp haiku/trunk/src/apps/icon-o-matic/generic/gui/stateview/StateView.h haiku/trunk/src/apps/icon-o-matic/generic/gui/stateview/ViewState.cpp haiku/trunk/src/apps/icon-o-matic/generic/gui/stateview/ViewState.h haiku/trunk/src/apps/icon-o-matic/generic/gui/ui_defines.h haiku/trunk/src/apps/icon-o-matic/import_export/svg/DocumentBuilder.h haiku/trunk/src/apps/icon-o-matic/shape/PathManipulator.cpp haiku/trunk/src/apps/icon-o-matic/shape/PathManipulator.h haiku/trunk/src/apps/icon-o-matic/shape/commands/ChangePointCommand.cpp haiku/trunk/src/apps/icon-o-matic/shape/commands/ChangePointCommand.h haiku/trunk/src/apps/icon-o-matic/transformable/ResetTransformationCommand.h haiku/trunk/src/apps/icon-o-matic/transformable/TransformBox.cpp haiku/trunk/src/apps/icon-o-matic/transformable/TransformBox.h haiku/trunk/src/apps/icon-o-matic/transformable/TransformCommand.cpp haiku/trunk/src/apps/icon-o-matic/transformable/TransformObjectsCommand.h Log: culmulative update... * holding down space, or using the third mouse button, will force the "pan canvas" mode * using the mouse wheel zooms in and out * fixed issues with the undo commands when nudging something with the cursor keys * manipulators can now indicate wether they changed the mouse cursor * ChangePointCommand is no longer inserted if the point didn't change * new "flip" points feature in context menu, flips "in" and "out" curve control points * mouse wheel events are now propagated together with the mouse position * new "UndoesPrevious" method in Command interface (used to clean up command stack) * clean ups in CommandStack Modified: haiku/trunk/src/apps/icon-o-matic/CanvasView.cpp =================================================================== --- haiku/trunk/src/apps/icon-o-matic/CanvasView.cpp 2007-04-09 00:09:00 UTC (rev 20622) +++ haiku/trunk/src/apps/icon-o-matic/CanvasView.cpp 2007-04-09 08:30:28 UTC (rev 20623) @@ -1,5 +1,5 @@ /* - * Copyright 2006, Haiku. + * Copyright 2006-2007, Haiku. * Distributed under the terms of the MIT License. * * Authors: @@ -9,10 +9,14 @@ #include "CanvasView.h" #include +#include +#include #include +#include #include +#include "cursors.h" #include "ui_defines.h" #include "CommandStack.h" @@ -33,6 +37,10 @@ fCanvasOrigin(0.0, 0.0), fZoomLevel(1.0), + fSpaceHeldDown(false), + fScrollTracking(false), + fScrollTrackingStart(0.0, 0.0), + fMouseFilterMode(SNAPPING_OFF), fOffsreenBitmap(NULL), @@ -136,9 +144,68 @@ if (!IsFocus()) MakeFocus(true); - StateView::MouseDown(where); + uint32 buttons; + if (Window()->CurrentMessage()->FindInt32("buttons", + (int32*)&buttons) < B_OK) + buttons = 0; + + // handle clicks of the third mouse button ourselves (panning), + // otherwise have StateView handle it (normal clicks) + if (fSpaceHeldDown || buttons & B_TERTIARY_MOUSE_BUTTON) { + // switch into scrolling mode and update cursor + fScrollTracking = true; + where.x = roundf(where.x); + where.y = roundf(where.y); + fScrollOffsetStart = ScrollOffset(); + fScrollTrackingStart = where - fScrollOffsetStart; + _UpdateToolCursor(); + SetMouseEventMask(B_POINTER_EVENTS, + B_LOCK_WINDOW_FOCUS | B_SUSPEND_VIEW_FOCUS); + } else { + StateView::MouseDown(where); + } } +// MouseUp +void +CanvasView::MouseUp(BPoint where) +{ + if (fScrollTracking) { + // stop scroll tracking and update cursor + fScrollTracking = false; + _UpdateToolCursor(); + // update StateView mouse position + uint32 transit = Bounds().Contains(where) ? + B_INSIDE_VIEW : B_OUTSIDE_VIEW; + StateView::MouseMoved(where, transit, NULL); + } else { + StateView::MouseUp(where); + } +} + +// MouseMoved +void +CanvasView::MouseMoved(BPoint where, uint32 transit, const BMessage* dragMessage) +{ + if (fScrollTracking) { + uint32 buttons; + GetMouse(&where, &buttons, false); + if (!buttons) { + MouseUp(where); + return; + } + where.x = roundf(where.x); + where.y = roundf(where.y); + where -= ScrollOffset(); + BPoint offset = where - fScrollTrackingStart; + SetScrollOffset(fScrollOffsetStart - offset); + } else { + // normal mouse movement handled by StateView + if (!fSpaceHeldDown) + StateView::MouseMoved(where, transit, dragMessage); + } +} + // FilterMouse void CanvasView::FilterMouse(BPoint* where) const @@ -180,6 +247,23 @@ } } +// MouseWheelChanged +bool +CanvasView::MouseWheelChanged(BPoint where, float x, float y) +{ + if (!Bounds().Contains(where)) + return false; + + if (y > 0.0) { + _SetZoom(_NextZoomOutLevel(fZoomLevel)); + return true; + } else if (y < 0.0) { + _SetZoom(_NextZoomInLevel(fZoomLevel)); + return true; + } + return false; +} + // #pragma mark - // ScrollOffsetChanged @@ -187,9 +271,15 @@ CanvasView::ScrollOffsetChanged(BPoint oldOffset, BPoint newOffset) { BPoint offset = newOffset - oldOffset; + + if (offset == B_ORIGIN) + // prevent circular code (MouseMoved might call ScrollBy...) + return; + ScrollBy(offset.x, offset.y); - MouseMoved(fMouseInfo.position + offset, fMouseInfo.transit, NULL); + if (!fScrollTracking) + MouseMoved(fMouseInfo.position + offset, fMouseInfo.transit, NULL); } // VisibleSizeChanged @@ -308,6 +398,11 @@ _SetZoom(_NextZoomOutLevel(fZoomLevel)); break; + case B_SPACE: + fSpaceHeldDown = true; + _UpdateToolCursor(); + break; + default: return StateView::_HandleKeyDown(key, modifiers); } @@ -315,6 +410,23 @@ return true; } +// _HandleKeyUp +bool +CanvasView::_HandleKeyUp(uint32 key, uint32 modifiers) +{ + switch (key) { + case B_SPACE: + fSpaceHeldDown = false; + _UpdateToolCursor(); + break; + + default: + return StateView::_HandleKeyUp(key, modifiers); + } + + return true; +} + // _CanvasRect() BRect CanvasView::_CanvasRect() const @@ -473,6 +585,26 @@ } } +// _UpdateToolCursor +void +CanvasView::_UpdateToolCursor() +{ + if (fIcon) { + if (fScrollTracking || fSpaceHeldDown) { + // indicate scrolling mode + const uchar* cursorData = fScrollTracking ? kGrabCursor : kHandCursor; + BCursor cursor(cursorData); + SetViewCursor(&cursor, true); + } else { + // pass on to current state of StateView + UpdateStateCursor(); + } + } else { + BCursor cursor(kStopCursor); + SetViewCursor(&cursor, true); + } +} + // #pragma mark - // _NextZoomInLevel Modified: haiku/trunk/src/apps/icon-o-matic/CanvasView.h =================================================================== --- haiku/trunk/src/apps/icon-o-matic/CanvasView.h 2007-04-09 00:09:00 UTC (rev 20622) +++ haiku/trunk/src/apps/icon-o-matic/CanvasView.h 2007-04-09 08:30:28 UTC (rev 20623) @@ -43,8 +43,14 @@ virtual void Draw(BRect updateRect); virtual void MouseDown(BPoint where); + virtual void MouseUp(BPoint where); + virtual void MouseMoved(BPoint where, uint32 transit, + const BMessage* dragMessage); virtual void FilterMouse(BPoint* where) const; + virtual bool MouseWheelChanged(BPoint where, + float x, float y); + // Scrollable interface protected: virtual void ScrollOffsetChanged(BPoint oldOffset, @@ -76,6 +82,7 @@ protected: // StateView interface virtual bool _HandleKeyDown(uint32 key, uint32 modifiers); + virtual bool _HandleKeyUp(uint32 key, uint32 modifiers); // CanvasView BRect _CanvasRect() const; @@ -88,6 +95,8 @@ void _MakeBackground(); + void _UpdateToolCursor(); + private: double _NextZoomInLevel(double zoom) const; double _NextZoomOutLevel(double zoom) const; @@ -105,6 +114,11 @@ BPoint fCanvasOrigin; double fZoomLevel; + bool fSpaceHeldDown; + bool fScrollTracking; + BPoint fScrollTrackingStart; + BPoint fScrollOffsetStart; + uint32 fMouseFilterMode; BBitmap* fOffsreenBitmap; Modified: haiku/trunk/src/apps/icon-o-matic/Jamfile =================================================================== --- haiku/trunk/src/apps/icon-o-matic/Jamfile 2007-04-09 00:09:00 UTC (rev 20622) +++ haiku/trunk/src/apps/icon-o-matic/Jamfile 2007-04-09 08:30:28 UTC (rev 20623) @@ -243,6 +243,7 @@ AddTransformersCommand.cpp ChangePointCommand.cpp CleanUpPathCommand.cpp + FlipPointsCommand.cpp FreezeTransformationCommand.cpp InsertPointCommand.cpp MoveShapesCommand.cpp Modified: haiku/trunk/src/apps/icon-o-matic/generic/command/Command.cpp =================================================================== --- haiku/trunk/src/apps/icon-o-matic/generic/command/Command.cpp 2007-04-09 00:09:00 UTC (rev 20622) +++ haiku/trunk/src/apps/icon-o-matic/generic/command/Command.cpp 2007-04-09 08:30:28 UTC (rev 20623) @@ -58,6 +58,13 @@ name << "Name of action goes here."; } +// UndoesPrevious +bool +Command::UndoesPrevious(const Command* previous) +{ + return false; +} + // CombineWithNext bool Command::CombineWithNext(const Command* next) Modified: haiku/trunk/src/apps/icon-o-matic/generic/command/Command.h =================================================================== --- haiku/trunk/src/apps/icon-o-matic/generic/command/Command.h 2007-04-09 00:09:00 UTC (rev 20622) +++ haiku/trunk/src/apps/icon-o-matic/generic/command/Command.h 2007-04-09 08:30:28 UTC (rev 20623) @@ -27,6 +27,7 @@ virtual void GetName(BString& name); + virtual bool UndoesPrevious(const Command* previous); virtual bool CombineWithNext(const Command* next); virtual bool CombineWithPrevious(const Command* previous); Modified: haiku/trunk/src/apps/icon-o-matic/generic/command/CommandStack.cpp =================================================================== --- haiku/trunk/src/apps/icon-o-matic/generic/command/CommandStack.cpp 2007-04-09 00:09:00 UTC (rev 20622) +++ haiku/trunk/src/apps/icon-o-matic/generic/command/CommandStack.cpp 2007-04-09 08:30:28 UTC (rev 20623) @@ -1,5 +1,5 @@ /* - * Copyright 2006, Haiku. + * Copyright 2006-2007, Haiku. * Distributed under the terms of the MIT License. * * Authors: @@ -34,23 +34,25 @@ status_t CommandStack::Perform(Command* command) { + if (!Lock()) + return B_ERROR; + status_t ret = command ? B_OK : B_BAD_VALUE; - if (Lock()) { - if (ret == B_OK) - ret = command->InitCheck(); - - if (ret == B_OK) - ret = command->Perform(); - - if (ret == B_OK) - ret = _AddCommand(command); - - if (ret != B_OK) { - // no one else feels responsible... - delete command; - } - Unlock(); + if (ret == B_OK) + ret = command->InitCheck(); + + if (ret == B_OK) + ret = command->Perform(); + + if (ret == B_OK) + ret = _AddCommand(command); + + if (ret != B_OK) { + // no one else feels responsible... + delete command; } + + Unlock(); return ret; } @@ -58,19 +60,20 @@ status_t CommandStack::Undo() { + if (!Lock()) + return B_ERROR; + status_t status = B_ERROR; - if (Lock()) { - if (!fUndoHistory.empty()) { - Command* command = fUndoHistory.top(); - fUndoHistory.pop(); - status = command->Undo(); - if (status == B_OK) - fRedoHistory.push(command); - else - fUndoHistory.push(command); - } - Unlock(); + if (!fUndoHistory.empty()) { + Command* command = fUndoHistory.top(); + fUndoHistory.pop(); + status = command->Undo(); + if (status == B_OK) + fRedoHistory.push(command); + else + fUndoHistory.push(command); } + Unlock(); Notify(); @@ -81,19 +84,20 @@ status_t CommandStack::Redo() { + if (!Lock()) + return B_ERROR; + status_t status = B_ERROR; - if (Lock()) { - if (!fRedoHistory.empty()) { - Command* command = fRedoHistory.top(); - fRedoHistory.pop(); - status = command->Redo(); - if (status == B_OK) - fUndoHistory.push(command); - else - fRedoHistory.push(command); - } - Unlock(); + if (!fRedoHistory.empty()) { + Command* command = fRedoHistory.top(); + fRedoHistory.pop(); + status = command->Redo(); + if (status == B_OK) + fUndoHistory.push(command); + else + fRedoHistory.push(command); } + Unlock(); Notify(); @@ -187,29 +191,56 @@ CommandStack::_AddCommand(Command* command) { status_t status = B_OK; - // try to collapse commands to a single command + bool add = true; if (!fUndoHistory.empty()) { + // try to collapse commands to a single command + // or remove this and the previous command if + // they reverse each other if (Command* top = fUndoHistory.top()) { - if (top->CombineWithNext(command)) { + if (command->UndoesPrevious(top)) { add = false; + fUndoHistory.pop(); + delete top; delete command; + } else if (top->CombineWithNext(command)) { + add = false; + delete command; + // after collapsing, the command might + // have changed it's mind about InitCheck() + // (the commands reversed each other) + if (top->InitCheck() < B_OK) { + fUndoHistory.pop(); + delete top; + } } else if (command->CombineWithPrevious(top)) { fUndoHistory.pop(); delete top; + // after collapsing, the command might + // have changed it's mind about InitCheck() + // (the commands reversed each other) + if (command->InitCheck() < B_OK) { + delete command; + add = false; + } } } } if (add) { - // TODO: check return value and set status - fUndoHistory.push(command); + try { + fUndoHistory.push(command); + } catch (...) { + status = B_ERROR; + } } - // the redo stack needs to be empty - // as soon as a command was added (also in case of collapsing) - while (!fRedoHistory.empty()) { - delete fRedoHistory.top(); - fRedoHistory.pop(); + if (status == B_OK) { + // the redo stack needs to be empty + // as soon as a command was added (also in case of collapsing) + while (!fRedoHistory.empty()) { + delete fRedoHistory.top(); + fRedoHistory.pop(); + } } Notify(); Modified: haiku/trunk/src/apps/icon-o-matic/generic/gui/stateview/Manipulator.cpp =================================================================== --- haiku/trunk/src/apps/icon-o-matic/generic/gui/stateview/Manipulator.cpp 2007-04-09 00:09:00 UTC (rev 20622) +++ haiku/trunk/src/apps/icon-o-matic/generic/gui/stateview/Manipulator.cpp 2007-04-09 08:30:28 UTC (rev 20623) @@ -1,5 +1,5 @@ /* - * Copyright 2006, Haiku. + * Copyright 2006-2007, Haiku. * Distributed under the terms of the MIT License. * * Authors: @@ -106,9 +106,10 @@ } // UpdateCursor -void +bool Manipulator::UpdateCursor() { + return false; } // #pragma mark - Modified: haiku/trunk/src/apps/icon-o-matic/generic/gui/stateview/Manipulator.h =================================================================== --- haiku/trunk/src/apps/icon-o-matic/generic/gui/stateview/Manipulator.h 2007-04-09 00:09:00 UTC (rev 20622) +++ haiku/trunk/src/apps/icon-o-matic/generic/gui/stateview/Manipulator.h 2007-04-09 08:30:28 UTC (rev 20623) @@ -1,5 +1,5 @@ /* - * Copyright 2006, Haiku. + * Copyright 2006-2007, Haiku. * Distributed under the terms of the MIT License. * * Authors: @@ -44,7 +44,7 @@ virtual bool HandleKeyUp(uint32 key, uint32 modifiers, Command** _command); - virtual void UpdateCursor(); + virtual bool UpdateCursor(); virtual BRect Bounds() = 0; // the area that the manipulator is Modified: haiku/trunk/src/apps/icon-o-matic/generic/gui/stateview/MultipleManipulatorState.cpp =================================================================== --- haiku/trunk/src/apps/icon-o-matic/generic/gui/stateview/MultipleManipulatorState.cpp 2007-04-09 00:09:00 UTC (rev 20622) +++ haiku/trunk/src/apps/icon-o-matic/generic/gui/stateview/MultipleManipulatorState.cpp 2007-04-09 08:30:28 UTC (rev 20623) @@ -1,5 +1,5 @@ /* - * Copyright 2006, Haiku. + * Copyright 2006-2007, Haiku. * Distributed under the terms of the MIT License. * * Authors: @@ -172,6 +172,10 @@ MultipleManipulatorState::HandleKeyDown(uint32 key, uint32 modifiers, Command** _command) { + // TODO: somehow this looks suspicious, because it doesn't + // seem guaranteed that the manipulator having indicated to + // handle the key down handles the matching key up event... + // maybe there should be the concept of the "focused manipulator" int32 count = fManipulators.CountItems(); for (int32 i = 0; i < count; i++) { Manipulator* manipulator = @@ -197,6 +201,15 @@ return false; } +// UpdateCursor +bool +MultipleManipulatorState::UpdateCursor() +{ + if (fPreviousManipulator && fManipulators.HasItem(fPreviousManipulator)) + return fPreviousManipulator->UpdateCursor(); + return false; +} + // #pragma mark - // AddManipulator Modified: haiku/trunk/src/apps/icon-o-matic/generic/gui/stateview/MultipleManipulatorState.h =================================================================== --- haiku/trunk/src/apps/icon-o-matic/generic/gui/stateview/MultipleManipulatorState.h 2007-04-09 00:09:00 UTC (rev 20622) +++ haiku/trunk/src/apps/icon-o-matic/generic/gui/stateview/MultipleManipulatorState.h 2007-04-09 08:30:28 UTC (rev 20623) @@ -1,5 +1,5 @@ /* - * Copyright 2006, Haiku. + * Copyright 2006-2007, Haiku. * Distributed under the terms of the MIT License. * * Authors: @@ -44,6 +44,8 @@ virtual bool HandleKeyUp(uint32 key, uint32 modifiers, Command** _command); + virtual bool UpdateCursor(); + // MultipleManipulatorState bool AddManipulator(Manipulator* manipulator); Manipulator* RemoveManipulator(int32 index); Modified: haiku/trunk/src/apps/icon-o-matic/generic/gui/stateview/StateView.cpp =================================================================== --- haiku/trunk/src/apps/icon-o-matic/generic/gui/stateview/StateView.cpp 2007-04-09 00:09:00 UTC (rev 20622) +++ haiku/trunk/src/apps/icon-o-matic/generic/gui/stateview/StateView.cpp 2007-04-09 08:30:28 UTC (rev 20623) @@ -1,5 +1,5 @@ /* - * Copyright 2006, Haiku. + * Copyright 2006-2007, Haiku. * Distributed under the terms of the MIT License. * * Authors: @@ -78,7 +78,8 @@ float y; if (message->FindFloat("be:wheel_delta_x", &x) >= B_OK && message->FindFloat("be:wheel_delta_y", &y) >= B_OK) { - if (fTarget->MouseWheelChanged(x, y)) + if (fTarget->MouseWheelChanged( + fTarget->MouseInfo()->position, x, y)) result = B_SKIP_MESSAGE; } break; @@ -330,6 +331,15 @@ fCurrentState->Init(); } +// UpdateStateCursor +void +StateView::UpdateStateCursor() +{ + if (!fCurrentState || !fCurrentState->UpdateCursor()) { + SetViewCursor(B_CURSOR_SYSTEM_DEFAULT, true); + } +} + // Draw void StateView::Draw(BView* into, BRect updateRect) @@ -350,7 +360,7 @@ // MouseWheelChanged bool -StateView::MouseWheelChanged(float x, float y) +StateView::MouseWheelChanged(BPoint where, float x, float y) { return false; } @@ -359,6 +369,11 @@ bool StateView::HandleKeyDown(uint32 key, uint32 modifiers) { + // down't allow key events if mouse already pressed + // (central place to prevent command stack mix up) + if (fMouseInfo.buttons != 0) + return false; + AutoWriteLocker locker(fLocker); if (fLocker && !locker.IsLocked()) return false; @@ -380,6 +395,11 @@ bool StateView::HandleKeyUp(uint32 key, uint32 modifiers) { + // down't allow key events if mouse already pressed + // (central place to prevent command stack mix up) + if (fMouseInfo.buttons != 0) + return false; + AutoWriteLocker locker(fLocker); if (fLocker && !locker.IsLocked()) return false; Modified: haiku/trunk/src/apps/icon-o-matic/generic/gui/stateview/StateView.h =================================================================== --- haiku/trunk/src/apps/icon-o-matic/generic/gui/stateview/StateView.h 2007-04-09 00:09:00 UTC (rev 20622) +++ haiku/trunk/src/apps/icon-o-matic/generic/gui/stateview/StateView.h 2007-04-09 08:30:28 UTC (rev 20623) @@ -1,5 +1,5 @@ /* - * Copyright 2006, Haiku. + * Copyright 2006-2007, Haiku. * Distributed under the terms of the MIT License. * * Authors: @@ -40,10 +40,12 @@ // StateView interface void SetState(ViewState* state); + void UpdateStateCursor(); void Draw(BView* into, BRect updateRect); - virtual bool MouseWheelChanged(float x, float y); + virtual bool MouseWheelChanged(BPoint where, + float x, float y); bool HandleKeyDown(uint32 key, uint32 modifiers); bool HandleKeyUp(uint32 key, uint32 modifiers); Modified: haiku/trunk/src/apps/icon-o-matic/generic/gui/stateview/ViewState.cpp =================================================================== --- haiku/trunk/src/apps/icon-o-matic/generic/gui/stateview/ViewState.cpp 2007-04-09 00:09:00 UTC (rev 20622) +++ haiku/trunk/src/apps/icon-o-matic/generic/gui/stateview/ViewState.cpp 2007-04-09 08:30:28 UTC (rev 20623) @@ -1,5 +1,5 @@ /* - * Copyright 2006, Haiku. + * Copyright 2006-2007, Haiku. * Distributed under the terms of the MIT License. * * Authors: @@ -109,4 +109,9 @@ return false; } - +// UpdateCursor +bool +ViewState::UpdateCursor() +{ + return false; +} Modified: haiku/trunk/src/apps/icon-o-matic/generic/gui/stateview/ViewState.h =================================================================== --- haiku/trunk/src/apps/icon-o-matic/generic/gui/stateview/ViewState.h 2007-04-09 00:09:00 UTC (rev 20622) +++ haiku/trunk/src/apps/icon-o-matic/generic/gui/stateview/ViewState.h 2007-04-09 08:30:28 UTC (rev 20623) @@ -1,5 +1,5 @@ /* - * Copyright 2006, Haiku. + * Copyright 2006-2007, Haiku. * Distributed under the terms of the MIT License. * * Authors: @@ -57,7 +57,9 @@ virtual bool HandleKeyUp(uint32 key, uint32 modifiers, Command** _command); + virtual bool UpdateCursor(); + inline uint32 PressedMouseButtons() const { return fMouseInfo->buttons; } Modified: haiku/trunk/src/apps/icon-o-matic/generic/gui/ui_defines.h =================================================================== --- haiku/trunk/src/apps/icon-o-matic/generic/gui/ui_defines.h 2007-04-09 00:09:00 UTC (rev 20622) +++ haiku/trunk/src/apps/icon-o-matic/generic/gui/ui_defines.h 2007-04-09 08:30:28 UTC (rev 20623) @@ -1,5 +1,5 @@ /* - * Copyright 2006, Haiku. + * Copyright 2006-2007, Haiku. * Distributed under the terms of the MIT License. * * Authors: Modified: haiku/trunk/src/apps/icon-o-matic/import_export/svg/DocumentBuilder.h =================================================================== --- haiku/trunk/src/apps/icon-o-matic/import_export/svg/DocumentBuilder.h 2007-04-09 00:09:00 UTC (rev 20622) +++ haiku/trunk/src/apps/icon-o-matic/import_export/svg/DocumentBuilder.h 2007-04-09 08:30:28 UTC (rev 20623) @@ -1,5 +1,5 @@ /* - * Copyright 2006, Haiku. All rights reserved. + * Copyright 2006-2007, Haiku. All rights reserved. * Distributed under the terms of the MIT License. * * Authors: Modified: haiku/trunk/src/apps/icon-o-matic/shape/PathManipulator.cpp =================================================================== --- haiku/trunk/src/apps/icon-o-matic/shape/PathManipulator.cpp 2007-04-09 00:09:00 UTC (rev 20622) +++ haiku/trunk/src/apps/icon-o-matic/shape/PathManipulator.cpp 2007-04-09 08:30:28 UTC (rev 20623) @@ -1,5 +1,5 @@ /* - * Copyright 2006, Haiku. + * Copyright 2006-2007, Haiku. * Distributed under the terms of the MIT License. * * Authors: @@ -26,6 +26,7 @@ #include "ChangePointCommand.h" //#include "CloseCommand.h" #include "InsertPointCommand.h" +#include "FlipPointsCommand.h" //#include "NewPathCommand.h" #include "NudgePointsCommand.h" //#include "RemovePathCommand.h" @@ -74,6 +75,7 @@ MSG_UPDATE_SHAPE_UI = 'udsi', MSG_SPLIT_POINTS = 'splt', + MSG_FLIP_POINTS = 'flip', }; inline const char* @@ -773,6 +775,11 @@ item->SetEnabled(hasSelection); menu->AddItem(item); + message = new BMessage(MSG_FLIP_POINTS); + item = new BMenuItem("Flip", message); + item->SetEnabled(hasSelection); + menu->AddItem(item); + message = new BMessage(MSG_REMOVE_POINTS); item = new BMenuItem("Remove", message, 'A'); item->SetEnabled(hasSelection); @@ -829,6 +836,11 @@ fSelection->Items(), fSelection->CountItems()); break; + case MSG_FLIP_POINTS: + *_command = new FlipPointsCommand(fPath, + fSelection->Items(), + fSelection->CountItems()); + break; case B_SELECT_ALL: { *fOldSelection = *fSelection; fSelection->MakeEmpty(); @@ -958,13 +970,12 @@ } // UpdateCursor -void +bool PathManipulator::UpdateCursor() { - if (fTransformBox) { - fTransformBox->UpdateCursor(); - return; - } + if (fTransformBox) + return fTransformBox->UpdateCursor(); + const uchar* cursorData; switch (fMode) { case ADD_POINT: @@ -1008,6 +1019,8 @@ BCursor cursor(cursorData); fCanvasView->SetViewCursor(&cursor, true); fCanvasView->Sync(); + + return true; } // AttachedToView Modified: haiku/trunk/src/apps/icon-o-matic/shape/PathManipulator.h =================================================================== --- haiku/trunk/src/apps/icon-o-matic/shape/PathManipulator.h 2007-04-09 00:09:00 UTC (rev 20622) +++ haiku/trunk/src/apps/icon-o-matic/shape/PathManipulator.h 2007-04-09 08:30:28 UTC (rev 20623) @@ -1,5 +1,5 @@ /* - * Copyright 2006, Haiku. + * Copyright 2006-2007, Haiku. * Distributed under the terms of the MIT License. * * Authors: @@ -59,7 +59,7 @@ virtual bool HandleKeyUp(uint32 key, uint32 modifiers, Command** _command); - virtual void UpdateCursor(); + virtual bool UpdateCursor(); virtual void AttachedToView(BView* view); virtual void DetachedFromView(BView* view); Modified: haiku/trunk/src/apps/icon-o-matic/shape/commands/ChangePointCommand.cpp =================================================================== --- haiku/trunk/src/apps/icon-o-matic/shape/commands/ChangePointCommand.cpp 2007-04-09 00:09:00 UTC (rev 20622) +++ haiku/trunk/src/apps/icon-o-matic/shape/commands/ChangePointCommand.cpp 2007-04-09 08:30:28 UTC (rev 20623) @@ -39,6 +39,32 @@ delete[] fOldSelection; } +// InitCheck +status_t +ChangePointCommand::InitCheck() +{ + // TODO: figure out if selection changed!!! + // (this command is also used to undo changes to the selection) + // (but tracking the selection does not yet work in Icon-O-Matic) + + status_t ret = PathCommand::InitCheck(); + if (ret < B_OK) + return ret; + + BPoint point; + BPoint pointIn; + BPoint pointOut; + bool connected; + if (!fPath->GetPointsAt(fIndex, point, pointIn, pointOut, &connected)) + return B_ERROR; + + if (point != fPoint || pointIn != fPointIn + || pointOut != fPointOut || connected != fConnected) + return B_OK; + + return B_ERROR; +} + // Perform status_t ChangePointCommand::Perform() Modified: haiku/trunk/src/apps/icon-o-matic/shape/commands/ChangePointCommand.h =================================================================== --- haiku/trunk/src/apps/icon-o-matic/shape/commands/ChangePointCommand.h 2007-04-09 00:09:00 UTC (rev 20622) +++ haiku/trunk/src/apps/icon-o-matic/shape/commands/ChangePointCommand.h 2007-04-09 08:30:28 UTC (rev 20623) @@ -21,6 +21,8 @@ int32 count); virtual ~ChangePointCommand(); + virtual status_t InitCheck(); + virtual status_t Perform(); virtual status_t Undo(); virtual status_t Redo(); Modified: haiku/trunk/src/apps/icon-o-matic/transformable/ResetTransformationCommand.h =================================================================== --- haiku/trunk/src/apps/icon-o-matic/transformable/ResetTransformationCommand.h 2007-04-09 00:09:00 UTC (rev 20622) +++ haiku/trunk/src/apps/icon-o-matic/transformable/ResetTransformationCommand.h 2007-04-09 08:30:28 UTC (rev 20623) @@ -1,5 +1,5 @@ /* - * Copyright 2006, Haiku. All rights reserved. + * Copyright 2006-2007, Haiku. All rights reserved. * Distributed under the terms of the MIT License. * * Authors: Modified: haiku/trunk/src/apps/icon-o-matic/transformable/TransformBox.cpp =================================================================== --- haiku/trunk/src/apps/icon-o-matic/transformable/TransformBox.cpp 2007-04-09 00:09:00 UTC (rev 20622) +++ haiku/trunk/src/apps/icon-o-matic/transformable/TransformBox.cpp 2007-04-09 08:30:28 UTC (rev 20623) @@ -1,5 +1,5 @@ /* - * Copyright 2006, Haiku. + * Copyright 2006-2007, Haiku. * Distributed under the terms of the MIT License. * * Authors: @@ -299,16 +299,19 @@ return false; } -// #pragma mark - - // UpdateCursor -void +bool TransformBox::UpdateCursor() { - if (fCurrentState) + if (fCurrentState) { fCurrentState->UpdateViewCursor(fView, fMousePos); + return true; + } + return false; } +// #pragma mark - + // AttachedToView void TransformBox::AttachedToView(BView* view) Modified: haiku/trunk/src/apps/icon-o-matic/transformable/TransformBox.h =================================================================== --- haiku/trunk/src/apps/icon-o-matic/transformable/TransformBox.h 2007-04-09 00:09:00 UTC (rev 20622) +++ haiku/trunk/src/apps/icon-o-matic/transformable/TransformBox.h 2007-04-09 08:30:28 UTC (rev 20623) @@ -1,5 +1,5 @@ /* - * Copyright 2006, Haiku. + * Copyright 2006-2007, Haiku. * Distributed under the terms of the MIT License. * * Authors: @@ -54,7 +54,7 @@ virtual bool HandleKeyUp(uint32 key, uint32 modifiers, Command** _command); - virtual void UpdateCursor(); + virtual bool UpdateCursor(); virtual void AttachedToView(BView* view); virtual void DetachedFromView(BView* view); Modified: haiku/trunk/src/apps/icon-o-matic/transformable/TransformCommand.cpp =================================================================== --- haiku/trunk/src/apps/icon-o-matic/transformable/TransformCommand.cpp 2007-04-09 00:09:00 UTC (rev 20622) +++ haiku/trunk/src/apps/icon-o-matic/transformable/TransformCommand.cpp 2007-04-09 08:30:28 UTC (rev 20623) @@ -1,5 +1,5 @@ /* - * Copyright 2006, Haiku. + * Copyright 2006-2007, Haiku. * Distributed under the terms of the MIT License. * * Authors: @@ -72,8 +72,8 @@ || fNewXScale != fOldXScale || fNewYScale != fOldYScale)) return B_OK; - else - return B_NO_INIT; + + return B_NO_INIT; [... truncated: 59 lines follow ...] From hugosantos at mail.berlios.de Mon Apr 9 11:35:01 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Mon, 9 Apr 2007 11:35:01 +0200 Subject: [Haiku-commits] r20624 - haiku/trunk/src/add-ons/kernel/network/protocols/tcp Message-ID: <200704090935.l399Z1S9032316@sheep.berlios.de> Author: hugosantos Date: 2007-04-09 11:34:47 +0200 (Mon, 09 Apr 2007) New Revision: 20624 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20624&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/BufferQueue.cpp haiku/trunk/src/add-ons/kernel/network/protocols/tcp/BufferQueue.h haiku/trunk/src/add-ons/kernel/network/protocols/tcp/EndpointManager.cpp haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.cpp haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.h Log: fixed multiple TCP issues. - Moved FIN handling to after Segment Text handling, it matches the RFC and fixes a possible issue with a user missing some final segment data when receiving a FIN. - Fixed the FIN handling to better terminate connections (no more senseless chatter in the end with RSTs etc). - When Bind()ing, set the socket address so a call to getsockname() gets the allocated port correctly. - After reaching the ESTABLISHED state, try to wake all pending threads (still needs work). - Corrected the maximum amount of time we wait in SendData() to respect socket->send.timeout. - Now ReadData() behaves correctly in all possible states. - There was a missing handling of MSG_DONTWAIT, fixed. - Better internal handling of PSH. Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/BufferQueue.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/BufferQueue.cpp 2007-04-09 08:30:28 UTC (rev 20623) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/BufferQueue.cpp 2007-04-09 09:34:47 UTC (rev 20624) @@ -355,7 +355,10 @@ } void -BufferQueue::SetPushPointer(tcp_sequence sequence) +BufferQueue::SetPushPointer() { - fPushPointer = sequence; + if (fList.IsEmpty()) + fPushPointer = 0; + else + fPushPointer = fList.Tail()->sequence + fList.Tail()->size; } Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/BufferQueue.h =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/BufferQueue.h 2007-04-09 08:30:28 UTC (rev 20623) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/BufferQueue.h 2007-04-09 09:34:47 UTC (rev 20624) @@ -33,9 +33,16 @@ size_t Available() const { return fContiguousBytes; } size_t Available(tcp_sequence sequence) const; - size_t PushedData() const { return fPushPointer > fFirstSequence ? fPushPointer - fFirstSequence : 0; } - void SetPushPointer(tcp_sequence sequence); + size_t PushedData() const + { + // we must check if fPushPointer is not 0 here due to + // `tcp_sequence's special handling of > + return fPushPointer != 0 && fPushPointer > fFirstSequence ? + fPushPointer - fFirstSequence : 0; + } + void SetPushPointer(); + size_t Used() const { return fNumBytes; } size_t Free() const { return fMaxBytes - fNumBytes; } Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/EndpointManager.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/EndpointManager.cpp 2007-04-09 08:30:28 UTC (rev 20623) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/EndpointManager.cpp 2007-04-09 09:34:47 UTC (rev 20624) @@ -132,6 +132,8 @@ EndpointManager::SetConnection(TCPEndpoint *endpoint, const sockaddr *local, const sockaddr *peer, const sockaddr *interfaceLocal) { + TRACE(("EndpointManager::SetConnection(%p)\n", endpoint)); + RecursiveLocker locker(&fLock); sockaddr localBuffer; @@ -212,6 +214,8 @@ status_t EndpointManager::Bind(TCPEndpoint *endpoint, sockaddr *address) { + TRACE(("EndpointManager::Bind(%p, %s)\n", endpoint, AddressString(gDomain, address, true).Data())); + if (gAddressModule->is_empty_address(address, true)) return B_BAD_VALUE; @@ -255,6 +259,8 @@ } else hash_insert(fEndpointHash, endpoint); + gAddressModule->set_to((sockaddr *)&endpoint->socket->address, address); + endpoint->fEndpointNextWithSamePort = NULL; hash_insert(fConnectionHash, endpoint); @@ -265,6 +271,8 @@ status_t EndpointManager::BindToEphemeral(TCPEndpoint *endpoint, sockaddr *address) { + TRACE(("EndpointManager::BindToEphemeral(%p)\n", endpoint)); + RecursiveLocker locker(&fLock); uint32 max = kFirstEphemeralPort + 65536; @@ -284,7 +292,10 @@ TCPEndpoint *other = _LookupEndpoint(port); if (other == NULL) { // found a port + gAddressModule->set_to_empty_address((sockaddr *)&endpoint->socket->address); gAddressModule->set_port((sockaddr *)&endpoint->socket->address, port); + TRACE((" EndpointManager::BindToEphemeral(%p) -> %s\n", endpoint, + AddressString(gDomain, (sockaddr *)&endpoint->socket->address, true).Data())); endpoint->fEndpointNextWithSamePort = NULL; hash_insert(fEndpointHash, endpoint); hash_insert(fConnectionHash, endpoint); @@ -308,9 +319,6 @@ RecursiveLocker locker(&fLock); - if (!endpoint->IsBound()) - return B_BAD_VALUE; - TCPEndpoint *other = _LookupEndpoint(gAddressModule->get_port((sockaddr *)&endpoint->socket->address)); if (other != endpoint) { // remove endpoint from the list of endpoints with the same port Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-09 08:30:28 UTC (rev 20623) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-09 09:34:47 UTC (rev 20624) @@ -59,10 +59,30 @@ FLAG_OPTION_WINDOW_SHIFT = 0x01, FLAG_OPTION_TIMESTAMP = 0x02, FLAG_NO_RECEIVE = 0x04, - FLAG_NO_SEND = 0x08, }; +static status_t +wait_on_locker(RecursiveLocker &locker, sem_id sem, bigtime_t timeout) +{ + locker.Unlock(); + status_t status = acquire_sem_etc(sem, 1, B_ABSOLUTE_TIMEOUT | + B_CAN_INTERRUPT, timeout); + locker.Lock(); + return status; +} + + +static inline bigtime_t +absolute_timeout(bigtime_t timeout) +{ + if (timeout == 0 || timeout == B_INFINITE_TIMEOUT) + return timeout; + + return timeout + system_time(); +} + + TCPEndpoint::TCPEndpoint(net_socket *socket) : fOptions(0), @@ -167,27 +187,23 @@ if (status != B_OK) return status; - TRACE("Close(): Entering state %d", fState); + TRACE("Close(): Entering state %s", name_for_state(fState)); if (socket->options & SO_LINGER) { TRACE("Close(): Lingering for %i secs", socket->linger); - bigtime_t maximum = system_time() + socket->linger * 1000000LL; + bigtime_t maximum = absolute_timeout(socket->linger * 1000000LL); while (fSendQueue.Used() > 0) { - lock.Unlock(); - status = acquire_sem_etc(fSendLock, 1, B_CAN_INTERRUPT - | B_ABSOLUTE_TIMEOUT, maximum); - if (status == B_TIMED_OUT) { - TRACE("Close(): Lingering made me wait, but not all data was sent."); - return B_OK; - } else if (status < B_OK) + status = wait_on_locker(lock, fSendLock, maximum); + if (status == B_TIMED_OUT) + break; + else if (status < B_OK) return status; - - lock.Lock(); } - TRACE("Close(): Waited for all data to be sent with success"); + TRACE("Close(): after waiting, the SendQ was left with %lu bytes.", + fSendQueue.Used()); } // TODO: do i need to wait until fState returns to CLOSED? @@ -225,7 +241,7 @@ RecursiveLocker locker(&fLock); - TRACE(" Connect(): in state %d", fState); + TRACE(" Connect(): in state %s", name_for_state(fState)); // Can only call connect() from CLOSED or LISTEN states // otherwise endpoint is considered already connected @@ -319,6 +335,9 @@ status_t TCPEndpoint::Bind(sockaddr *address) { + if (address == NULL) + return B_BAD_VALUE; + TRACE("Bind() on address %s", AddressString(gDomain, address, true).Data()); @@ -376,9 +395,8 @@ RecursiveLocker lock(fLock); - if (direction == SHUT_RD || direction == SHUT_RDWR) { + if (direction == SHUT_RD || direction == SHUT_RDWR) fFlags |= FLAG_NO_RECEIVE; - } if (direction == SHUT_WR || direction == SHUT_RDWR) _ShutdownEgress(false); @@ -398,14 +416,25 @@ RecursiveLocker lock(fLock); - if (fFlags & FLAG_NO_SEND) { + if (fState == CLOSED) + return ENOTCONN; + else if (fState == LISTEN) { + // TODO change socket from passive to active. + return EOPNOTSUPP; + } else if (fState == FINISH_SENT || fState == FINISH_ACKNOWLEDGED + || fState == CLOSING || fState == WAIT_FOR_FINISH_ACKNOWLEDGE + || fState == TIME_WAIT) { // TODO: send SIGPIPE signal to app? return EPIPE; } size_t bytesLeft = buffer->size; + bigtime_t timeout = absolute_timeout(socket->send.timeout); + do { + // TODO we should not segment here, but on TX. + net_buffer *chunk; if (bytesLeft > socket->send.buffer_size) { // divide the buffer in multiple of the maximum segment size @@ -421,14 +450,9 @@ chunk = buffer; while (fSendQueue.Free() < chunk->size) { - lock.Unlock(); - - status_t status = acquire_sem_etc(fSendLock, 1, - B_RELATIVE_TIMEOUT | B_CAN_INTERRUPT, socket->send.timeout); + status_t status = wait_on_locker(lock, fSendLock, timeout); if (status < B_OK) return status; - - lock.Lock(); } // TODO: check state! @@ -441,8 +465,11 @@ size_t chunkSize = chunk->size; fSendQueue.Add(chunk); - status_t status = _SendQueued(); + status_t status = B_OK; + if (fState == ESTABLISHED || fState == FINISH_RECEIVED) + status = _SendQueued(); + if (buffer != chunk) { // as long as we didn't eat the buffer, we can still return an error code // (we don't own the buffer if we return an error code) @@ -474,31 +501,25 @@ RecursiveLocker locker(fLock); + *_buffer = NULL; + + if (fState == CLOSED) + return ENOTCONN; + + bigtime_t timeout = absolute_timeout(socket->receive.timeout); + if (fState == SYNCHRONIZE_SENT || fState == SYNCHRONIZE_RECEIVED) { - // we need to wait until the connection becomes established if (flags & MSG_DONTWAIT) return B_WOULD_BLOCK; - locker.Unlock(); - - status_t status = acquire_sem_etc(fSendLock, 1, - B_RELATIVE_TIMEOUT | B_CAN_INTERRUPT, socket->receive.timeout); - if (status < B_OK) - return status; - - locker.Lock(); + while (fState != ESTABLISHED) { + // we need to wait until the connection becomes established + status_t status = wait_on_locker(locker, fSendLock, timeout); + if (status < B_OK) + return status; + } } - if ((fFlags & FLAG_NO_RECEIVE) != 0 && fReceiveQueue.Available() == 0) { - // there is no data left in the queue, and we can't receive anything, - // anymore - *_buffer = NULL; - return B_OK; - } - - // read data out of buffer - // TODO: add support for urgent data (MSG_OOB) - size_t dataNeeded = socket->receive.low_water_mark; // When MSG_WAITALL is set then the function should block @@ -506,49 +527,65 @@ if (flags & MSG_WAITALL) dataNeeded = numBytes; - bigtime_t timeout = socket->receive.timeout; - if (timeout != B_INFINITE_TIMEOUT) - timeout += system_time(); + // TODO: add support for urgent data (MSG_OOB) - while ((fFlags & FLAG_NO_RECEIVE) == 0 - && fReceiveQueue.Available() < dataNeeded - && (fReceiveQueue.PushedData() == 0 - || fReceiveQueue.Available() < fReceiveQueue.PushedData())) { - locker.Unlock(); + while (true) { + if (fState == CLOSING || fState == WAIT_FOR_FINISH_ACKNOWLEDGE + || fState == TIME_WAIT) { + // ``Connection closing''. + return B_OK; + } - status_t status = acquire_sem_etc(fReceiveLock, 1, - B_ABSOLUTE_TIMEOUT | B_CAN_INTERRUPT, timeout); + if (fReceiveQueue.Available() > dataNeeded || + (fReceiveQueue.PushedData() > 0 + && (fReceiveQueue.PushedData() >= fReceiveQueue.Available()))) + break; - locker.Lock(); + if (fState == FINISH_RECEIVED) { + // ``If no text is awaiting delivery, the RECEIVE will + // get a Connection closing''. + return B_OK; + } + if (flags & MSG_DONTWAIT) + return B_WOULD_BLOCK; + + status_t status = wait_on_locker(locker, fReceiveLock, timeout); if (status < B_OK) { // The Open Group base specification mentions that EINTR should be // returned if the recv() is interrupted before _any data_ is // available. So we actually check if there is data, and if so, // push it to the user. if ((status == B_TIMED_OUT || status == B_INTERRUPTED) - && fReceiveQueue.Available() > 0) + && fReceiveQueue.Available() > 0) break; + return status; } } - TRACE("ReadData(): read %lu bytes, %lu are available (flags 0x%x)", - numBytes, fReceiveQueue.Available(), (unsigned int)fFlags); + TRACE(" ReadData(): read %lu bytes, %lu are available.", + numBytes, fReceiveQueue.Available()); if (numBytes < fReceiveQueue.Available()) release_sem_etc(fReceiveLock, 1, B_DO_NOT_RESCHEDULE); - return fReceiveQueue.Get(numBytes, (flags & MSG_PEEK) == 0, _buffer); + ssize_t receivedBytes = fReceiveQueue.Get(numBytes, + (flags & MSG_PEEK) == 0, _buffer); + + TRACE(" ReadData(): %lu bytes kept.", fReceiveQueue.Available()); + + return receivedBytes; } ssize_t TCPEndpoint::ReadAvailable() { - TRACE("ReadAvailable()"); + RecursiveLocker locker(fLock); - RecursiveLocker locker(fLock); + TRACE("ReadAvailable(): %li", _AvailableData()); + return _AvailableData(); } @@ -743,9 +780,7 @@ release_sem_etc(fAcceptSemaphore, 1, B_DO_NOT_RESCHEDULE); } - release_sem_etc(fSendLock, 1, B_DO_NOT_RESCHEDULE); - release_sem_etc(fReceiveLock, 1, B_DO_NOT_RESCHEDULE); - // TODO: this is not enough - we need to use B_RELEASE_ALL + release_sem_etc(fSendLock, 0, B_DO_NOT_RESCHEDULE | B_RELEASE_ALL); _NotifyReader(); } else { // simultaneous open @@ -762,8 +797,8 @@ int32 TCPEndpoint::Receive(tcp_segment_header &segment, net_buffer *buffer) { - TRACE("Receive(): Connection in state %d received packet %p (%lu bytes) with flags 0x%x, seq %lu, ack %lu!", - fState, buffer, buffer->size, segment.flags, segment.sequence, segment.acknowledge); + TRACE("Receive(): Connection in state %s received packet %p (%lu bytes) with flags 0x%x, seq %lu, ack %lu!", + name_for_state(fState), buffer, buffer->size, segment.flags, segment.sequence, segment.acknowledge); // TODO: rethink locking! @@ -804,25 +839,21 @@ } } else if (segment.acknowledge == fSendUnacknowledged && fReceiveQueue.IsContiguous() - && fReceiveQueue.Free() >= buffer->size) { + && fReceiveQueue.Free() >= buffer->size + && !(fFlags & FLAG_NO_RECEIVE)) { TRACE("Receive(): header prediction receive!"); // we're on the receiving end of the connection, and this segment // is the one we were expecting, in-sequence - if (fFlags & FLAG_NO_RECEIVE) { - return DROP; - } else { - fReceiveNext += buffer->size; - TRACE("Receive(): receive next = %lu", (uint32)fReceiveNext); - fReceiveQueue.Add(buffer, segment.sequence); - if (segment.flags & TCP_FLAG_PUSH) - fReceiveQueue.SetPushPointer(fReceiveNext); + fReceiveNext += buffer->size; + TRACE("Receive(): receive next = %lu", (uint32)fReceiveNext); + fReceiveQueue.Add(buffer, segment.sequence); + if (segment.flags & TCP_FLAG_PUSH) + fReceiveQueue.SetPushPointer(); - release_sem_etc(fReceiveLock, 1, B_DO_NOT_RESCHEDULE); - // TODO: real conditional locking needed! - _NotifyReader(); + _NotifyReader(); - return KEEP | ACKNOWLEDGE; - } + return KEEP | (segment.flags & TCP_FLAG_PUSH ? + IMMEDIATE_ACKNOWLEDGE : ACKNOWLEDGE); } } @@ -845,8 +876,6 @@ } if (fState != TIME_WAIT && fReceiveQueue.Available() > 0) { - release_sem_etc(fReceiveLock, 1, B_DO_NOT_RESCHEDULE); - // TODO: real conditional locking needed! _NotifyReader(); } else { return DELETE | DROP; @@ -927,9 +956,7 @@ fState = ESTABLISHED; - release_sem_etc(fSendLock, 1, B_DO_NOT_RESCHEDULE); - release_sem_etc(fReceiveLock, 1, B_DO_NOT_RESCHEDULE); - // TODO: real conditional locking needed! + release_sem_etc(fSendLock, 0, B_DO_NOT_RESCHEDULE | B_RELEASE_ALL); _NotifyReader(); } @@ -1009,64 +1036,60 @@ } } - // TODO: ignore data *after* FIN + bool notify = false; + if (buffer->size > 0 && _ShouldReceive()) { + fReceiveQueue.Add(buffer, segment.sequence); + fReceiveNext += buffer->size; + notify = true; + TRACE("Receive(): adding data, receive next = %lu. Now have %lu bytes.", + (uint32)fReceiveNext, fReceiveQueue.Available()); + + if (segment.flags & TCP_FLAG_PUSH) + fReceiveQueue.SetPushPointer(); + } else { + action = (action & ~KEEP) | DROP; + } + if (segment.flags & TCP_FLAG_FINISH) { - TRACE("Receive(): peer is finishing connection!"); - fReceiveNext++; + if (fState != CLOSED && fState != LISTEN && fState != SYNCHRONIZE_SENT) { + TRACE("Receive(): peer is finishing connection!"); + fReceiveNext++; + notify = true; - release_sem_etc(fReceiveLock, 1, B_DO_NOT_RESCHEDULE); - // TODO: real conditional locking needed! - _NotifyReader(); + // FIN implies PSH + fReceiveQueue.SetPushPointer(); - // other side is closing connection; change states - switch (fState) { - case ESTABLISHED: - case SYNCHRONIZE_RECEIVED: - fState = FINISH_RECEIVED; - action |= IMMEDIATE_ACKNOWLEDGE; - break; - case FINISH_ACKNOWLEDGED: - fState = TIME_WAIT; - _EnterTimeWait(); - break; - case FINISH_RECEIVED: - // a second FIN? - break; - case FINISH_SENT: - // simultaneous close - fState = CLOSING; - break; + // RFC 793 states that we must send an ACK to FIN + action |= IMMEDIATE_ACKNOWLEDGE; - default: - break; + // other side is closing connection; change states + switch (fState) { + case ESTABLISHED: + case SYNCHRONIZE_RECEIVED: + fState = FINISH_RECEIVED; + break; + case FINISH_SENT: + // simultaneous close + fState = CLOSING; + break; + case FINISH_ACKNOWLEDGED: + fState = TIME_WAIT; + _EnterTimeWait(); + break; + default: + break; + } } } - if (buffer->size > 0 || (segment.flags & (TCP_FLAG_SYNCHRONIZE | TCP_FLAG_FINISH)) != 0) - action |= ACKNOWLEDGE; - - TRACE("Receive():Entering state %d, segment action %ld", fState, action); - - // state machine is done switching states and the data is good. - // put it in the receive buffer - - if (buffer->size > 0 && (fFlags & FLAG_NO_RECEIVE) == 0) { - fReceiveQueue.Add(buffer, segment.sequence); - fReceiveNext += buffer->size; - TRACE("Receive(): adding data, receive next = %lu!", (uint32)fReceiveNext); - - release_sem_etc(fReceiveLock, 1, B_DO_NOT_RESCHEDULE); - // TODO: real conditional locking needed! + if (notify) _NotifyReader(); - } else - gBufferModule->free(buffer); - if (segment.flags & TCP_FLAG_PUSH) - fReceiveQueue.SetPushPointer(fReceiveQueue.LastSequence()); + if (buffer->size > 0 || (segment.flags & TCP_FLAG_SYNCHRONIZE) != 0) + action |= ACKNOWLEDGE; - if (segment.flags & TCP_FLAG_FINISH) - fFlags |= FLAG_NO_RECEIVE; + TRACE("Receive():Entering state %s, segment action %ld", name_for_state(fState), action); return action; } @@ -1316,8 +1339,6 @@ fState = FINISH_SENT; else if (fState == FINISH_RECEIVED) fState = WAIT_FOR_FINISH_ACKNOWLEDGE; - else if (closing) - fState = CLOSED; else return B_OK; @@ -1327,8 +1348,6 @@ return status; } - fFlags |= FLAG_NO_SEND; - return B_OK; } @@ -1338,9 +1357,7 @@ { ssize_t availableData = fReceiveQueue.Available(); - // FLAG_NO_RECEIVE is set whenever the socket is in a state - // where read() would be non-blocking and return 0. - if ((fFlags & FLAG_NO_RECEIVE) && availableData == 0) + if (availableData == 0 && !_ShouldReceive()) return ENOTCONN; return availableData; @@ -1350,10 +1367,24 @@ void TCPEndpoint::_NotifyReader() { + // TODO maintain a waiting receiver count so we know whether + // we should release or not. + release_sem_etc(fReceiveLock, 1, B_DO_NOT_RESCHEDULE); gSocketModule->notify(socket, B_SELECT_READ, _AvailableData()); } +bool +TCPEndpoint::_ShouldReceive() const +{ + if (fFlags & FLAG_NO_RECEIVE) + return false; + + return fState == ESTABLISHED || fState == FINISH_SENT + || fState == FINISH_ACKNOWLEDGED; +} + + // #pragma mark - timer Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h 2007-04-09 08:30:28 UTC (rev 20623) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h 2007-04-09 09:34:47 UTC (rev 20624) @@ -69,6 +69,7 @@ status_t _ShutdownEgress(bool closing); ssize_t _AvailableData() const; void _NotifyReader(); + bool _ShouldReceive() const; static void _TimeWaitTimer(net_timer *timer, void *data); static void _RetransmitTimer(net_timer *timer, void *data); Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.cpp 2007-04-09 08:30:28 UTC (rev 20623) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.cpp 2007-04-09 09:34:47 UTC (rev 20624) @@ -260,7 +260,7 @@ } -static const char * +const char * name_for_state(tcp_state state) { switch (state) { Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.h =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.h 2007-04-09 08:30:28 UTC (rev 20623) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.h 2007-04-09 09:34:47 UTC (rev 20624) @@ -168,4 +168,6 @@ status_t add_tcp_header(tcp_segment_header &segment, net_buffer *buffer); +const char *name_for_state(tcp_state state); + #endif // TCP_H From axeld at pinc-software.de Mon Apr 9 19:13:41 2007 From: axeld at pinc-software.de (Axel =?iso-8859-15?q?D=F6rfler?=) Date: Mon, 09 Apr 2007 19:13:41 +0200 CEST Subject: [Haiku-commits] =?iso-8859-15?q?r20611_-_haiku/trunk/src/add-ons/?= =?iso-8859-15?q?kernel/network/stack?= In-Reply-To: <200704080550.l385oZss001513@sheep.berlios.de> Message-ID: <2834919765-BeMail@zon> hugosantos at mail.berlios.de wrote: > + BenaphoreLocker rx_lock(interface->rx_lock); Another coding style violation: the former would be rxLock :-) Bye, Axel. From axeld at pinc-software.de Mon Apr 9 19:14:14 2007 From: axeld at pinc-software.de (Axel =?iso-8859-15?q?D=F6rfler?=) Date: Mon, 09 Apr 2007 19:14:14 +0200 CEST Subject: [Haiku-commits] =?iso-8859-15?q?r20611_-_haiku/trunk/src/add-ons/?= =?iso-8859-15?q?kernel/network/stack?= In-Reply-To: <200704080550.l385oZss001513@sheep.berlios.de> Message-ID: <2867061016-BeMail@zon> hugosantos at mail.berlios.de wrote: > + switch (option) { > + case SIOCGIFINDEX: And the case is indented by one tab, too. Bye, Axel. From axeld at pinc-software.de Mon Apr 9 19:23:13 2007 From: axeld at pinc-software.de (Axel =?iso-8859-15?q?D=F6rfler?=) Date: Mon, 09 Apr 2007 19:23:13 +0200 CEST Subject: [Haiku-commits] =?iso-8859-15?q?r20620_-_in_haiku/trunk=3A_build/?= =?iso-8859-15?q?jam_src/add-ons/kernel/network/datalink=5Fprotocols_src/a?= =?iso-8859-15?q?dd-ons/kernel/network/datalink=5Fprotocols/arp_src/add-on?= =?iso-8859-15?q?s/kernel/network/datalink=5Fprotocols/ipv4=5Fdatagram_src?= =?iso-8859-15?q?/add-ons/kernel/network/stack?= In-Reply-To: <200704082134.l38LYa0Y016380@sheep.berlios.de> Message-ID: <3406691271-BeMail@zon> hugosantos at mail.berlios.de wrote: > +// TODO ETHER_FRAME_TYPE doesn't belong there, we need Layer 2 > +// independence. > +static const int32 kIPv4FrameType = ETHER_FRAME_TYPE | > ETHER_TYPE_IP; And that's why I thought the ARP module would be a good place for this :-) Bye, Axel. From hugosantos at gmail.com Mon Apr 9 19:24:17 2007 From: hugosantos at gmail.com (Hugo Santos) Date: Mon, 9 Apr 2007 18:24:17 +0100 Subject: [Haiku-commits] r20611 - haiku/trunk/src/add-ons/kernel/network/stack In-Reply-To: <2834919765-BeMail@zon> References: <200704080550.l385oZss001513@sheep.berlios.de> <2834919765-BeMail@zon> Message-ID: <9c46321e0704091024w383fdb57me21ae288d4321e4e@mail.gmail.com> On 4/9/07, Axel D?rfler wrote: > hugosantos at mail.berlios.de wrote: > > + BenaphoreLocker rx_lock(interface->rx_lock); > > Another coding style violation: the former would be rxLock :-) Ok, thanks. I'll change this whenever i touch that code again. Hugo From hugosantos at gmail.com Mon Apr 9 19:28:40 2007 From: hugosantos at gmail.com (Hugo Santos) Date: Mon, 9 Apr 2007 18:28:40 +0100 Subject: [Haiku-commits] r20620 - in haiku/trunk: build/jam src/add-ons/kernel/network/datalink_protocols src/add-ons/kernel/network/datalink_protocols/arp src/add-ons/kernel/network/datalink_protocols/ipv4_datagram src/add-ons/kernel/network/stack In-Reply-To: <3406691271-BeMail@zon> References: <200704082134.l38LYa0Y016380@sheep.berlios.de> <3406691271-BeMail@zon> Message-ID: <9c46321e0704091028o55f983l9e0ee44daa3e1056@mail.gmail.com> Axel, what if we want to support IPv4 over a tunnel for instance? One that doesn't emulate Ethernet. IPv4 should only be registered once (most stuff uses ETHER_TYPE_IP's value to identify IP anyway). I do see the advantage of ETHER_FRAME_TYPE, but maybe the reader could register type and mask? This way we could install more generic handlers instead of per L2. Hugo On 4/9/07, Axel D?rfler wrote: > hugosantos at mail.berlios.de wrote: > > +// TODO ETHER_FRAME_TYPE doesn't belong there, we need Layer 2 > > +// independence. > > +static const int32 kIPv4FrameType = ETHER_FRAME_TYPE | > > ETHER_TYPE_IP; > > And that's why I thought the ARP module would be a good place for this > :-) > > Bye, > Axel. > > _______________________________________________ > Haiku-commits mailing list > Haiku-commits at lists.berlios.de > https://lists.berlios.de/mailman/listinfo/haiku-commits > From hugosantos at gmail.com Mon Apr 9 19:33:56 2007 From: hugosantos at gmail.com (Hugo Santos) Date: Mon, 9 Apr 2007 18:33:56 +0100 Subject: [Haiku-commits] r20623 - in haiku/trunk/src/apps/icon-o-matic: . generic/command generic/gui generic/gui/stateview import_export/svg shape shape/commands transformable In-Reply-To: <200704090830.l398UVGI028692@sheep.berlios.de> References: <200704090830.l398UVGI028692@sheep.berlios.de> Message-ID: <9c46321e0704091033k3850b15mff19b99c17409dfa@mail.gmail.com> Hey Stephan, It seems you forgot to add FlipPointsCommand.{h,cpp}. :-) Hugo From geist at foobox.com Mon Apr 9 22:04:59 2007 From: geist at foobox.com (Travis Geiselbrecht) Date: Mon, 9 Apr 2007 13:04:59 -0700 Subject: [Haiku-commits] r20611 - haiku/trunk/src/add-ons/kernel/network/stack References: <2834919765-BeMail@zon> Message-ID: <001301c77ae2$5a7a71c0$87020b0a@secretlevel.com> From: "Axel D?rfler" > hugosantos at mail.berlios.de wrote: >> + BenaphoreLocker rx_lock(interface->rx_lock); > > Another coding style violation: the former would be rxLock :-) Boy I betcha that old annoying newos code with the _'s really drives you guys nuts. :) Travis From stippi at mail.berlios.de Mon Apr 9 23:58:27 2007 From: stippi at mail.berlios.de (stippi at BerliOS) Date: Mon, 9 Apr 2007 23:58:27 +0200 Subject: [Haiku-commits] r20625 - haiku/trunk/src/apps/icon-o-matic/shape/commands Message-ID: <200704092158.l39LwRUo028032@sheep.berlios.de> Author: stippi Date: 2007-04-09 23:58:26 +0200 (Mon, 09 Apr 2007) New Revision: 20625 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20625&view=rev Added: haiku/trunk/src/apps/icon-o-matic/shape/commands/FlipPointsCommand.cpp haiku/trunk/src/apps/icon-o-matic/shape/commands/FlipPointsCommand.h Log: fix the build... sorry guys! Added: haiku/trunk/src/apps/icon-o-matic/shape/commands/FlipPointsCommand.cpp =================================================================== --- haiku/trunk/src/apps/icon-o-matic/shape/commands/FlipPointsCommand.cpp 2007-04-09 09:34:47 UTC (rev 20624) +++ haiku/trunk/src/apps/icon-o-matic/shape/commands/FlipPointsCommand.cpp 2007-04-09 21:58:26 UTC (rev 20625) @@ -0,0 +1,111 @@ +/* + * Copyright 2007, Haiku. All rights reserved. + * Distributed under the terms of the MIT License. + * + * Authors: + * Stephan A?mus + */ + +#include "FlipPointsCommand.h" + +#include +#include + +#include "VectorPath.h" + +using std::nothrow; + +// constructor +FlipPointsCommand::FlipPointsCommand(VectorPath* path, + const int32* indices, + int32 count) + : PathCommand(path), + fIndex(NULL), + fCount(0) +{ + if (indices && count > 0) { + fIndex = new (nothrow) int32[count]; + fCount = count; + } + + if (InitCheck() < B_OK) + return; + + memcpy(fIndex, indices, count * sizeof(int32)); +} + +// destructor +FlipPointsCommand::~FlipPointsCommand() +{ + delete[] fIndex; +} + +// InitCheck +status_t +FlipPointsCommand::InitCheck() +{ + status_t status = PathCommand::InitCheck(); + if (status < B_OK) + return status; + if (!fIndex) + status = B_NO_MEMORY; + return status; +} + +// Perform +status_t +FlipPointsCommand::Perform() +{ + status_t status = B_OK; + + AutoNotificationSuspender _(fPath); + + // NOTE: fCount guaranteed > 0 + for (int32 i = 0; i < fCount; i++) { + BPoint point; + BPoint pointIn; + BPoint pointOut; + bool connected; + + if (fPath->GetPointsAt(fIndex[i], point, pointIn, pointOut, &connected)) { +BPoint p1(point - (pointOut - point)); +printf("flip: (%.1f, %.1f) -> (%.1f, %.1f)\n", pointOut.x, pointOut.y, p1.x, p1.y); + // flip "in" and "out" control points + fPath->SetPoint(fIndex[i], + point, + point - (pointIn - point), + point - (pointOut - point), + connected); + } else { + status = B_ERROR; + break; + } + } + + return status; +} + +// Undo +status_t +FlipPointsCommand::Undo() +{ + status_t status = Perform(); + + if (status >= B_OK) { + // restore selection + _Select(fIndex, fCount); + } + + return status; +} + +// GetName +void +FlipPointsCommand::GetName(BString& name) +{ + if (fCount > 1) + name << "Flip Control Points"; + else + name << "Flip Control Point"; +} + Added: haiku/trunk/src/apps/icon-o-matic/shape/commands/FlipPointsCommand.h =================================================================== --- haiku/trunk/src/apps/icon-o-matic/shape/commands/FlipPointsCommand.h 2007-04-09 09:34:47 UTC (rev 20624) +++ haiku/trunk/src/apps/icon-o-matic/shape/commands/FlipPointsCommand.h 2007-04-09 21:58:26 UTC (rev 20625) @@ -0,0 +1,35 @@ +/* + * Copyright 2007, Haiku. All rights reserved. + * Distributed under the terms of the MIT License. + * + * Authors: + * Stephan A?mus + */ + +#ifndef FLIP_POINTS_COMMAND_H +#define FLIP_POINTS_COMMAND_H + +#include "PathCommand.h" + +class BPoint; + +class FlipPointsCommand : public PathCommand { + public: + FlipPointsCommand(VectorPath* path, + const int32* indices, + int32 count); + virtual ~FlipPointsCommand(); + + virtual status_t InitCheck(); + + virtual status_t Perform(); + virtual status_t Undo(); + + virtual void GetName(BString& name); + + private: + int32* fIndex; + int32 fCount; +}; + +#endif // FLIP_POINTS_COMMAND_H From axeld at pinc-software.de Tue Apr 10 00:02:04 2007 From: axeld at pinc-software.de (Axel =?iso-8859-15?q?D=F6rfler?=) Date: Tue, 10 Apr 2007 00:02:04 +0200 CEST Subject: [Haiku-commits] =?iso-8859-15?q?r20611_-_haiku/trunk/src/add-ons/?= =?iso-8859-15?q?kernel/network/stack?= In-Reply-To: <001301c77ae2$5a7a71c0$87020b0a@secretlevel.com> Message-ID: <20137160382-BeMail@zon> "Travis Geiselbrecht" wrote: > From: "Axel D?rfler" > > hugosantos at mail.berlios.de wrote: > >> + BenaphoreLocker rx_lock(interface->rx_lock); > > Another coding style violation: the former would be rxLock :-) > Boy I betcha that old annoying newos code with the _'s really drives > you > guys nuts. :) The '_' is pretty much gone in the mean time ;-) We just try hard to have a consistent coding style in our code base, and there are already so many gray areas... ;) Bye, Axel. From axeld at mail.berlios.de Tue Apr 10 00:29:17 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Tue, 10 Apr 2007 00:29:17 +0200 Subject: [Haiku-commits] r20626 - haiku/trunk/src/add-ons/translators/raw Message-ID: <200704092229.l39MTHg6029795@sheep.berlios.de> Author: axeld Date: 2007-04-10 00:29:16 +0200 (Tue, 10 Apr 2007) New Revision: 20626 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20626&view=rev Modified: haiku/trunk/src/add-ons/translators/raw/RAW.cpp haiku/trunk/src/add-ons/translators/raw/RAW.h haiku/trunk/src/add-ons/translators/raw/RAWTranslator.cpp Log: Now puts the EXIF data verbatim into the message passed to Translate(). Modified: haiku/trunk/src/add-ons/translators/raw/RAW.cpp =================================================================== --- haiku/trunk/src/add-ons/translators/raw/RAW.cpp 2007-04-09 21:58:26 UTC (rev 20625) +++ haiku/trunk/src/add-ons/translators/raw/RAW.cpp 2007-04-09 22:29:16 UTC (rev 20626) @@ -109,7 +109,8 @@ fOutputBitsPerSample(8), fDecodeLeaf(0), fDecodeBitsZeroAfterMax(false), - fFilters(~0) + fFilters(~0), + fEXIFOffset(-1) { fImages = new image_data_info[kImageBufferCount]; fDecodeBuffer = new decode[kDecodeBufferCount]; @@ -2792,6 +2793,10 @@ case 34665: // EXIF tag fRead.Seek(fRead.Next() + baseOffset, SEEK_SET); + + fEXIFOffset = fRead.Position(); + fEXIFLength = tag.length; + _ParseEXIF(baseOffset); break; @@ -3353,3 +3358,15 @@ return B_OK; } + +status_t +DCRaw::GetEXIFTag(off_t& offset, size_t& length) const +{ + if (fEXIFOffset < 0) + return B_ENTRY_NOT_FOUND; + + offset = fEXIFOffset; + length = fEXIFLength; + return B_OK; +} + Modified: haiku/trunk/src/add-ons/translators/raw/RAW.h =================================================================== --- haiku/trunk/src/add-ons/translators/raw/RAW.h 2007-04-09 21:58:26 UTC (rev 20625) +++ haiku/trunk/src/add-ons/translators/raw/RAW.h 2007-04-09 22:29:16 UTC (rev 20626) @@ -63,6 +63,8 @@ uint32 CountImages() const; status_t ImageAt(uint32 index, image_data_info& info) const; + status_t GetEXIFTag(off_t& offset, size_t& length) const; + private: int32 _AllocateImage(); image_data_info& _Raw(); @@ -178,6 +180,8 @@ uint32 fFilters; uint32 fEXIFFilters; + off_t fEXIFOffset; + uint32 fEXIFLength; off_t fCurveOffset; }; Modified: haiku/trunk/src/add-ons/translators/raw/RAWTranslator.cpp =================================================================== --- haiku/trunk/src/add-ons/translators/raw/RAWTranslator.cpp 2007-04-09 21:58:26 UTC (rev 20625) +++ haiku/trunk/src/add-ons/translators/raw/RAWTranslator.cpp 2007-04-09 22:29:16 UTC (rev 20626) @@ -189,6 +189,19 @@ return roster->Translate(&io, NULL, settings, target, outType); } + // retrieve EXIF data + off_t exifOffset; + size_t exifLength; + if (settings != NULL && raw.GetEXIFTag(exifOffset, exifLength) == B_OK) { + void* exifBuffer = malloc(exifLength); + if (exifBuffer != NULL) { + if (source->ReadAt(exifOffset, exifBuffer, exifLength) + == (ssize_t)exifLength) + settings->AddData("exif", B_RAW_TYPE, exifBuffer, exifLength); + + free(exifBuffer); + } + } uint32 dataSize = data.output_width * 4 * data.output_height; TranslatorBitmap header; From hugosantos at mail.berlios.de Tue Apr 10 00:51:19 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Tue, 10 Apr 2007 00:51:19 +0200 Subject: [Haiku-commits] r20627 - haiku/trunk/src/add-ons/kernel/network/protocols/tcp Message-ID: <200704092251.l39MpJiS031690@sheep.berlios.de> Author: hugosantos Date: 2007-04-10 00:50:55 +0200 (Tue, 10 Apr 2007) New Revision: 20627 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20627&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/EndpointManager.cpp Log: Set proper address on BindToEphemeral(). Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/EndpointManager.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/EndpointManager.cpp 2007-04-09 22:29:16 UTC (rev 20626) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/EndpointManager.cpp 2007-04-09 22:50:55 UTC (rev 20627) @@ -292,7 +292,7 @@ TCPEndpoint *other = _LookupEndpoint(port); if (other == NULL) { // found a port - gAddressModule->set_to_empty_address((sockaddr *)&endpoint->socket->address); + gAddressModule->set_to((sockaddr *)&endpoint->socket->address, address); gAddressModule->set_port((sockaddr *)&endpoint->socket->address, port); TRACE((" EndpointManager::BindToEphemeral(%p) -> %s\n", endpoint, AddressString(gDomain, (sockaddr *)&endpoint->socket->address, true).Data())); From hugosantos at mail.berlios.de Tue Apr 10 00:51:28 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Tue, 10 Apr 2007 00:51:28 +0200 Subject: [Haiku-commits] r20628 - in haiku/trunk: build/jam src/bin/network src/bin/network/nc Message-ID: <200704092251.l39MpSjT031837@sheep.berlios.de> Author: hugosantos Date: 2007-04-10 00:51:08 +0200 (Tue, 10 Apr 2007) New Revision: 20628 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20628&view=rev Added: haiku/trunk/src/bin/network/nc/ haiku/trunk/src/bin/network/nc/Jamfile haiku/trunk/src/bin/network/nc/generic.h haiku/trunk/src/bin/network/nc/netcat.c Modified: haiku/trunk/build/jam/HaikuImage haiku/trunk/src/bin/network/Jamfile Log: added 'netcat', which is particularly helpful debugging TCP. Modified: haiku/trunk/build/jam/HaikuImage =================================================================== --- haiku/trunk/build/jam/HaikuImage 2007-04-09 22:50:55 UTC (rev 20627) +++ haiku/trunk/build/jam/HaikuImage 2007-04-09 22:51:08 UTC (rev 20628) @@ -29,7 +29,7 @@ idestatus ifconfig install installsound iroster isvolume join keymap kill less lessecho lesskey link listarea listattr listdev listimage listport listres listsem ln locate logger logname ls lsindex m4 make - makebootable md5sum merge mimeset mkdos mkdir mkindex modifiers mount + makebootable nc md5sum merge mimeset mkdos mkdir mkindex modifiers mount mount_nfs mountvolume mv netstat nl od open pack_cis paste patch pathchk pc ping play playfile playsound playwav pr prio printenv printf ps ptx pwd query quit release renice rescan rlog rm rmattr rmindex rmdir roster route Modified: haiku/trunk/src/bin/network/Jamfile =================================================================== --- haiku/trunk/src/bin/network/Jamfile 2007-04-09 22:50:55 UTC (rev 20627) +++ haiku/trunk/src/bin/network/Jamfile 2007-04-09 22:51:08 UTC (rev 20628) @@ -4,6 +4,7 @@ SubInclude HAIKU_TOP src bin network ftp ; SubInclude HAIKU_TOP src bin network ifconfig ; SubInclude HAIKU_TOP src bin network mount_nfs ; +SubInclude HAIKU_TOP src bin network nc ; SubInclude HAIKU_TOP src bin network netstat ; #SubInclude HAIKU_TOP src bin network pppconfig ; #SubInclude HAIKU_TOP src bin network ppp_up ; Added: haiku/trunk/src/bin/network/nc/Jamfile =================================================================== --- haiku/trunk/src/bin/network/nc/Jamfile 2007-04-09 22:50:55 UTC (rev 20627) +++ haiku/trunk/src/bin/network/nc/Jamfile 2007-04-09 22:51:08 UTC (rev 20628) @@ -0,0 +1,24 @@ +SubDir HAIKU_TOP src bin network nc ; + +SetSubDirSupportedPlatforms $(HAIKU_BONE_COMPATIBLE_PLATFORMS) ; + +if $(TARGET_PLATFORM) != haiku { + UseHeaders [ FDirName $(HAIKU_TOP) headers posix ] : true ; + # We need the public network headers also when not compiling for Haiku. + # Unfortunately we get more than we want, namely all POSIX headers. +} + +BinCommand nc : + netcat.c + : $(NETWORK_LIBS) +; + +HaikuInstall install-networking + : [ FDirName $(HAIKU_TEST_DIR) kits net ] + : nc ; + +HaikuInstall install-userland-networking + : [ FDirName $(HAIKU_TEST_DIR) kits net userland ] + : nc + : installed-userland-networking +; Added: haiku/trunk/src/bin/network/nc/generic.h =================================================================== --- haiku/trunk/src/bin/network/nc/generic.h 2007-04-09 22:50:55 UTC (rev 20627) +++ haiku/trunk/src/bin/network/nc/generic.h 2007-04-09 22:51:08 UTC (rev 20628) @@ -0,0 +1,377 @@ +/* generic.h -- anything you don't #undef at the end remains in effect. + The ONLY things that go in here are generic indicator flags; it's up + to your programs to declare and call things based on those flags. + + You should only need to make changes via a minimal system-specific section + at the end of this file. To build a new section, rip through this and + check everything it mentions on your platform, and #undef that which needs + it. If you generate a system-specific section you didn't find in here, + please mail me a copy so I can update the "master". + + I realize I'm probably inventing another pseudo-standard here, but + goddamnit, everybody ELSE has already, and I can't include all of their + hairball schemes too. HAVE_xx conforms to the gnu/autoconf usage and + seems to be the most common format. In fact, I dug a lot of these out + of autoconf and tried to common them all together using "stupidh" to + collect data from platforms. + + In disgust... _H* 940910, 941115, 950511. Pseudo-version: 1.3 + + Updated 951104 with many patches from netcat feedback, and properly + closed a lot of slop in open-ended comments: version 1.4 + 960217 + nextstep: version 1.5 +*/ + +#ifndef GENERIC_H /* only run through this once */ +#define GENERIC_H + +/* =============================== */ +/* System calls, lib routines, etc */ +/* =============================== */ + +/* How does your system declare malloc, void or char? Usually void, but go + ask the SunOS people why they had to be different... */ +#define VOID_MALLOC + +/* notably from fwtk/firewall.h: posix locking? */ +#define HAVE_FLOCK /* otherwise it's lockf() */ + +/* if you don't have setsid(), you might have setpgrp(). */ +#define HAVE_SETSID + +/* random() is generally considered better than rand() */ +#define HAVE_RANDOM + +/* the srand48/lrand48/etc family is s'posedly even better */ +#define HAVE_RAND48 +/* bmc at telebase and others have suggested these macros if a box *does* have + rand48. Will consider for later if we're doing something that really + requires stronger random numbers, but netcat and such certainly doesn't. +#define srandom(seed) srand48((long) seed) +#define random() lrand48() */ + +/* if your machine doesn't have lstat(), it should have stat() [dos...] */ +#define HAVE_LSTAT + +/* different kinds of term ioctls. How to recognize them, very roughly: + sysv/POSIX_ME_HARDER: termio[s].h, struct termio[s], tty.c_*[] + bsd/old stuff: sgtty.h, ioctl(TIOCSETP), sgttyb.sg_*, tchars.t_* */ +#define HAVE_TERMIOS + +/* dbm vs ndbm */ +#define HAVE_NDBM + +/* extended utmp/wtmp stuff. MOST machines still do NOT have this SV-ism */ +#define UTMPX + +/* some systems have nice() which takes *relative* values... [resource.h] */ +#define HAVE_SETPRIORITY + +/* a sysvism, I think, but ... */ +#define HAVE_SYSINFO + +/* ============= */ +/* Include files */ +/* ============= */ + +/* Presence of these can be determined via a script that sniffs them + out if you aren't sure. See "stupidh"... */ + +/* stdlib comes with most modern compilers, but ya never know */ +#define HAVE_STDLIB_H + +/* not on a DOS box! */ +#define HAVE_UNISTD_H + +/* stdarg is a weird one */ +#define HAVE_STDARG_H + +/* dir.h or maybe ndir.h otherwise. */ +#define HAVE_DIRENT_H + +/* string or strings */ +#define HAVE_STRINGS_H + +/* if you don't have lastlog.h, what you want might be in login.h */ +#define HAVE_LASTLOG_H + +/* predefines for _PATH_various */ +#define HAVE_PATHS_H + +/* some SV-flavors break select stuff out separately */ +#define HAVE_SELECT_H + +/* assorted others */ +#define HAVE_PARAM_H /* in sys/ */ +#define HAVE_SYSMACROS_H /* in sys/ */ +#define HAVE_TTYENT_H /* securetty et al */ + +/* ==================== */ + +/* Still maybe have to do something about the following, if it's even + worth it. I just grepped a lot of these out of various code, without + looking them up yet: + +#define HAVE_EINPROGRESS +#define HAVE_F_SETOWN +HAVE_FILIO_H ... fionbio, fiosetown, etc... will need for hairier + select loops. +#define HAVE_SETENV ... now *there's* a hairy one; **environ is portable +#define BIG_ENDIAN/little_endian ... *please* try to avoid this stupidity + and LSBFIRST/MSBFIRST +#define HAVE_GETUSERSHELL ... you could always pull it out of getpwent() +#define HAVE_SETE[UG]ID ... lib or syscall, it varies on diff platforms +#define HAVE_STRCHR ... should actually be handled by string/strings +#define HAVE_PSTAT +#define HAVE_ST_BLKSIZE ... a stat() thing? +#define HAVE_IP_TOS +#define HAVE_STRFTIME ... screw this, we'll just INCLUDE one for lame + old boxes that don't have it [sunos 3.x, early 4.x?] +#define HAVE_VFPRINTF +#define HAVE_SHADOW_PASSWD ... in its multitudinous schemes?? ... how + about sumpin' like #define SHADOW_PASSWD_TYPE ... could get grody. + ... looks like sysv /etc/shadow, getspent() family is common. +#define SIG* ... what a swamp, punt for now; should all be in signal.h +#define HAVE_STRCSPN ... see larry wall's comment in the fwtk regex code +#define ULTRIX_AUTH ... bwahaha. +#define HAVE_YP or NIS or whatever you wanna call it this week +randomness about VARARGS?? +--- later stuff to be considered --- +#define UINT4 ... u-int on alpha/osf, i.e. __alpha/__osf__, ulong elsewhere? + dont name it that, though, it'll conflict with extant .h files like md5 +randomness about machine/endian.h, machine/inline.h -- bsdi, net/2 +randomness about _PATH_WTMP vs WTMP_FILE and where they even live!! +#define HAVE_SYS_ERRLIST ... whether it's in stdio.h or not [bsd 4.4] +--- still more stuff +#define HAVE_SETENV +#define _PATH_UTMP vs UTMP_FILE, a la deslogind?! +#define HAVE_DAEMON +#define HAVE_INETADDR [vixie bind?] +lseek: SEEK_SET vs L_SET and associated lossage [epi-notes, old 386Mach] +bsdi: ioctl_compat.h ? +--- takin' some ifdefs from CNS krb: +F_GETOWN/F_SETOWN +CRAY: long = 8 bytes, etc [class with alpha?] +CGETENT +SIGINFO +SIGTSTP SIGTTOU SIGWINCH +SPX? +SYSV_TERMIO -- covered elsewhere, I hope +TIOCEXT TIOCFLUSH TIOC[GS]WINSIZ +NEWINIT: something about init cleaning up dead login processes [telnet?] +PARENT_DOES_UTMP, too [telnet] +VDISCARD +VEOL/VEOL2/VLNEXT VREPRINT -- termios stuff?, and related... +STREAMSPTY/STREAMSPTYEM +AF_INET/AF_UNSPEC, PF_* +ECHOCTL/ECHOKE +F_ULOCK [?!] +setpgrp/getpgrp() ONEARG business.. +HAVE_ALLOCA +HAVE_GETUTENT +HAVE_SYS_SELECT_H [irix!] +HAVE_DIRENT [old 386mach has *direct.h*!] +HAVE_SIGSET +HAVE_VFORK_H and HAVE_VFORK +HAVE_VHANGUP +HAVE_VSPRINTF +HAVE_IPTOS_* +HAVE_STRCASECMP, STRNCASECMP +HAVE_SYS_FCNTL_H +HAVE_SYS_TIME_H +HAVE_UTIMES +NOTTYENT [?] +HAVE_FCHMOD +HAVE_GETUSERSHELL +HAVE_SIGCONTEXT [stack hair, very machine-specific] +YYLINENO? +POSIX_SIGNALS +POSIX_TERMIOS +SETPROCTITLE -- breaks some places, like fbsd sendmail +SIG* -- actual signal names? some are missing +SIOCGIFCONF +SO_BROADCAST +SHMEM [krb tickets] +VARARGS, or HAVE_VARARGS +CBAUD +... and B300, B9600, etc etc +HAVE_BZERO vs memset/memcpy +HAVE_SETVBUF +HAVE_STRDUP +HAVE_GETENV +HAVE_STRSAVE +HAVE_STBLKSIZE [stat?] +HAVE_STREAM_H -- in sys/, ref sendmail 8.7 for IP_SRCROUTE +FCHMOD +INITGROUPS -- most machines seem to *have* +SETREUID +SNPRINTF +SETPGRP semantics bsd vs. sys5 style + +There's also the issue about WHERE various .h files live, sys/ or otherwise. +There's a BIG swamp lurking where network code of any sort lives. +*/ + +/* ======================== */ +/* System-specific sections */ +/* ======================== */ + +/* By turning OFF various bits of the above, you can customize for + a given platform. Yes, we're ignoring the stock compiler predefines + and using our own plugged in via the Makefile. */ + +/* DOS boxes, with MSC; you may need to adapt to a different compiler. */ +/* looks like later ones *do* have dirent.h, for example */ +#ifdef MSDOS +#undef HAVE_FLOCK +#undef HAVE_RANDOM +#undef HAVE_LSTAT +#undef HAVE_TERMIOS +#undef UTMPX +#undef HAVE_SYSINFO +#undef HAVE_UNISTD_H +#undef HAVE_DIRENT_H /* unless you have the k00l little wrapper from L5!! */ +#undef HAVE_STRINGS_H +#undef HAVE_LASTLOG_H +#undef HAVE_PATHS_H +#undef HAVE_PARAM_H +#undef HAVE_SYSMACROS_H +#undef HAVE_SELECT_H +#undef HAVE_TTYENT_H +#endif /* MSDOS */ + +/* buglix 4.x; dunno about 3.x on down. should be bsd4.2 */ +#ifdef ULTRIX +#undef UTMPX +#undef HAVE_PATHS_H +#undef HAVE_SYSMACROS_H +#undef HAVE_SELECT_H +#endif /* buglix */ + +/* some of this might still be broken on older sunoses */ +#ifdef SUNOS +#undef VOID_MALLOC +#undef UTMPX +#undef HAVE_PATHS_H +#undef HAVE_SELECT_H +#endif /* sunos */ + +/* "contact your vendor for a fix" */ +#ifdef SOLARIS +/* has UTMPX */ +#undef HAVE_RANDOM +#undef HAVE_SETPRIORITY +#undef HAVE_STRINGS_H /* this is genuinely the case, go figure */ +#undef HAVE_PATHS_H +#undef HAVE_SELECT_H +#undef HAVE_TTYENT_H +#endif /* SOLARIS */ + +/* whatever aix variant MIT had at the time; 3.2.x?? */ +#ifdef AIX +#undef UTMPX +#undef HAVE_LASTLOG_H +#define HAVE_LOGIN_H /* "special", in the educational sense */ +#endif /* aix */ + +/* linux, which is trying as desperately as the gnu folks can to be + POSIXLY_CORRECT. I think I'm gonna hurl... */ +#ifdef LINUX +#undef UTMPX +#undef HAVE_SYSINFO +#undef HAVE_SELECT_H +#undef HAVE_TTYENT_H +#endif /* linux */ + +/* irix 5.x; may not be correct for earlier ones */ +#ifdef IRIX +/* wow, does irix really have everything?! */ +#endif /* irix */ + +/* osf on alphas */ +#ifdef OSF +#undef UTMPX +#undef HAVE_SELECT_H +#endif /* osf */ + +/* they's some FUCKED UP paths in this one! */ +#ifdef FREEBSD +#undef UTMPX +#undef HAVE_SYSINFO +#undef HAVE_LASTLOG_H +#undef HAVE_SYSMACROS_H +#undef HAVE_SELECT_H /* actually a lie, but only for kernel */ +#endif /* freebsd */ + +/* Originally from the sidewinder site, of all places, but subsequently + checked further under a more normal bsdi 2.0 */ +#ifdef BSDI +#undef UTMPX +#undef HAVE_LASTLOG_H +#undef HAVE_SYSMACROS_H +/* and their malloc.h was in sys/ ?! */ +#undef HAVE_SELECT_H +#endif /* bsdi */ + +/* netbsd/44lite, jives with amiga-netbsd from cactus */ +#ifdef NETBSD +#undef UTMPX +#undef HAVE_SYSINFO +#undef HAVE_LASTLOG_H +#undef HAVE_SELECT_H +#endif /* netbsd */ + +/* Hpux 9.0x, from BBN and various patches sent in */ +#ifdef HPUX +#undef HAVE_RANDOM /* but *does* have ?rand48 -- need to consider.. */ +#undef HAVE_UTMPX +#undef HAVE_LASTLOG_H /* has utmp/wtmp/btmp nonsense, and pututline() */ +#undef HAVE_PATHS_H +#undef HAVE_SELECT_H +#undef HAVE_TTYENT_H +#endif /* hockeypux */ + +/* Unixware [a loose definition of "unix", to be sure], 1.1.2 [at least] + from Brian Clapper. He wasn't sure about 2.0... */ +#ifdef UNIXWARE +/* has UTMPX */ +#undef HAVE_SETPRIORITY +/* NOTE: UnixWare does provide the BSD stuff, in "/usr/ucbinclude" (headers) + and "/usr/ucblib" (libraries). However, I've run into problems linking + stuff out of that version of the C library, when objects are also coming + out of the "regular" C library. My advice: Avoid the BSD compatibility + stuff wherever possible. Brian Clapper */ +#undef HAVE_STRINGS_H +#undef HAVE_PATHS_H +#undef HAVE_TTYENT_H +#endif /* UNIXWARE */ + +/* A/UX 3.1.x from darieb at sandia.gov */ +#ifdef AUX +#undef HAVE_RANDOM +#undef HAVE_SELECT_H /* xxx: untested */ +#endif /* a/ux */ + +/* NeXTSTEP 3.2 motorola mudge at l0pht.com xxx should also work with + white hardware and Sparc/HPPA. Should work with 3.3 too as it's + 4.3 / 4.4 bsd wrapped around mach */ +#ifdef NEXT +#undef UTMPX +#undef HAVE_SELECT_X +#endif /* NeXTSTEP 3.2 motorola */ + +/* Make some "generic" assumptions if all else fails */ +#ifdef GENERIC +#undef HAVE_FLOCK +#if defined(SYSV) && (SYSV < 4) /* TW leftover: old SV doesnt have symlinks */ +#undef HAVE_LSTAT +#endif /* old SYSV */ +#undef HAVE_TERMIOS +#undef UTMPX +#undef HAVE_PATHS_H +#undef HAVE_SELECT_H +#endif /* generic */ + +/* ================ */ +#endif /* GENERIC_H */ + Added: haiku/trunk/src/bin/network/nc/netcat.c =================================================================== --- haiku/trunk/src/bin/network/nc/netcat.c 2007-04-09 22:50:55 UTC (rev 20627) +++ haiku/trunk/src/bin/network/nc/netcat.c 2007-04-09 22:51:08 UTC (rev 20628) @@ -0,0 +1,1667 @@ +/* Netcat 1.10 RELEASE 960320 + + A damn useful little "backend" utility begun 950915 or thereabouts, + as *Hobbit*'s first real stab at some sockets programming. Something that + should have and indeed may have existed ten years ago, but never became a + standard Unix utility. IMHO, "nc" could take its place right next to cat, + cp, rm, mv, dd, ls, and all those other cryptic and Unix-like things. + + Read the README for the whole story, doc, applications, etc. + + Layout: + conditional includes: + includes: + handy defines: + globals: + malloced globals: + cmd-flag globals: + support routines: + readwrite select loop: + main: + + bluesky: + parse ranges of IP address as well as ports, perhaps + RAW mode! + backend progs to grab a pty and look like a real telnetd?! + backend progs to do various encryption modes??!?! +*/ + +#include "generic.h" /* same as with L5, skey, etc */ + +/* conditional includes -- a very messy section which you may have to dink + for your own architecture [and please send diffs...]: */ +/* #undef _POSIX_SOURCE */ /* might need this for something? */ +/* #define HAVE_BIND */ /* ASSUMPTION -- seems to work everywhere! */ +#define HAVE_HELP /* undefine if you dont want the help text */ +/* #define ANAL */ /* if you want case-sensitive DNS matching */ + +#ifdef HAVE_STDLIB_H +#include +#else +#include +#endif +#ifdef HAVE_SELECT_H /* random SV variants need this */ +#include +#endif + +/* have to do this *before* including types.h. xxx: Linux still has it wrong */ +#ifdef FD_SETSIZE /* should be in types.h, butcha never know. */ +#undef FD_SETSIZE /* if we ever need more than 16 active */ +#endif /* fd's, something is horribly wrong! */ +#define FD_SETSIZE 16 /* <-- this'll give us a long anyways, wtf */ +#include /* *now* do it. Sigh, this is broken */ + +#ifdef HAVE_RANDOM /* aficionados of ?rand48() should realize */ +#define SRAND srandom /* that this doesn't need *strong* random */ +#define RAND random /* numbers just to mix up port numbers!! */ +#else +#define SRAND srand +#define RAND rand +#endif /* HAVE_RANDOM */ + +/* includes: */ +#include /* timeval, time_t */ +#include /* jmp_buf et al */ +#include /* basics, SO_ and AF_ defs, sockaddr, ... */ +#include /* sockaddr_in, htons, in_addr */ +#include /* IPOPT_LSRR, header stuff */ +#include /* hostent, gethostby*, getservby* */ +#include /* inet_ntoa */ +#include +#include /* strcpy, strchr, yadda yadda */ +#include +#include +#include /* O_WRONLY et al */ + +/* handy stuff: */ +#define SA struct sockaddr /* socket overgeneralization braindeath */ +#define SAI struct sockaddr_in /* ... whoever came up with this model */ +#define IA struct in_addr /* ... should be taken out and shot, */ + /* ... not that TLI is any better. sigh.. */ +#define SLEAZE_PORT 31337 /* for UDP-scan RTT trick, change if ya want */ +#define USHORT unsigned short /* use these for options an' stuff */ +#define BIGSIZ 8192 /* big buffers */ + +#ifndef INADDR_NONE +#define INADDR_NONE 0xffffffff +#endif +#ifdef MAXHOSTNAMELEN +#undef MAXHOSTNAMELEN /* might be too small on aix, so fix it */ +#endif +#define MAXHOSTNAMELEN 256 + +struct host_poop { + char name[MAXHOSTNAMELEN]; /* dns name */ + char addrs[8][24]; /* ascii-format IP addresses */ + struct in_addr iaddrs[8]; /* real addresses: in_addr.s_addr: ulong */ +}; +#define HINF struct host_poop + +struct port_poop { + char name [64]; /* name in /etc/services */ + char anum [8]; /* ascii-format number */ + USHORT num; /* real host-order number */ +}; +#define PINF struct port_poop + +/* globals: */ +jmp_buf jbuf; /* timer crud */ +int jval = 0; /* timer crud */ +int netfd = -1; +int ofd = 0; /* hexdump output fd */ +static char unknown[] = "(UNKNOWN)"; +static char p_tcp[] = "tcp"; /* for getservby* */ +static char p_udp[] = "udp"; +#ifdef HAVE_BIND +extern int h_errno; +/* stolen almost wholesale from bsd herror.c */ +static char * h_errs[] = { + "Error 0", /* but we *don't* use this */ + "Unknown host", /* 1 HOST_NOT_FOUND */ + "Host name lookup failure", /* 2 TRY_AGAIN */ + "Unknown server error", /* 3 NO_RECOVERY */ + "No address associated with name", /* 4 NO_ADDRESS */ +}; +#else +int h_errno; /* just so we *do* have it available */ +#endif /* HAVE_BIND */ +int gatesidx = 0; /* LSRR hop count */ +int gatesptr = 4; /* initial LSRR pointer, settable */ +USHORT Single = 1; /* zero if scanning */ +unsigned int insaved = 0; /* stdin-buffer size for multi-mode */ +unsigned int wrote_out = 0; /* total stdout bytes */ +unsigned int wrote_net = 0; /* total net bytes */ +static char wrote_txt[] = " sent %d, rcvd %d"; +static char hexnibs[20] = "0123456789abcdef "; + +/* will malloc up the following globals: */ +struct timeval * timer1 = NULL; +struct timeval * timer2 = NULL; +SAI * lclend = NULL; /* sockaddr_in structs */ +SAI * remend = NULL; +HINF ** gates = NULL; /* LSRR hop hostpoop */ +char * optbuf = NULL; /* LSRR or sockopts */ +char * bigbuf_in; /* data buffers */ +char * bigbuf_net; +fd_set * ding1; /* for select loop */ +fd_set * ding2; +PINF * portpoop = NULL; /* for getportpoop / getservby* */ +unsigned char * stage = NULL; /* hexdump line buffer */ + +/* global cmd flags: */ +USHORT o_alla = 0; +unsigned int o_interval = 0; +USHORT o_listen = 0; +USHORT o_nflag = 0; +USHORT o_wfile = 0; +USHORT o_random = 0; +USHORT o_udpmode = 0; +USHORT o_verbose = 0; +unsigned int o_wait = 0; +USHORT o_zero = 0; +/* o_tn in optional section */ + +/* Debug macro: squirt whatever message and sleep a bit so we can see it go + by. need to call like Debug ((stuff)) [with no ; ] so macro args match! + Beware: writes to stdOUT... */ +#ifdef DEBUG +#define Debug(x) printf x; printf ("\n"); fflush (stdout); sleep (1); +#else +#define Debug(x) /* nil... */ +#endif + + +/* support routines -- the bulk of this thing. Placed in such an order that + we don't have to forward-declare anything: */ + +/* holler : + fake varargs -- need to do this way because we wind up calling through + more levels of indirection than vanilla varargs can handle, and not all + machines have vfprintf/vsyslog/whatever! 6 params oughta be enough. */ +void holler (str, p1, p2, p3, p4, p5, p6) + char * str; + char * p1, * p2, * p3, * p4, * p5, * p6; +{ + if (o_verbose) { + fprintf (stderr, str, p1, p2, p3, p4, p5, p6); +#ifdef HAVE_BIND + if (h_errno) { /* if host-lookup variety of error ... */ + if (h_errno > 4) /* oh no you don't, either */ + fprintf (stderr, "preposterous h_errno: %d", h_errno); + else + fprintf (stderr, h_errs[h_errno]); /* handle it here */ + h_errno = 0; /* and reset for next call */ + } +#endif + if (errno) { /* this gives funny-looking messages, but */ + perror (" "); /* it's more portable than sys_errlist[]... */ + } else /* xxx: do something better? */ + fprintf (stderr, "\n"); + fflush (stderr); + } +} /* holler */ + +/* bail : + error-exit handler, callable from anywhere */ +void bail (str, p1, p2, p3, p4, p5, p6) + char * str; + char * p1, * p2, * p3, * p4, * p5, * p6; +{ + o_verbose = 1; + holler (str, p1, p2, p3, p4, p5, p6); + close (netfd); + sleep (1); + exit (1); +} /* bail */ + +/* catch : + no-brainer interrupt handler */ +void catch () +{ + errno = 0; + if (o_verbose > 1) /* normally we don't care */ + bail (wrote_txt, wrote_net, wrote_out); + bail (" punt!"); +} + +/* timeout and other signal handling cruft */ +void tmtravel () +{ + signal (SIGALRM, SIG_IGN); + alarm (0); + if (jval == 0) + bail ("spurious timer interrupt!"); + longjmp (jbuf, jval); +} + +/* arm : + set the timer. Zero secs arg means unarm */ +void arm (num, secs) + unsigned int num; + unsigned int secs; +{ + if (secs == 0) { /* reset */ + signal (SIGALRM, SIG_IGN); + alarm (0); + jval = 0; + } else { /* set */ + signal (SIGALRM, tmtravel); + alarm (secs); + jval = num; + } /* if secs */ +} /* arm */ + +/* Hmalloc : + malloc up what I want, rounded up to *4, and pre-zeroed. Either succeeds + or bails out on its own, so that callers don't have to worry about it. */ +char * Hmalloc (size) + unsigned int size; +{ + unsigned int s = (size + 4) & 0xfffffffc; /* 4GB?! */ + char * p = malloc (s); + if (p != NULL) + memset (p, 0, s); + else + bail ("Hmalloc %d failed", s); + return (p); +} /* Hmalloc */ + +/* findline : + find the next newline in a buffer; return inclusive size of that "line", + or the entire buffer size, so the caller knows how much to then write(). + Not distinguishing \n vs \r\n for the nonce; it just works as is... */ +unsigned int findline (buf, siz) + char * buf; + unsigned int siz; +{ + register char * p; + register int x; + if (! buf) /* various sanity checks... */ + return (0); + if (siz > BIGSIZ) + return (0); + x = siz; + for (p = buf; x > 0; x--) { + if (*p == '\n') { + x = (int) (p - buf); + x++; /* 'sokay if it points just past the end! */ +Debug (("findline returning %d", x)) + return (x); + } + p++; + } /* for */ +Debug (("findline returning whole thing: %d", siz)) + return (siz); +} /* findline */ + +/* comparehosts : + cross-check the host_poop we have so far against new gethostby*() info, + and holler about mismatches. Perhaps gratuitous, but it can't hurt to + point out when someone's DNS is fukt. Returns 1 if mismatch, in case + someone else wants to do something about it. */ +int comparehosts (poop, hp) + HINF * poop; + struct hostent * hp; +{ + errno = 0; + h_errno = 0; +/* The DNS spec is officially case-insensitive, but for those times when you + *really* wanna see any and all discrepancies, by all means define this. */ +#ifdef ANAL + if (strcmp (poop->name, hp->h_name) != 0) { /* case-sensitive */ +#else + if (strcasecmp (poop->name, hp->h_name) != 0) { /* normal */ +#endif + holler ("DNS fwd/rev mismatch: %s != %s", poop->name, hp->h_name); + return (1); + } + return (0); +/* ... do we need to do anything over and above that?? */ +} /* comparehosts */ + +/* gethostpoop : + resolve a host 8 ways from sunday; return a new host_poop struct with its + info. The argument can be a name or [ascii] IP address; it will try its + damndest to deal with it. "numeric" governs whether we do any DNS at all, + and we also check o_verbose for what's appropriate work to do. */ +HINF * gethostpoop (name, numeric) + char * name; + USHORT numeric; +{ + struct hostent * hostent; + struct in_addr iaddr; + register HINF * poop = NULL; + register int x; + +/* I really want to strangle the twit who dreamed up all these sockaddr and + hostent abstractions, and then forced them all to be incompatible with + each other so you *HAVE* to do all this ridiculous casting back and forth. + If that wasn't bad enough, all the doc insists on referring to local ports + and addresses as "names", which makes NO sense down at the bare metal. + + What an absolutely horrid paradigm, and to think of all the people who + have been wasting significant amounts of time fighting with this stupid + deliberate obfuscation over the last 10 years... then again, I like + languages wherein a pointer is a pointer, what you put there is your own + business, the compiler stays out of your face, and sheep are nervous. + Maybe that's why my C code reads like assembler half the time... */ + +/* If we want to see all the DNS stuff, do the following hair -- + if inet_addr, do reverse and forward with any warnings; otherwise try + to do forward and reverse with any warnings. In other words, as long + as we're here, do a complete DNS check on these clowns. Yes, it slows + things down a bit for a first run, but once it's cached, who cares? */ + + errno = 0; + h_errno = 0; + if (name) + poop = (HINF *) Hmalloc (sizeof (HINF)); + if (! poop) + bail ("gethostpoop fuxored"); + strcpy (poop->name, unknown); /* preload it */ +/* see wzv:workarounds.c for dg/ux return-a-struct inet_addr lossage */ + iaddr.s_addr = inet_addr (name); + + if (iaddr.s_addr == INADDR_NONE) { /* here's the great split: names... */ + if (numeric) + bail ("Can't parse %s as an IP address", name); + hostent = gethostbyname (name); + if (! hostent) +/* failure to look up a name is fatal, since we can't do anything with it */ + bail ("%s: forward host lookup failed: ", name); + strncpy (poop->name, hostent->h_name, MAXHOSTNAMELEN - 2); + for (x = 0; hostent->h_addr_list[x] && (x < 8); x++) { + memcpy (&poop->iaddrs[x], hostent->h_addr_list[x], sizeof (IA)); + strncpy (poop->addrs[x], inet_ntoa (poop->iaddrs[x]), + sizeof (poop->addrs[0])); + } /* for x -> addrs, part A */ + if (! o_verbose) /* if we didn't want to see the */ + return (poop); /* inverse stuff, we're done. */ +/* do inverse lookups in separate loop based on our collected forward addrs, + since gethostby* tends to crap into the same buffer over and over */ + for (x = 0; poop->iaddrs[x].s_addr && (x < 8); x++) { + hostent = gethostbyaddr ((char *)&poop->iaddrs[x], + sizeof (IA), AF_INET); + if ((! hostent) || (! hostent-> h_name)) + holler ("Warning: inverse host lookup failed for %s: ", + poop->addrs[x]); + else + (void) comparehosts (poop, hostent); + } /* for x -> addrs, part B */ + + } else { /* not INADDR_NONE: numeric addresses... */ + memcpy (poop->iaddrs, &iaddr, sizeof (IA)); + strncpy (poop->addrs[0], inet_ntoa (iaddr), sizeof (poop->addrs)); + if (numeric) /* if numeric-only, we're done */ + return (poop); + if (! o_verbose) /* likewise if we don't want */ + return (poop); /* the full DNS hair */ + hostent = gethostbyaddr ((char *) &iaddr, sizeof (IA), AF_INET); +/* numeric or not, failure to look up a PTR is *not* considered fatal */ + if (! hostent) + holler ("%s: inverse host lookup failed: ", name); + else { + strncpy (poop->name, hostent->h_name, MAXHOSTNAMELEN - 2); + hostent = gethostbyname (poop->name); + if ((! hostent) || (! hostent->h_addr_list[0])) + holler ("Warning: forward host lookup failed for %s: ", + poop->name); + else + (void) comparehosts (poop, hostent); + } /* if hostent */ + } /* INADDR_NONE Great Split */ + +/* whatever-all went down previously, we should now have a host_poop struct + with at least one IP address in it. */ + h_errno = 0; + return (poop); +} /* gethostpoop */ + +/* getportpoop : + Same general idea as gethostpoop -- look up a port in /etc/services, fill + in global port_poop, but return the actual port *number*. Pass ONE of: + pstring to resolve stuff like "23" or "exec"; + pnum to reverse-resolve something that's already a number. + If o_nflag is on, fill in what we can but skip the getservby??? stuff. + Might as well have consistent behavior here, and it *is* faster. */ +USHORT getportpoop (pstring, pnum) + char * pstring; + unsigned int pnum; +{ + struct servent * servent; + register int x; + register int y; + char * whichp = p_tcp; + if (o_udpmode) + whichp = p_udp; + portpoop->name[0] = '?'; /* fast preload */ + portpoop->name[1] = '\0'; + +/* case 1: reverse-lookup of a number; placed first since this case is much + more frequent if we're scanning */ + if (pnum) { + if (pstring) /* one or the other, pleeze */ + return (0); + x = pnum; + if (o_nflag) /* go faster, skip getservbyblah */ + goto gp_finish; + y = htons (x); /* gotta do this -- see Fig.1 below */ + servent = getservbyport (y, whichp); + if (servent) { + y = ntohs (servent->s_port); + if (x != y) /* "never happen" */ + holler ("Warning: port-bynum mismatch, %d != %d", x, y); + strncpy (portpoop->name, servent->s_name, sizeof (portpoop->name)); + } /* if servent */ + goto gp_finish; + } /* if pnum */ + +/* case 2: resolve a string, but we still give preference to numbers instead + of trying to resolve conflicts. None of the entries in *my* extensive + /etc/services begins with a digit, so this should "always work" unless + you're at 3com and have some company-internal services defined... */ + if (pstring) { + if (pnum) /* one or the other, pleeze */ + return (0); + x = atoi (pstring); + if (x) + return (getportpoop (NULL, x)); /* recurse for numeric-string-arg */ + if (o_nflag) /* can't use names! */ + return (0); + servent = getservbyname (pstring, whichp); + if (servent) { + strncpy (portpoop->name, servent->s_name, sizeof (portpoop->name)); + x = ntohs (servent->s_port); + goto gp_finish; + } /* if servent */ + } /* if pstring */ + + return (0); /* catches any problems so far */ + +/* Obligatory netdb.h-inspired rant: servent.s_port is supposed to be an int. + Despite this, we still have to treat it as a short when copying it around. + Not only that, but we have to convert it *back* into net order for + getservbyport to work. Manpages generally aren't clear on all this, but + there are plenty of examples in which it is just quietly done. More BSD + lossage... since everything getserv* ever deals with is local to our own + host, why bother with all this network-order/host-order crap at all?! + That should be saved for when we want to actually plug the port[s] into + some real network calls -- and guess what, we have to *re*-convert at that + point as well. Fuckheads. */ + +gp_finish: +/* Fall here whether or not we have a valid servent at this point, with + x containing our [host-order and therefore useful, dammit] port number */ + sprintf (portpoop->anum, "%d", x); /* always load any numeric specs! */ + portpoop->num = (x & 0xffff); /* ushort, remember... */ + return (portpoop->num); +} /* getportpoop */ + +/* nextport : + Come up with the next port to try, be it random or whatever. "block" is + a ptr to randports array, whose bytes [so far] carry these meanings: + 0 ignore + 1 to be tested + 2 tested [which is set as we find them here] + returns a USHORT random port, or 0 if all the t-b-t ones are used up. */ +USHORT nextport (block) + char * block; +{ + register unsigned int x; + register unsigned int y; + + y = 70000; /* high safety count for rnd-tries */ + while (y > 0) { + x = (RAND() & 0xffff); + if (block[x] == 1) { /* try to find a not-done one... */ + block[x] = 2; + break; + } + x = 0; /* bummer. */ + y--; + } /* while y */ + if (x) + return (x); + + y = 65535; /* no random one, try linear downsearch */ + while (y > 0) { /* if they're all used, we *must* be sure! */ + if (block[y] == 1) { + block[y] = 2; + break; + } + y--; + } /* while y */ + if (y) + return (y); /* at least one left */ + + return (0); /* no more left! */ +} /* nextport */ + +/* loadports : + set "to be tested" indications in BLOCK, from LO to HI. Almost too small + to be a separate routine, but makes main() a little cleaner... */ +void loadports (block, lo, hi) + char * block; + USHORT lo; + USHORT hi; +{ + USHORT x; + + if (! block) + bail ("loadports: no block?!"); + if ((! lo) || (! hi)) + bail ("loadports: bogus values %d, %d", lo, hi); + x = hi; + while (lo <= x) { [... truncated: 1113 lines follow ...] From hugosantos at mail.berlios.de Tue Apr 10 00:51:55 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Tue, 10 Apr 2007 00:51:55 +0200 Subject: [Haiku-commits] r20629 - in haiku/trunk/src/add-ons/kernel/network/protocols: ipv4 tcp Message-ID: <200704092251.l39Mpt20031959@sheep.berlios.de> Author: hugosantos Date: 2007-04-10 00:51:28 +0200 (Tue, 10 Apr 2007) New Revision: 20629 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20629&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp haiku/trunk/src/add-ons/kernel/network/protocols/tcp/EndpointManager.cpp haiku/trunk/src/add-ons/kernel/network/protocols/tcp/EndpointManager.h haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h Log: A couple more TCP fixes. - ipv4_bind() was broken when binding to addresses not INADDR_ANY, as it wasn't copying the address to the socket, fixed. - fixed a small issue in TCP's BindToEphemeral where the correct address might not have been bound to the socket. - some assorted TCP wait lists fixes. - fixed TCP's Connect() over the loopback interface, we might already be ESTABLISHED after _SendQueue() returns. - fixed the amount of time we wait in TCP's Accept(). Modified: haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp 2007-04-09 22:51:08 UTC (rev 20628) +++ haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp 2007-04-09 22:51:28 UTC (rev 20629) @@ -872,6 +872,7 @@ // only INADDR_ANY and addresses of local interfaces are accepted: if (((sockaddr_in *)address)->sin_addr.s_addr == INADDR_ANY || sDatalinkModule->is_local_address(sDomain, address, NULL, NULL)) { + memcpy(&protocol->socket->address, address, sizeof(struct sockaddr_in)); protocol->socket->address.ss_len = sizeof(struct sockaddr_in); // explicitly set length, as our callers can't be trusted to // always provide the correct length! Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/EndpointManager.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/EndpointManager.cpp 2007-04-09 22:51:08 UTC (rev 20628) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/EndpointManager.cpp 2007-04-09 22:51:28 UTC (rev 20629) @@ -212,10 +212,13 @@ status_t -EndpointManager::Bind(TCPEndpoint *endpoint, sockaddr *address) +EndpointManager::Bind(TCPEndpoint *endpoint) { - TRACE(("EndpointManager::Bind(%p, %s)\n", endpoint, AddressString(gDomain, address, true).Data())); + sockaddr *address = (sockaddr *)&endpoint->socket->address; + TRACE(("EndpointManager::Bind(%p, %s)\n", endpoint, + AddressString(gDomain, address, true).Data())); + if (gAddressModule->is_empty_address(address, true)) return B_BAD_VALUE; @@ -259,8 +262,6 @@ } else hash_insert(fEndpointHash, endpoint); - gAddressModule->set_to((sockaddr *)&endpoint->socket->address, address); - endpoint->fEndpointNextWithSamePort = NULL; hash_insert(fConnectionHash, endpoint); @@ -269,7 +270,7 @@ status_t -EndpointManager::BindToEphemeral(TCPEndpoint *endpoint, sockaddr *address) +EndpointManager::BindToEphemeral(TCPEndpoint *endpoint) { TRACE(("EndpointManager::BindToEphemeral(%p)\n", endpoint)); @@ -292,7 +293,6 @@ TCPEndpoint *other = _LookupEndpoint(port); if (other == NULL) { // found a port - gAddressModule->set_to((sockaddr *)&endpoint->socket->address, address); gAddressModule->set_port((sockaddr *)&endpoint->socket->address, port); TRACE((" EndpointManager::BindToEphemeral(%p) -> %s\n", endpoint, AddressString(gDomain, (sockaddr *)&endpoint->socket->address, true).Data())); @@ -319,7 +319,8 @@ RecursiveLocker locker(&fLock); - TCPEndpoint *other = _LookupEndpoint(gAddressModule->get_port((sockaddr *)&endpoint->socket->address)); + TCPEndpoint *other = _LookupEndpoint(gAddressModule->get_port( + (sockaddr *)&endpoint->socket->address)); if (other != endpoint) { // remove endpoint from the list of endpoints with the same port while (other != NULL && other->fEndpointNextWithSamePort != endpoint) { Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/EndpointManager.h =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/EndpointManager.h 2007-04-09 22:51:08 UTC (rev 20628) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/EndpointManager.h 2007-04-09 22:51:28 UTC (rev 20629) @@ -30,8 +30,8 @@ const sockaddr *peer, const sockaddr *interfaceLocal); TCPEndpoint *FindConnection(sockaddr *local, sockaddr *peer); - status_t Bind(TCPEndpoint *endpoint, sockaddr *address); - status_t BindToEphemeral(TCPEndpoint *endpoint, sockaddr *address); + status_t Bind(TCPEndpoint *endpoint); + status_t BindToEphemeral(TCPEndpoint *endpoint); status_t Unbind(TCPEndpoint *endpoint); private: Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-09 22:51:08 UTC (rev 20628) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-09 22:51:28 UTC (rev 20629) @@ -32,8 +32,12 @@ #include +// References: +// - RFC 793 - Transmission Control Protocol +// - RFC 813 - Window and Acknowledgement Strategy in TCP +// // Things this implementation currently doesn't implement: -// TCP, RFC 793 +// // TCP Slow Start, Congestion Avoidance, Fast Retransmit, and Fast Recovery, RFC 2001, RFC 2581, RFC 3042 // NewReno Modification to TCP's Fast Recovery, RFC 2582 // Explicit Congestion Notification (ECN), RFC 3168 @@ -62,29 +66,69 @@ }; -static status_t -wait_on_locker(RecursiveLocker &locker, sem_id sem, bigtime_t timeout) +static inline bigtime_t +absolute_timeout(bigtime_t timeout) { + if (timeout == 0 || timeout == B_INFINITE_TIMEOUT) + return timeout; + + return timeout + system_time(); +} + + +WaitList::WaitList(const char *name) + : fWaiting(0) +{ + fSem = create_sem(0, name); +} + + +WaitList::~WaitList() +{ + delete_sem(fSem); +} + + +status_t +WaitList::InitCheck() const +{ + return fSem; +} + + +status_t +WaitList::Wait(RecursiveLocker &locker, bigtime_t timeout) +{ + // this function is called with `locker' held. + fWaiting++; locker.Unlock(); - status_t status = acquire_sem_etc(sem, 1, B_ABSOLUTE_TIMEOUT | + status_t status = acquire_sem_etc(fSem, 1, B_ABSOLUTE_TIMEOUT | B_CAN_INTERRUPT, timeout); locker.Lock(); + if (status == B_OK) + Signal(); return status; } -static inline bigtime_t -absolute_timeout(bigtime_t timeout) +void +WaitList::Signal() { - if (timeout == 0 || timeout == B_INFINITE_TIMEOUT) - return timeout; + // the same locker used with Wait() must be held + // when calling this function. - return timeout + system_time(); + if (fWaiting == 0) + return; + + fWaiting--; + release_sem_etc(fSem, 1, B_DO_NOT_RESCHEDULE); } TCPEndpoint::TCPEndpoint(net_socket *socket) : + fReceiveList("tcp receive"), + fSendList("tcp send"), fOptions(0), fSendWindowShift(0), fReceiveWindowShift(0), @@ -111,10 +155,6 @@ recursive_lock_init(&fLock, "tcp lock"); // TODO: to be replaced with a real locking strategy! - //benaphore_init(&fReceiveLock, "tcp receive"); - //benaphore_init(&fSendLock, "tcp send"); - fSendLock = create_sem(0, "tcp send"); - fReceiveLock = create_sem(0, "tcp receive"); gStackModule->init_timer(&fPersistTimer, TCPEndpoint::_PersistTimer, this); gStackModule->init_timer(&fRetransmitTimer, TCPEndpoint::_RetransmitTimer, this); @@ -136,10 +176,6 @@ gEndpointManager->Unbind(this); recursive_lock_destroy(&fLock); - //benaphore_destroy(&fReceiveLock); - //benaphore_destroy(&fSendLock); - delete_sem(fReceiveLock); - delete_sem(fSendLock); } @@ -148,11 +184,13 @@ { if (fLock.sem < B_OK) return fLock.sem; - if (fReceiveLock < B_OK) - return fReceiveLock; - if (fSendLock < B_OK) - return fSendLock; + if (fReceiveList.InitCheck() < B_OK) + return fReceiveList.InitCheck(); + + if (fSendList.InitCheck() < B_OK) + return fSendList.InitCheck(); + return B_OK; } @@ -195,8 +233,8 @@ bigtime_t maximum = absolute_timeout(socket->linger * 1000000LL); while (fSendQueue.Used() > 0) { - status = wait_on_locker(lock, fSendLock, maximum); - if (status == B_TIMED_OUT) + status = fSendList.Wait(lock, maximum); + if (status == B_TIMED_OUT || status == B_WOULD_BLOCK) break; else if (status < B_OK) return status; @@ -294,19 +332,23 @@ return status; } + // If we are running over Loopback, after _SendQueued() returns we + // may be in ESTABLISHED already. + if (fState == ESTABLISHED) + return B_OK; + // wait until 3-way handshake is complete (if needed) - bigtime_t timeout = min_c(socket->send.timeout, TCP_CONNECTION_TIMEOUT); if (timeout == 0) { // we're a non-blocking socket return EINPROGRESS; } - locker.Unlock(); + while (status == B_OK && fState != ESTABLISHED) + status = fSendList.Wait(locker, absolute_timeout(timeout)); - status = acquire_sem_etc(fSendLock, 1, B_RELATIVE_TIMEOUT | B_CAN_INTERRUPT, timeout); + TRACE(" Connect(): Connection complete: %s", strerror(status)); - TRACE(" Connect(): Connection complete: %s", strerror(status)); return status; } @@ -316,12 +358,12 @@ { TRACE("Accept()"); - // TODO: test for pending sockets - // TODO: test for non-blocking I/O status_t status; + bigtime_t timeout = absolute_timeout(socket->receive.timeout); + do { - status = acquire_sem_etc(fAcceptSemaphore, 1, B_RELATIVE_TIMEOUT, - socket->receive.timeout); + status = acquire_sem_etc(fAcceptSemaphore, 1, B_ABSOLUTE_TIMEOUT | + B_CAN_INTERRUPT, timeout); if (status < B_OK) return status; @@ -352,10 +394,14 @@ return status; if (gAddressModule->get_port(address) == 0) - status = gEndpointManager->BindToEphemeral(this, address); + status = gEndpointManager->BindToEphemeral(this); else - status = gEndpointManager->Bind(this, address); + status = gEndpointManager->Bind(this); + TRACE(" Bind() bound to %s (status %i)", + AddressString(gDomain, (sockaddr *)&socket->address, true).Data(), + (int)status); + return status; } @@ -450,7 +496,7 @@ chunk = buffer; while (fSendQueue.Free() < chunk->size) { - status_t status = wait_on_locker(lock, fSendLock, timeout); + status_t status = fSendList.Wait(lock, timeout); if (status < B_OK) return status; } @@ -514,7 +560,7 @@ while (fState != ESTABLISHED) { // we need to wait until the connection becomes established - status_t status = wait_on_locker(locker, fSendLock, timeout); + status_t status = fSendList.Wait(locker, timeout); if (status < B_OK) return status; } @@ -550,7 +596,7 @@ if (flags & MSG_DONTWAIT) return B_WOULD_BLOCK; - status_t status = wait_on_locker(locker, fReceiveLock, timeout); + status_t status = fReceiveList.Wait(locker, timeout); if (status < B_OK) { // The Open Group base specification mentions that EINTR should be // returned if the recv() is interrupted before _any data_ is @@ -568,7 +614,7 @@ numBytes, fReceiveQueue.Available()); if (numBytes < fReceiveQueue.Available()) - release_sem_etc(fReceiveLock, 1, B_DO_NOT_RESCHEDULE); + fReceiveList.Signal(); ssize_t receivedBytes = fReceiveQueue.Get(numBytes, (flags & MSG_PEEK) == 0, _buffer); @@ -654,6 +700,9 @@ int32 TCPEndpoint::ListenReceive(tcp_segment_header &segment, net_buffer *buffer) { + TRACE("ListenReceive(): Connection in state %s received packet %p (%lu bytes) with flags 0x%x, seq %lu, ack %lu!", + name_for_state(fState), buffer, buffer->size, segment.flags, segment.sequence, segment.acknowledge); + // Essentially, we accept only TCP_FLAG_SYNCHRONIZE in this state, // but the error behaviour differs if (segment.flags & TCP_FLAG_RESET) @@ -780,7 +829,7 @@ release_sem_etc(fAcceptSemaphore, 1, B_DO_NOT_RESCHEDULE); } - release_sem_etc(fSendLock, 0, B_DO_NOT_RESCHEDULE | B_RELEASE_ALL); + fSendList.Signal(); _NotifyReader(); } else { // simultaneous open @@ -829,7 +878,7 @@ gStackModule->cancel_timer(&fRetransmitTimer); // notify threads waiting on the socket to become writable again - release_sem_etc(fSendLock, 1, B_DO_NOT_RESCHEDULE); + fSendList.Signal(); // TODO: real conditional locking needed! gSocketModule->notify(socket, B_SELECT_WRITE, fSendWindow); @@ -956,7 +1005,7 @@ fState = ESTABLISHED; - release_sem_etc(fSendLock, 0, B_DO_NOT_RESCHEDULE | B_RELEASE_ALL); + fSendList.Signal(); _NotifyReader(); } @@ -1000,7 +1049,6 @@ fSendNext = fSendUnacknowledged; if (segment.acknowledge > fSendQueue.LastSequence() && fState > ESTABLISHED) { - // our TCP_FLAG_FINISH has been acknowledged TRACE("Receive(): FIN has been acknowledged!"); switch (fState) { @@ -1367,9 +1415,7 @@ void TCPEndpoint::_NotifyReader() { - // TODO maintain a waiting receiver count so we know whether - // we should release or not. - release_sem_etc(fReceiveLock, 1, B_DO_NOT_RESCHEDULE); + fReceiveList.Signal(); gSocketModule->notify(socket, B_SELECT_READ, _AvailableData()); } Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h 2007-04-09 22:51:08 UTC (rev 20628) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h 2007-04-09 22:51:28 UTC (rev 20629) @@ -15,6 +15,7 @@ #include #include +#include #include #include @@ -22,6 +23,22 @@ class EndpointManager; +class WaitList { +public: + WaitList(const char *name); + ~WaitList(); + + status_t InitCheck() const; + + status_t Wait(RecursiveLocker &, bigtime_t timeout); + void Signal(); + +private: + sem_id fSem; + int32 fWaiting; +}; + + class TCPEndpoint : public net_protocol { public: TCPEndpoint(net_socket *socket); @@ -81,8 +98,8 @@ TCPEndpoint *fEndpointNextWithSamePort; recursive_lock fLock; - sem_id fReceiveLock; - sem_id fSendLock; + WaitList fReceiveList; + WaitList fSendList; sem_id fAcceptSemaphore; uint8 fOptions; From axeld at pinc-software.de Tue Apr 10 01:47:29 2007 From: axeld at pinc-software.de (Axel =?iso-8859-15?q?D=F6rfler?=) Date: Tue, 10 Apr 2007 01:47:29 +0200 CEST Subject: [Haiku-commits] =?iso-8859-15?q?r20629_-_in_haiku/trunk/src/add-o?= =?iso-8859-15?q?ns/kernel/network/protocols=3A_ipv4_tcp?= In-Reply-To: <200704092251.l39Mpt20031959@sheep.berlios.de> Message-ID: <26462838436-BeMail@zon> hugosantos at mail.berlios.de wrote: > + status_t status = acquire_sem_etc(fSem, 1, B_ABSOLUTE_TIMEOUT | > B_CAN_INTERRUPT, timeout); Another small style correction: the operator always gets to the start of the next line, not to the end of the line. But very nice work, thanks! Bye, Axel. From axeld at mail.berlios.de Tue Apr 10 02:14:36 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Tue, 10 Apr 2007 02:14:36 +0200 Subject: [Haiku-commits] r20630 - haiku/trunk/src/add-ons/translators/raw Message-ID: <200704100014.l3A0EaiX017954@sheep.berlios.de> Author: axeld Date: 2007-04-10 02:14:32 +0200 (Tue, 10 Apr 2007) New Revision: 20630 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20630&view=rev Modified: haiku/trunk/src/add-ons/translators/raw/RAW.cpp haiku/trunk/src/add-ons/translators/raw/RAW.h haiku/trunk/src/add-ons/translators/raw/RAWTranslator.cpp haiku/trunk/src/add-ons/translators/raw/ReadHelper.h Log: Now adds a fake TIFF header to the exported EXIF data so that the used endian of the data is known. Modified: haiku/trunk/src/add-ons/translators/raw/RAW.cpp =================================================================== --- haiku/trunk/src/add-ons/translators/raw/RAW.cpp 2007-04-09 22:51:28 UTC (rev 20629) +++ haiku/trunk/src/add-ons/translators/raw/RAW.cpp 2007-04-10 00:14:32 UTC (rev 20630) @@ -3360,13 +3360,19 @@ status_t -DCRaw::GetEXIFTag(off_t& offset, size_t& length) const +DCRaw::GetEXIFTag(off_t& offset, size_t& length, bool& bigEndian) const { if (fEXIFOffset < 0) return B_ENTRY_NOT_FOUND; offset = fEXIFOffset; length = fEXIFLength; + +#if B_HOST_IS_LENDIAN + bigEndian = fRead.IsSwapping(); +#else + bigEndian = !fRead.IsSwapping(); +#endif return B_OK; } Modified: haiku/trunk/src/add-ons/translators/raw/RAW.h =================================================================== --- haiku/trunk/src/add-ons/translators/raw/RAW.h 2007-04-09 22:51:28 UTC (rev 20629) +++ haiku/trunk/src/add-ons/translators/raw/RAW.h 2007-04-10 00:14:32 UTC (rev 20630) @@ -63,7 +63,8 @@ uint32 CountImages() const; status_t ImageAt(uint32 index, image_data_info& info) const; - status_t GetEXIFTag(off_t& offset, size_t& length) const; + status_t GetEXIFTag(off_t& offset, size_t& length, + bool& bigEndian) const; private: int32 _AllocateImage(); Modified: haiku/trunk/src/add-ons/translators/raw/RAWTranslator.cpp =================================================================== --- haiku/trunk/src/add-ons/translators/raw/RAWTranslator.cpp 2007-04-09 22:51:28 UTC (rev 20629) +++ haiku/trunk/src/add-ons/translators/raw/RAWTranslator.cpp 2007-04-10 00:14:32 UTC (rev 20630) @@ -63,11 +63,11 @@ RAWTranslator::RAWTranslator() - : BaseTranslator("Raw Images", "Raw Image Translator", + : BaseTranslator("RAW Images", "RAW Image Translator", RAW_TRANSLATOR_VERSION, sInputFormats, kNumInputFormats, sOutputFormats, kNumOutputFormats, - "RawTranslator_Settings", + "RAWTranslator_Settings", sDefaultSettings, kNumDefaultSettings, B_TRANSLATOR_BITMAP, RAW_IMAGE_FORMAT) { @@ -192,12 +192,26 @@ // retrieve EXIF data off_t exifOffset; size_t exifLength; - if (settings != NULL && raw.GetEXIFTag(exifOffset, exifLength) == B_OK) { - void* exifBuffer = malloc(exifLength); + bool bigEndian; + if (settings != NULL && raw.GetEXIFTag(exifOffset, exifLength, bigEndian) == B_OK) { + uint8* exifBuffer = (uint8*)malloc(exifLength + 16); if (exifBuffer != NULL) { - if (source->ReadAt(exifOffset, exifBuffer, exifLength) + // add fake TIFF header to EXIF data + struct { + uint16 endian; + uint16 tiff_marker; + uint32 offset; + uint16 null; + } _PACKED header; + header.endian = bigEndian ? 'MM' : 'II'; + header.tiff_marker = 42; + header.offset = 16; + header.null = 0; + memcpy(exifBuffer, &header, sizeof(header)); + + if (source->ReadAt(exifOffset, exifBuffer + 16, exifLength) == (ssize_t)exifLength) - settings->AddData("exif", B_RAW_TYPE, exifBuffer, exifLength); + settings->AddData("exif", B_RAW_TYPE, exifBuffer, exifLength + 16); free(exifBuffer); } Modified: haiku/trunk/src/add-ons/translators/raw/ReadHelper.h =================================================================== --- haiku/trunk/src/add-ons/translators/raw/ReadHelper.h 2007-04-09 22:51:28 UTC (rev 20629) +++ haiku/trunk/src/add-ons/translators/raw/ReadHelper.h 2007-04-10 00:14:32 UTC (rev 20630) @@ -173,16 +173,16 @@ throw fError; } - status_t Status() + status_t Status() const { return fError >= B_OK ? B_OK : fError; }; off_t Seek(off_t offset, int32 mode) { return fStream.Seek(offset, mode); } - off_t Position() + off_t Position() const { return fStream.Position(); } void SetSwap(bool yesNo) { fSwap = yesNo; }; - bool IsSwapping() { return fSwap; }; + bool IsSwapping() const { return fSwap; }; BPositionIO& Stream() { return fStream; } From hugosantos at mail.berlios.de Tue Apr 10 07:29:09 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Tue, 10 Apr 2007 07:29:09 +0200 Subject: [Haiku-commits] r20631 - in haiku/trunk: headers/private/net src/add-ons/kernel/network/protocols/tcp src/add-ons/kernel/network/stack Message-ID: <200704100529.l3A5T9Lm014723@sheep.berlios.de> Author: hugosantos Date: 2007-04-10 07:28:56 +0200 (Tue, 10 Apr 2007) New Revision: 20631 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20631&view=rev Modified: haiku/trunk/headers/private/net/net_socket.h haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp haiku/trunk/src/add-ons/kernel/network/stack/net_socket.cpp Log: Fixed some more TCP issues. - Properly flag sockets using non-blocking connects() when in SYN SENT. - and when in LISTEN, we should use the socket's connection queue size. Modified: haiku/trunk/headers/private/net/net_socket.h =================================================================== --- haiku/trunk/headers/private/net/net_socket.h 2007-04-10 00:14:32 UTC (rev 20630) +++ haiku/trunk/headers/private/net/net_socket.h 2007-04-10 05:28:56 UTC (rev 20631) @@ -65,6 +65,7 @@ status_t (*spawn_pending_socket)(net_socket *parent, net_socket **_socket); void (*delete_socket)(net_socket *socket); status_t (*dequeue_connected)(net_socket *parent, net_socket **_socket); + ssize_t (*count_connected)(net_socket *parent); status_t (*set_max_backlog)(net_socket *socket, uint32 backlog); status_t (*set_connected)(net_socket *socket); Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-10 00:14:32 UTC (rev 20630) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-10 05:28:56 UTC (rev 20631) @@ -52,7 +52,7 @@ // the space after 'this' is important in order for this to work with cpp 2.95 # define TRACE(format, args...) dprintf("TCP:%p:" format "\n", this , ##args) #else -# define TRACE(args...) +# define TRACE(args...) do { } while (0) #endif // Initial estimate for packet round trip time (RTT) @@ -62,6 +62,9 @@ enum { FLAG_OPTION_WINDOW_SHIFT = 0x01, FLAG_OPTION_TIMESTAMP = 0x02, + // TODO: Should FLAG_NO_RECEIVE apply as well to received connections? + // That is, what is excepected from accept() after a shutdown() + // is performed on a listen()ing socket. FLAG_NO_RECEIVE = 0x04, }; @@ -334,13 +337,16 @@ // If we are running over Loopback, after _SendQueued() returns we // may be in ESTABLISHED already. - if (fState == ESTABLISHED) + if (fState == ESTABLISHED) { + TRACE(" Connect() completed after _SendQueued()"); return B_OK; + } // wait until 3-way handshake is complete (if needed) bigtime_t timeout = min_c(socket->send.timeout, TCP_CONNECTION_TIMEOUT); if (timeout == 0) { // we're a non-blocking socket + TRACE(" Connect() delayed, return EINPROGRESS"); return EINPROGRESS; } @@ -368,6 +374,8 @@ return status; status = gSocketModule->dequeue_connected(socket, _acceptedSocket); + if (status == B_OK) + TRACE(" Accept() returning %p", (*_acceptedSocket)->first_protocol); } while (status < B_OK); return status; @@ -533,9 +541,8 @@ ssize_t TCPEndpoint::SendAvailable() { - TRACE("SendAvailable()"); - RecursiveLocker locker(fLock); + TRACE("SendAvailable(): %li", fSendQueue.Free()); return fSendQueue.Free(); } @@ -767,6 +774,8 @@ } } + TRACE(" ListenReceive() created new endpoint %p", endpoint); + // send SYN+ACK status_t status = endpoint->_SendQueued(); @@ -1403,6 +1412,14 @@ ssize_t TCPEndpoint::_AvailableData() const { + // TODO: Refer to the FLAG_NO_RECEIVE comment above regarding + // the application of FLAG_NO_RECEIVE in listen()ing + // sockets. + if (fState == LISTEN) + return gSocketModule->count_connected(socket); + else if (fState == SYNCHRONIZE_SENT) + return 0; + ssize_t availableData = fReceiveQueue.Available(); if (availableData == 0 && !_ShouldReceive()) Modified: haiku/trunk/src/add-ons/kernel/network/stack/net_socket.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/net_socket.cpp 2007-04-10 00:14:32 UTC (rev 20630) +++ haiku/trunk/src/add-ons/kernel/network/stack/net_socket.cpp 2007-04-10 05:28:56 UTC (rev 20631) @@ -372,6 +372,22 @@ } +ssize_t +socket_count_connected(net_socket *_parent) +{ + net_socket_private *parent = (net_socket_private *)_parent; + + BenaphoreLocker _(parent->lock); + + int count = 0; + for (void *it = list_get_first_item(&parent->connected_children); + it != NULL; it = list_get_next_item(&parent->connected_children, it)) + count++; + + return count; +} + + status_t socket_set_max_backlog(net_socket *_socket, uint32 backlog) { @@ -1101,6 +1117,7 @@ socket_spawn_pending, socket_delete, socket_dequeue_connected, + socket_count_connected, socket_set_max_backlog, socket_connected, From axeld at mail.berlios.de Tue Apr 10 12:52:43 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Tue, 10 Apr 2007 12:52:43 +0200 Subject: [Haiku-commits] r20632 - haiku/trunk/src/add-ons/translators/raw Message-ID: <200704101052.l3AAqhhx017562@sheep.berlios.de> Author: axeld Date: 2007-04-10 12:52:41 +0200 (Tue, 10 Apr 2007) New Revision: 20632 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20632&view=rev Modified: haiku/trunk/src/add-ons/translators/raw/TIFF.h Log: Added missing TIFF tag types. Modified: haiku/trunk/src/add-ons/translators/raw/TIFF.h =================================================================== --- haiku/trunk/src/add-ons/translators/raw/TIFF.h 2007-04-10 05:28:56 UTC (rev 20631) +++ haiku/trunk/src/add-ons/translators/raw/TIFF.h 2007-04-10 10:52:41 UTC (rev 20632) @@ -10,10 +10,14 @@ enum types { - TIFF_UINT16_TYPE = 3, + TIFF_UINT8_TYPE = 1, + TIFF_STRING_TYPE, + TIFF_UINT16_TYPE, TIFF_UINT32_TYPE, TIFF_UFRACTION_TYPE, - TIFF_INT16_TYPE = 8, + TIFF_INT8_TYPE, + TIFF_UNDEFINED_TYPE, + TIFF_INT16_TYPE, TIFF_INT32_TYPE, TIFF_FRACTION_TYPE, TIFF_FLOAT_TYPE, From axeld at mail.berlios.de Tue Apr 10 12:54:49 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Tue, 10 Apr 2007 12:54:49 +0200 Subject: [Haiku-commits] r20633 - haiku/trunk/src/add-ons/translators/jpeg Message-ID: <200704101054.l3AAsnxt018827@sheep.berlios.de> Author: axeld Date: 2007-04-10 12:54:44 +0200 (Tue, 10 Apr 2007) New Revision: 20633 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20633&view=rev Added: haiku/trunk/src/add-ons/translators/jpeg/exif_parser.cpp haiku/trunk/src/add-ons/translators/jpeg/exif_parser.h Modified: haiku/trunk/src/add-ons/translators/jpeg/JPEGTranslator.cpp haiku/trunk/src/add-ons/translators/jpeg/JPEGTranslator.h haiku/trunk/src/add-ons/translators/jpeg/Jamfile Log: * Now also saves the EXIF data in the supplied message in Translate() (decompress only, you cannot add EXIF data yet). * Preparations to honour the orientation of JPEG images stored in the EXIF tags. Modified: haiku/trunk/src/add-ons/translators/jpeg/JPEGTranslator.cpp =================================================================== --- haiku/trunk/src/add-ons/translators/jpeg/JPEGTranslator.cpp 2007-04-10 10:52:41 UTC (rev 20632) +++ haiku/trunk/src/add-ons/translators/jpeg/JPEGTranslator.cpp 2007-04-10 10:54:44 UTC (rev 20633) @@ -32,9 +32,13 @@ #include "JPEGTranslator.h" +#include "exif_parser.h" + #include +#define MARKER_EXIF 0xe1 + // Set these accordingly #define JPEG_ACRONYM "JPEG" #define JPEG_FORMAT 'JPEG' @@ -79,7 +83,13 @@ {} }; +// Main functions of translator :) +static status_t Copy(BPositionIO *in, BPositionIO *out); +static status_t Compress(BPositionIO *in, BPositionIO *out); +static status_t Decompress(BPositionIO *in, BPositionIO *out, BMessage* ioExtension); +static status_t Error(j_common_ptr cinfo, status_t error = B_ERROR); + bool gAreSettingsRunning = false; @@ -1054,14 +1064,14 @@ } else if (inInfo->type == B_TRANSLATOR_BITMAP && outType == JPEG_FORMAT) { return Compress(inSource, outDestination); } else if (inInfo->type == JPEG_FORMAT && outType == B_TRANSLATOR_BITMAP) { - return Decompress(inSource, outDestination); + return Decompress(inSource, outDestination, ioExtension); } return B_NO_TRANSLATOR; } /*! The user has requested the same format for input and output, so just copy */ -status_t +static status_t Copy(BPositionIO *in, BPositionIO *out) { int block_size = 65536; @@ -1095,7 +1105,7 @@ /*! Encode into the native format */ -status_t +static status_t Compress(BPositionIO *in, BPositionIO *out) { // Load Settings @@ -1307,8 +1317,8 @@ /*! Decode the native format */ -status_t -Decompress(BPositionIO *in, BPositionIO *out) +static status_t +Decompress(BPositionIO *in, BPositionIO *out, BMessage* ioExtension) { // Load Settings jpeg_settings settings; @@ -1321,16 +1331,39 @@ jpeg_create_decompress(&cinfo); be_jpeg_stdio_src(&cinfo, in); + jpeg_save_markers(&cinfo, MARKER_EXIF, 131072); + // make sure the EXIF tag is stored + // Read info about image jpeg_read_header(&cinfo, TRUE); + BMessage exif; + + if (ioExtension != NULL) { + // add EXIF data to message, if any + jpeg_marker_struct* marker = cinfo.marker_list; + while (marker != NULL) { + if (marker->marker == MARKER_EXIF + && !strncmp((char*)marker->data, "Exif", 4)) { + // Strip EXIF header from TIFF data + ioExtension->AddData("exif", B_RAW_TYPE, + (uint8 *)marker->data + 6, marker->data_length - 6); + + BMemoryIO io(marker->data + 6, marker->data_length - 6); + convert_exif_to_message(io, exif); + } + marker = marker->next; + } + } + // Default color info - color_space out_color_space = B_RGB32; - int out_color_components = 4; + color_space outColorSpace = B_RGB32; + int outColorComponents = 4; // Function pointer to convert function // It will point to proper function if needed - void (*converter)(uchar *inscanline, uchar *outscanline, int inrow_bytes) = convert_from_24_to_32; + void (*converter)(uchar *inScanLine, uchar *outScanLine, + int inRowBytes) = convert_from_24_to_32; // If color space isn't rgb if (cinfo.out_color_space != JCS_RGB) { @@ -1342,8 +1375,8 @@ // Check if user wants to read only as RGB32 or not if (!settings.Always_B_RGB32) { // Grayscale - out_color_space = B_GRAY8; - out_color_components = 1; + outColorSpace = B_GRAY8; + outColorComponents = 1; converter = NULL; } else { // RGB @@ -1376,12 +1409,21 @@ // Initialize decompression jpeg_start_decompress(&cinfo); - // !!! Initialize this bounds rect to the size of your image - BRect bounds(0, 0, cinfo.output_width-1, cinfo.output_height-1); + int32 orientation; + if (exif.FindInt32("Orientation", &orientation) != B_OK) + orientation = 1; + // Initialize this bounds rect to the size of your image + BRect bounds(0, 0, cinfo.output_width - 1, cinfo.output_height - 1); + if (orientation & 4) { + // image is rotated + bounds.right = cinfo.output_height - 1; + bounds.bottom = cinfo.output_width - 1; + } + // Bytes count in one line of image (scanline) - int64 row_bytes = cinfo.output_width * out_color_components; - + int64 rowBytes = cinfo.output_width * outColorComponents; + // Fill out the B_TRANSLATOR_BITMAP's header TranslatorBitmap header; header.magic = B_HOST_TO_BENDIAN_INT32(B_TRANSLATOR_BITMAP); @@ -1389,9 +1431,9 @@ header.bounds.top = B_HOST_TO_BENDIAN_FLOAT(bounds.top); header.bounds.right = B_HOST_TO_BENDIAN_FLOAT(bounds.right); header.bounds.bottom = B_HOST_TO_BENDIAN_FLOAT(bounds.bottom); - header.colors = (color_space)B_HOST_TO_BENDIAN_INT32(out_color_space); - header.rowBytes = B_HOST_TO_BENDIAN_INT32(row_bytes); - header.dataSize = B_HOST_TO_BENDIAN_INT32(row_bytes * cinfo.output_height); + header.colors = (color_space)B_HOST_TO_BENDIAN_INT32(outColorSpace); + header.rowBytes = B_HOST_TO_BENDIAN_INT32(rowBytes); + header.dataSize = B_HOST_TO_BENDIAN_INT32(rowBytes * cinfo.output_height); // Write out the header status_t err = out->Write(&header, sizeof(TranslatorBitmap)); @@ -1408,14 +1450,14 @@ // Allocate scanline // Use libjpeg memory allocation functions, so in case of error it will free them itself in_scanline = (unsigned char *)(cinfo.mem->alloc_large)((j_common_ptr)&cinfo, - JPOOL_PERMANENT, row_bytes); + JPOOL_PERMANENT, rowBytes); // We need 2nd scanline storage only for conversion if (converter != NULL) { // There will be conversion, allocate second scanline... // Use libjpeg memory allocation functions, so in case of error it will free them itself out_scanline = (unsigned char *)(cinfo.mem->alloc_large)((j_common_ptr)&cinfo, - JPOOL_PERMANENT, row_bytes); + JPOOL_PERMANENT, rowBytes); // ... and make it the one to write to file writeline = out_scanline; } else @@ -1427,11 +1469,11 @@ // Convert if needed if (converter != NULL) - converter(in_scanline, out_scanline, row_bytes); + converter(in_scanline, out_scanline, rowBytes); // Write the scanline buffer to the output stream - err = out->Write(writeline, row_bytes); - if (err < row_bytes) + err = out->Write(writeline, rowBytes); + if (err < rowBytes) return err < B_OK ? Error((j_common_ptr)&cinfo, err) : Error((j_common_ptr)&cinfo, B_ERROR); } @@ -1445,7 +1487,7 @@ Frees jpeg alocated memory Returns given error (B_ERROR by default) */ -status_t +static status_t Error(j_common_ptr cinfo, status_t error) { jpeg_destroy(cinfo); Modified: haiku/trunk/src/add-ons/translators/jpeg/JPEGTranslator.h =================================================================== --- haiku/trunk/src/add-ons/translators/jpeg/JPEGTranslator.h 2007-04-10 10:52:41 UTC (rev 20632) +++ haiku/trunk/src/add-ons/translators/jpeg/JPEGTranslator.h 2007-04-10 10:54:44 UTC (rev 20633) @@ -215,10 +215,4 @@ EXTERN(struct jpeg_error_mgr *) be_jpeg_std_error (struct jpeg_error_mgr * err, jpeg_settings * settings); // from "be_jerror.cpp" -// Main functions of translator :) -status_t Copy(BPositionIO *in, BPositionIO *out); -status_t Compress(BPositionIO *in, BPositionIO *out); -status_t Decompress(BPositionIO *in, BPositionIO *out); -status_t Error(j_common_ptr cinfo, status_t error = B_ERROR); - #endif // _JPEGTRANSLATOR_H_ Modified: haiku/trunk/src/add-ons/translators/jpeg/Jamfile =================================================================== --- haiku/trunk/src/add-ons/translators/jpeg/Jamfile 2007-04-10 10:52:41 UTC (rev 20632) +++ haiku/trunk/src/add-ons/translators/jpeg/Jamfile 2007-04-10 10:54:44 UTC (rev 20633) @@ -9,6 +9,9 @@ SubDirSysHdrs [ FDirName $(SUBDIR) libjpeg ] ; +SubDirSysHdrs [ FDirName $(SUBDIR) $(DOTDOT) raw ] ; + # for TIFF.h and ReadHelper.h + local jpeg_files = # libjpeg jcapimin.c @@ -82,6 +85,7 @@ be_jdatadst.cpp be_jdatasrc.cpp be_jerror.cpp + exif_parser.cpp JPEGTranslator.cpp $(jpeg_files) Added: haiku/trunk/src/add-ons/translators/jpeg/exif_parser.cpp =================================================================== --- haiku/trunk/src/add-ons/translators/jpeg/exif_parser.cpp 2007-04-10 10:52:41 UTC (rev 20632) +++ haiku/trunk/src/add-ons/translators/jpeg/exif_parser.cpp 2007-04-10 10:54:44 UTC (rev 20633) @@ -0,0 +1,327 @@ +/* + * Copyright 2007, Axel D?rfler, axeld at pinc-software.de. All rights reserved. + * Distributed under the terms of the MIT License. + */ + + +#include "exif_parser.h" + +#include + +#include + +#include +#include +#include + + +enum { + TAG_EXIF_OFFSET = 0x8769, + TAG_SUB_DIR_OFFSET = 0xa005, + + TAG_MAKER = 0x10f, + TAG_MODEL = 0x110, + TAG_ORIENTATION = 0x112, + TAG_EXPOSURE_TIME = 0x829a, + TAG_ISO = 0x8827, +}; + +static const convert_tag kDefaultTags[] = { + {TAG_MAKER, B_ANY_TYPE, "Maker"}, + {TAG_MODEL, B_ANY_TYPE, "Model"}, + {TAG_ORIENTATION, B_INT32_TYPE, "Orientation"}, + {TAG_EXPOSURE_TIME, B_DOUBLE_TYPE, "ExposureTime"}, + {TAG_ISO, B_INT32_TYPE, "ISO"}, +}; +static const size_t kNumDefaultTags = sizeof(kDefaultTags) + / sizeof(kDefaultTags[0]); + + +static status_t parse_tiff_directory(TReadHelper& read, BMessage& target, + const convert_tag* tags, size_t tagCount); + + +static status_t +add_to_message(TReadHelper& source, BMessage& target, tiff_tag& tag, + const char* name, type_code type) +{ + type_code defaultType = B_INT32_TYPE; + double doubleValue = 0.0; + int32 intValue = 0; + + switch (tag.type) { + case TIFF_STRING_TYPE: + { + if (type != B_ANY_TYPE && type != B_STRING_TYPE) + return B_BAD_VALUE; + + char* buffer = (char*)malloc(tag.length); + if (buffer == NULL) + return B_NO_MEMORY; + + source(buffer, tag.length); + + // remove trailing spaces + int32 i = tag.length; + while (--i > 0 && isspace(buffer[i]) || !buffer[i]) { + buffer[i] = '\0'; + } + + status_t status = target.AddString(name, buffer); + free(buffer); + + return status; + } + + case TIFF_UNDEFINED_TYPE: + { + if (type != B_ANY_TYPE && type != B_STRING_TYPE && type != B_RAW_TYPE) + return B_BAD_VALUE; + + char* buffer = (char*)malloc(tag.length); + if (buffer == NULL) + return B_NO_MEMORY; + + source(buffer, tag.length); + + status_t status; + if (type == B_STRING_TYPE) + status = target.AddString(name, buffer); + else + status = target.AddData(name, B_RAW_TYPE, buffer, tag.length); + + free(buffer); + + return status; + } + + // unsigned + case TIFF_UINT8_TYPE: + intValue = source.Next(); + break; + case TIFF_UINT16_TYPE: + defaultType = B_INT32_TYPE; + intValue = source.Next(); + break; + case TIFF_UINT32_TYPE: + defaultType = B_INT32_TYPE; + intValue = source.Next(); + break; + case TIFF_UFRACTION_TYPE: + { + defaultType = B_DOUBLE_TYPE; + double value = source.Next(); + doubleValue = value / source.Next(); + break; + } + + // signed + case TIFF_INT8_TYPE: + intValue = source.Next(); + break; + case TIFF_INT16_TYPE: + intValue = source.Next(); + break; + case TIFF_INT32_TYPE: + intValue = source.Next(); + break; + case TIFF_FRACTION_TYPE: + { + defaultType = B_DOUBLE_TYPE; + double value = source.Next(); + doubleValue = value / source.Next(); + } + + // floating point + case TIFF_FLOAT_TYPE: + defaultType = B_FLOAT_TYPE; + doubleValue = source.Next(); + break; + case TIFF_DOUBLE_TYPE: + defaultType = B_DOUBLE_TYPE; + doubleValue = source.Next(); + break; + + default: + return B_BAD_VALUE; + } + + if (defaultType == B_INT32_TYPE) + doubleValue = intValue; + else + intValue = int32(doubleValue + 0.5); + + if (type == B_ANY_TYPE) + type = defaultType; + + switch (type) { + case B_INT32_TYPE: + return target.AddInt32(name, intValue); + case B_FLOAT_TYPE: + return target.AddFloat(name, doubleValue); + case B_DOUBLE_TYPE: + return target.AddDouble(name, doubleValue); + + default: + return B_BAD_VALUE; + } +} + + +static const convert_tag* +find_convert_tag(uint16 id, const convert_tag* tags, size_t count) +{ + for (size_t i = 0; i < count; i++) { + if (tags[i].tag == id) + return &tags[i]; + } + + return NULL; +} + + +/*! + Reads a TIFF tag and positions the file stream to its data section +*/ +void +parse_tiff_tag(TReadHelper& read, tiff_tag& tag, off_t& offset) +{ + read(tag.tag); + read(tag.type); + read(tag.length); + + offset = read.Position() + 4; + + uint32 length = tag.length; + + switch (tag.type) { + case TIFF_UINT16_TYPE: + case TIFF_INT16_TYPE: + length *= 2; + break; + + case TIFF_UINT32_TYPE: + case TIFF_INT32_TYPE: + case TIFF_FLOAT_TYPE: + length *= 4; + break; + + case TIFF_UFRACTION_TYPE: + case TIFF_FRACTION_TYPE: + case TIFF_DOUBLE_TYPE: + length *= 8; + break; + + default: + break; + } + + if (length > 4) { + uint32 position; + read(position); + + read.Seek(position, SEEK_SET); + } +} + + +static status_t +parse_tiff_directory(TReadHelper& read, off_t offset, BMessage& target, + const convert_tag* convertTags, size_t convertTagCount) +{ + read.Seek(offset, SEEK_SET); + + uint16 tags; + read(tags); + if (tags > 512) + return B_BAD_DATA; + + while (tags--) { + off_t nextOffset; + tiff_tag tag; + parse_tiff_tag(read, tag, nextOffset); + + //printf("TAG %u\n", tag.tag); + + switch (tag.tag) { + case TAG_EXIF_OFFSET: + case TAG_SUB_DIR_OFFSET: + { + status_t status = parse_tiff_directory(read, target, + convertTags, convertTagCount); + if (status < B_OK) + return status; + break; + } + + default: + const convert_tag* convertTag = find_convert_tag(tag.tag, + convertTags, convertTagCount); + if (convertTag != NULL) { + add_to_message(read, target, tag, convertTag->name, + convertTag->type); + } + break; + } + read.Seek(nextOffset, SEEK_SET); + } + + return B_OK; +} + + +static status_t +parse_tiff_directory(TReadHelper& read, BMessage& target, + const convert_tag* tags, size_t tagCount) +{ + while (true) { + int32 offset; + read(offset); + if (offset == 0) + break; + + status_t status = parse_tiff_directory(read, offset, target, + tags, tagCount); + if (status < B_OK) + return status; + } + + return B_OK; +} + + +// #pragma mark - + + +status_t +convert_exif_to_message(BPositionIO& source, BMessage& target, + const convert_tag* tags, size_t tagCount) +{ + TReadHelper read(source); + + uint16 endian; + read(endian); + if (endian != 'MM' && endian != 'II') + return B_BAD_TYPE; + +#if B_HOST_IS_LENDIAN + read.SetSwap(endian == 'MM'); +#else + read.SetSwap(endian == 'II'); +#endif + + int16 magic; + read(magic); + if (magic != 42) + return B_BAD_TYPE; + + return parse_tiff_directory(read, target, tags, tagCount); +} + + +status_t +convert_exif_to_message(BPositionIO& source, BMessage& target) +{ + return convert_exif_to_message(source, target, kDefaultTags, + kNumDefaultTags); +} Added: haiku/trunk/src/add-ons/translators/jpeg/exif_parser.h =================================================================== --- haiku/trunk/src/add-ons/translators/jpeg/exif_parser.h 2007-04-10 10:52:41 UTC (rev 20632) +++ haiku/trunk/src/add-ons/translators/jpeg/exif_parser.h 2007-04-10 10:54:44 UTC (rev 20633) @@ -0,0 +1,25 @@ +/* + * Copyright 2007, Axel D?rfler, axeld at pinc-software.de. All rights reserved. + * Distributed under the terms of the MIT License. + */ +#ifndef EXIF_PARSER_H +#define EXIF_PARSER_H + + +#include +#include + +class BMessage; + + +struct convert_tag { + uint16 tag; + type_code type; + const char* name; +}; + +status_t convert_exif_to_message(BPositionIO& source, BMessage& target); +status_t convert_exif_to_message_etc(BPositionIO& source, BMessage& target, + const convert_tag* tags, size_t tagCount); + +#endif // EXIF_PARSER_H From axeld at mail.berlios.de Tue Apr 10 15:35:17 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Tue, 10 Apr 2007 15:35:17 +0200 Subject: [Haiku-commits] r20634 - haiku/trunk/src/add-ons/translators/raw Message-ID: <200704101335.l3ADZHZu006706@sheep.berlios.de> Author: axeld Date: 2007-04-10 15:35:16 +0200 (Tue, 10 Apr 2007) New Revision: 20634 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20634&view=rev Modified: haiku/trunk/src/add-ons/translators/raw/RAW.cpp haiku/trunk/src/add-ons/translators/raw/RAWTranslator.cpp Log: * Now keeps the orientation as defined in EXIF, instead of converting it to something handy for computation. * The translator now passes the EXIF orientation to the thumbnail translation using a special field "exif:orientation". Modified: haiku/trunk/src/add-ons/translators/raw/RAW.cpp =================================================================== --- haiku/trunk/src/add-ons/translators/raw/RAW.cpp 2007-04-10 10:54:44 UTC (rev 20633) +++ haiku/trunk/src/add-ons/translators/raw/RAW.cpp 2007-04-10 13:35:16 UTC (rev 20634) @@ -77,6 +77,22 @@ } +static inline bool +x_flipped(int32 orientation) +{ + return orientation == 2 || orientation == 3 + || orientation == 7 || orientation == 8; +} + + +static inline bool +y_flipped(int32 orientation) +{ + return orientation == 3 || orientation == 4 + || orientation == 6 || orientation == 7; +} + + // #pragma mark - @@ -230,11 +246,11 @@ inline int32 DCRaw::_FlipIndex(uint32 row, uint32 col, uint32 flip) { - if (flip & 4) + if (flip > 4) SWAP(row, col); - if (flip & 2) + if (y_flipped(flip)) row = fInputHeight - 1 - row; - if (flip & 1) + if (x_flipped(flip)) col = fInputWidth - 1 - col; return row * fInputWidth + col; @@ -2379,8 +2395,8 @@ { uint8* line, lookUpTable[0x10000]; - uint32 width = image.flip & 4 ? fOutputHeight : fOutputWidth; - uint32 height = image.flip & 4 ? fOutputWidth : fOutputHeight; + uint32 width = image.flip > 4 ? fOutputHeight : fOutputWidth; + uint32 height = image.flip > 4 ? fOutputWidth : fOutputHeight; uint32 outputRow = (4 * fOutputBitsPerSample / 8) * width; uint32 outputOffset = 0; @@ -2646,7 +2662,7 @@ break; case 274: // Orientation - image.flip = "50132467"[fRead.Next() & 7] - '0'; + image.flip = fRead.Next(); break; case 277: // Samples Per Pixel @@ -3244,6 +3260,7 @@ if (rawCount == 0) return B_NO_TRANSLATOR; + fMeta.flip = _Raw().flip; return B_OK; } @@ -3262,7 +3279,7 @@ fOutputWidth = (fInputWidth + fShrink) >> fShrink; fOutputHeight = (fInputHeight + fShrink) >> fShrink; - if (image.flip & 4) { + if (image.flip > 4) { // image is rotated image.output_width = fOutputHeight; image.output_height = fOutputWidth; Modified: haiku/trunk/src/add-ons/translators/raw/RAWTranslator.cpp =================================================================== --- haiku/trunk/src/add-ons/translators/raw/RAWTranslator.cpp 2007-04-10 10:54:44 UTC (rev 20633) +++ haiku/trunk/src/add-ons/translators/raw/RAWTranslator.cpp 2007-04-10 13:35:16 UTC (rev 20634) @@ -185,6 +185,14 @@ if (!data.is_raw) { // let others handle embedded JPEG data BMemoryIO io(buffer, bufferSize); + BMessage buffer; + if (meta.flip != 1) { + // preserve orientation + if (settings == NULL) + settings = &buffer; + settings->AddInt32("exif:orientation", meta.flip); + } + BTranslatorRoster* roster = BTranslatorRoster::Default(); return roster->Translate(&io, NULL, settings, target, outType); } From axeld at mail.berlios.de Tue Apr 10 15:36:54 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Tue, 10 Apr 2007 15:36:54 +0200 Subject: [Haiku-commits] r20635 - haiku/trunk/src/add-ons/translators/jpeg Message-ID: <200704101336.l3ADasPV006816@sheep.berlios.de> Author: axeld Date: 2007-04-10 15:36:53 +0200 (Tue, 10 Apr 2007) New Revision: 20635 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20635&view=rev Modified: haiku/trunk/src/add-ons/translators/jpeg/JPEGTranslator.cpp Log: * Now honours the orientation as specified in the EXIF tags; not very well tested, so it might happen that some rotations don't come out as expected... * This orientation can be overridden with a special "exif:orientation" setting passed via the ioExtension message. Modified: haiku/trunk/src/add-ons/translators/jpeg/JPEGTranslator.cpp =================================================================== --- haiku/trunk/src/add-ons/translators/jpeg/JPEGTranslator.cpp 2007-04-10 13:35:16 UTC (rev 20634) +++ haiku/trunk/src/add-ons/translators/jpeg/JPEGTranslator.cpp 2007-04-10 13:36:53 UTC (rev 20635) @@ -193,15 +193,48 @@ } -// #pragma mark - conversion routines +static bool +x_flipped(int32 orientation) +{ + return orientation == 2 || orientation == 3 + || orientation == 6 || orientation == 7; +} +static bool +y_flipped(int32 orientation) +{ + return orientation == 3 || orientation == 4 + || orientation == 7 || orientation == 8; +} + + +static int32 +dest_index(uint32 width, uint32 height, uint32 x, uint32 y, int32 orientation) +{ + if (orientation > 4) { + uint32 temp = x; + x = y; + y = temp; + } + if (y_flipped(orientation)) + y = height - 1 - y; + if (x_flipped(orientation)) + x = width - 1 - x; + + return y * width + x; +} + + +// #pragma mark - conversion for compression + + inline void -convert_from_gray1_to_gray8(uchar *in, uchar *out, int in_bytes) +convert_from_gray1_to_gray8(uint8* in, uint8* out, int32 inRowBytes) { int32 index = 0; int32 index2 = 0; - while (index < in_bytes) { + while (index < inRowBytes) { unsigned char c = in[index++]; for (int b = 128; b; b = b>>1) { unsigned char color; @@ -216,11 +249,11 @@ inline void -convert_from_gray1_to_24(uchar *in, uchar *out, int in_bytes) +convert_from_gray1_to_24(uint8* in, uint8* out, int32 inRowBytes) { int32 index = 0; int32 index2 = 0; - while (index < in_bytes) { + while (index < inRowBytes) { unsigned char c = in[index++]; for (int b = 128; b; b = b>>1) { unsigned char color; @@ -237,12 +270,12 @@ inline void -convert_from_cmap8_to_24(uchar *in, uchar *out, int in_bytes) +convert_from_cmap8_to_24(uint8* in, uint8* out, int32 inRowBytes) { const color_map * map = system_colors(); int32 index = 0; int32 index2 = 0; - while (index < in_bytes) { + while (index < inRowBytes) { rgb_color color = map->color_list[in[index++]]; out[index2++] = color.red; @@ -253,12 +286,12 @@ inline void -convert_from_15_to_24(uchar *in, uchar *out, int in_bytes) +convert_from_15_to_24(uint8* in, uint8* out, int32 inRowBytes) { int32 index = 0; int32 index2 = 0; int16 in_pixel; - while (index < in_bytes) { + while (index < inRowBytes) { in_pixel = in[index] | (in[index+1] << 8); index += 2; @@ -270,12 +303,12 @@ inline void -convert_from_15b_to_24(uchar *in, uchar *out, int in_bytes) +convert_from_15b_to_24(uint8* in, uint8* out, int32 inRowBytes) { int32 index = 0; int32 index2 = 0; int16 in_pixel; - while (index < in_bytes) { + while (index < inRowBytes) { in_pixel = in[index+1] | (in[index] << 8); index += 2; @@ -287,12 +320,12 @@ inline void -convert_from_16_to_24(uchar *in, uchar *out, int in_bytes) +convert_from_16_to_24(uint8* in, uint8* out, int32 inRowBytes) { int32 index = 0; int32 index2 = 0; int16 in_pixel; - while (index < in_bytes) { + while (index < inRowBytes) { in_pixel = in[index] | (in[index+1] << 8); index += 2; @@ -304,12 +337,12 @@ inline void -convert_from_16b_to_24(uchar *in, uchar *out, int in_bytes) +convert_from_16b_to_24(uint8* in, uint8* out, int32 inRowBytes) { int32 index = 0; int32 index2 = 0; int16 in_pixel; - while (index < in_bytes) { + while (index < inRowBytes) { in_pixel = in[index+1] | (in[index] << 8); index += 2; @@ -321,11 +354,11 @@ inline void -convert_from_24_to_24(uchar *in, uchar *out, int in_bytes) +convert_from_24_to_24(uint8* in, uint8* out, int32 inRowBytes) { int32 index = 0; int32 index2 = 0; - while (index < in_bytes) { + while (index < inRowBytes) { out[index2++] = in[index+2]; out[index2++] = in[index+1]; out[index2++] = in[index]; @@ -335,84 +368,98 @@ inline void -convert_from_32_to_24(uchar *in, uchar *out, int in_bytes) +convert_from_32_to_24(uint8* in, uint8* out, int32 inRowBytes) { - int32 index = 0; - int32 index2 = 0; - while (index < in_bytes) { - out[index2++] = in[index+2]; - out[index2++] = in[index+1]; - out[index2++] = in[index]; - index+=4; + for (int32 i = 0; i < inRowBytes; i++) { + out[0] = in[2]; + out[1] = in[1]; + out[2] = in[0]; + + in += 4; + out += 3; } } inline void -convert_from_32b_to_24(uchar *in, uchar *out, int in_bytes) +convert_from_32b_to_24(uint8* in, uint8* out, int32 inRowBytes) { - int32 index = 0; - int32 index2 = 0; - while (index < in_bytes) { - index++; - out[index2++] = in[index++]; - out[index2++] = in[index++]; - out[index2++] = in[index++]; + for (int32 i = 0; i < inRowBytes; i++) { + out[1] = in[0]; + out[2] = in[1]; + out[3] = in[2]; + + in += 4; + out += 3; } } +// #pragma mark - conversion for decompression + + inline void -convert_from_CMYK_to_32_photoshop(uchar *in, uchar *out, int out_bytes) +convert_from_CMYK_to_32_photoshop(uint8* in, uint8* out, int32 inRowBytes, int32 xStep) { - int32 index = 0; - int32 index2 = 0; - int32 black = 0; - while (index < out_bytes) { - black = in[index2+3]; - out[index++] = in[index2+2]*black/255; - out[index++] = in[index2+1]*black/255; - out[index++] = in[index2]*black/255; - out[index++] = 255; - index2 += 4; + for (int32 i = 0; i < inRowBytes; i += 4) { + int32 black = in[3]; + out[0] = in[2] * black / 255; + out[1] = in[1] * black / 255; + out[2] = in[0] * black / 255; + out[3] = 255; + + in += 4; + out += xStep; } } //! !!! UNTESTED !!! inline void -convert_from_CMYK_to_32(uchar *in, uchar *out, int out_bytes) +convert_from_CMYK_to_32(uint8* in, uint8* out, int32 inRowBytes, int32 xStep) { - int32 index = 0; - int32 index2 = 0; - int32 black = 0; - while (index < out_bytes) { - black = 255 - in[index2+3]; - out[index++] = ((255-in[index2+2])*black)/255; - out[index++] = ((255-in[index2+1])*black)/255; - out[index++] = ((255-in[index2])*black)/255; - out[index++] = 255; - index2 += 4; + for (int32 i = 0; i < inRowBytes; i += 4) { + int32 black = 255 - in[3]; + out[0] = ((255 - in[2]) * black) / 255; + out[1] = ((255 - in[1]) * black) / 255; + out[2] = ((255 - in[0]) * black) / 255; + out[3] = 255; + + in += 4; + out += xStep; } } //! RGB24 8:8:8 to xRGB 8:8:8:8 inline void -convert_from_24_to_32(uchar *in, uchar *out, int out_bytes) +convert_from_24_to_32(uint8* in, uint8* out, int32 inRowBytes, int32 xStep) { - int32 index = 0; - int32 index2 = 0; - while (index < out_bytes) { - out[index++] = in[index2+2]; - out[index++] = in[index2+1]; - out[index++] = in[index2]; - out[index++] = 255; - index2 += 3; + for (int32 i = 0; i < inRowBytes; i += 3) { + out[0] = in[2]; + out[1] = in[1]; + out[2] = in[0]; + out[3] = 255; + + in += 3; + out += xStep; } } +//! 8-bit to 8-bit, only need when rotating the image +void +translate_8(uint8* in, uint8* out, int32 inRowBytes, int32 xStep) +{ + for (int32 i = 0; i < inRowBytes; i++) { + out[0] = in[0]; + + in++; + out += xStep; + } +} + + // #pragma mark - SView @@ -1134,7 +1181,8 @@ // Function pointer to convert function // It will point to proper function if needed - void (*converter)(uchar *inscanline, uchar *outscanline, int inrow_bytes) = NULL; + void (*converter)(uchar *inscanline, uchar *outscanline, + int32 inRowBytes) = NULL; // Default color info J_COLOR_SPACE jpg_color_space = JCS_RGB; @@ -1304,7 +1352,7 @@ // Convert if needed if (converter != NULL) - converter(in_scanline, out_scanline, in_row_bytes-padding); + converter(in_scanline, out_scanline, in_row_bytes - padding); // Write scanline jpeg_write_scanlines(&cinfo, &writeline, 1); @@ -1331,8 +1379,10 @@ jpeg_create_decompress(&cinfo); be_jpeg_stdio_src(&cinfo, in); +#if 1 jpeg_save_markers(&cinfo, MARKER_EXIF, 131072); // make sure the EXIF tag is stored +#endif // Read info about image jpeg_read_header(&cinfo, TRUE); @@ -1363,7 +1413,7 @@ // Function pointer to convert function // It will point to proper function if needed void (*converter)(uchar *inScanLine, uchar *outScanLine, - int inRowBytes) = convert_from_24_to_32; + int32 inRowBytes, int32 xStep) = convert_from_24_to_32; // If color space isn't rgb if (cinfo.out_color_space != JCS_RGB) { @@ -1377,7 +1427,7 @@ // Grayscale outColorSpace = B_GRAY8; outColorComponents = 1; - converter = NULL; + converter = translate_8; } else { // RGB cinfo.out_color_space = JCS_RGB; @@ -1409,20 +1459,42 @@ // Initialize decompression jpeg_start_decompress(&cinfo); + // retrieve orientation from settings/EXIF int32 orientation; - if (exif.FindInt32("Orientation", &orientation) != B_OK) - orientation = 1; + if (ioExtension == NULL + || ioExtension->FindInt32("exif:orientation", &orientation) != B_OK) { + if (exif.FindInt32("Orientation", &orientation) != B_OK) + orientation = 1; + } + if (orientation != 1 && converter == NULL) + converter = translate_8; + + int32 outputWidth = orientation > 4 ? cinfo.output_height : cinfo.output_width; + int32 outputHeight = orientation > 4 ? cinfo.output_width : cinfo.output_height; + + int32 destOffset = dest_index(outputWidth, outputHeight, + 0, 0, orientation) * outColorComponents; + int32 xStep = dest_index(outputWidth, outputHeight, + 1, 0, orientation) * outColorComponents - destOffset; + int32 yStep = dest_index(outputWidth, outputHeight, + 0, 1, orientation) * outColorComponents - destOffset; + bool needAll = orientation != 1; + // Initialize this bounds rect to the size of your image - BRect bounds(0, 0, cinfo.output_width - 1, cinfo.output_height - 1); - if (orientation & 4) { - // image is rotated - bounds.right = cinfo.output_height - 1; - bounds.bottom = cinfo.output_width - 1; - } + BRect bounds(0, 0, outputWidth - 1, outputHeight - 1); +#if 0 +printf("destOffset = %ld, xStep = %ld, yStep = %ld, input: %ld x %ld, output: %ld x %ld, orientation %ld\n", + destOffset, xStep, yStep, (int32)cinfo.output_width, (int32)cinfo.output_height, + bounds.IntegerWidth() + 1, bounds.IntegerHeight() + 1, orientation); +#endif + // Bytes count in one line of image (scanline) - int64 rowBytes = cinfo.output_width * outColorComponents; + int32 inRowBytes = cinfo.output_width * cinfo.output_components; + int32 rowBytes = (bounds.IntegerWidth() + 1) * outColorComponents; + int32 dataSize = cinfo.output_width * cinfo.output_height + * outColorComponents; // Fill out the B_TRANSLATOR_BITMAP's header TranslatorBitmap header; @@ -1433,7 +1505,7 @@ header.bounds.bottom = B_HOST_TO_BENDIAN_FLOAT(bounds.bottom); header.colors = (color_space)B_HOST_TO_BENDIAN_INT32(outColorSpace); header.rowBytes = B_HOST_TO_BENDIAN_INT32(rowBytes); - header.dataSize = B_HOST_TO_BENDIAN_INT32(rowBytes * cinfo.output_height); + header.dataSize = B_HOST_TO_BENDIAN_INT32(dataSize); // Write out the header status_t err = out->Write(&header, sizeof(TranslatorBitmap)); @@ -1443,39 +1515,53 @@ return Error((j_common_ptr)&cinfo, B_ERROR); // Declare scanlines - JSAMPROW in_scanline = NULL; - JSAMPROW out_scanline = NULL; - JSAMPROW writeline; // Pointer to in_scanline or out_scanline (if there will be conversion) + JSAMPROW inScanLine = NULL; + uint8* dest = NULL; + uint8* destLine = NULL; // Allocate scanline // Use libjpeg memory allocation functions, so in case of error it will free them itself - in_scanline = (unsigned char *)(cinfo.mem->alloc_large)((j_common_ptr)&cinfo, - JPOOL_PERMANENT, rowBytes); + inScanLine = (unsigned char *)(cinfo.mem->alloc_large)((j_common_ptr)&cinfo, + JPOOL_PERMANENT, inRowBytes); // We need 2nd scanline storage only for conversion if (converter != NULL) { // There will be conversion, allocate second scanline... - // Use libjpeg memory allocation functions, so in case of error it will free them itself - out_scanline = (unsigned char *)(cinfo.mem->alloc_large)((j_common_ptr)&cinfo, - JPOOL_PERMANENT, rowBytes); - // ... and make it the one to write to file - writeline = out_scanline; + // Use libjpeg memory allocation functions, so in case of error it will free + // them itself + dest = (uint8*)(cinfo.mem->alloc_large)((j_common_ptr)&cinfo, + JPOOL_PERMANENT, needAll ? dataSize : rowBytes); + destLine = dest + destOffset; } else - writeline = in_scanline; + destLine = inScanLine; while (cinfo.output_scanline < cinfo.output_height) { // Read scanline - jpeg_read_scanlines(&cinfo, &in_scanline, 1); + jpeg_read_scanlines(&cinfo, &inScanLine, 1); // Convert if needed if (converter != NULL) - converter(in_scanline, out_scanline, rowBytes); + converter(inScanLine, destLine, inRowBytes, xStep); - // Write the scanline buffer to the output stream - err = out->Write(writeline, rowBytes); - if (err < rowBytes) - return err < B_OK ? Error((j_common_ptr)&cinfo, err) + if (!needAll) { + // Write the scanline buffer to the output stream + ssize_t bytesWritten = out->Write(destLine, rowBytes); + if (bytesWritten < rowBytes) { + return bytesWritten < B_OK + ? Error((j_common_ptr)&cinfo, bytesWritten) + : Error((j_common_ptr)&cinfo, B_ERROR); + } + } else + destLine += yStep; + } + + if (needAll) { + ssize_t bytesWritten = out->Write(dest, dataSize); + if (bytesWritten < dataSize) { + return bytesWritten < B_OK + ? Error((j_common_ptr)&cinfo, bytesWritten) : Error((j_common_ptr)&cinfo, B_ERROR); + } } jpeg_finish_decompress(&cinfo); From jackburton at mail.berlios.de Tue Apr 10 16:11:32 2007 From: jackburton at mail.berlios.de (jackburton at BerliOS) Date: Tue, 10 Apr 2007 16:11:32 +0200 Subject: [Haiku-commits] r20636 - haiku/trunk/src/kits/opengl Message-ID: <200704101411.l3AEBWwL009591@sheep.berlios.de> Author: jackburton Date: 2007-04-10 16:11:32 +0200 (Tue, 10 Apr 2007) New Revision: 20636 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20636&view=rev Modified: haiku/trunk/src/kits/opengl/GLView.cpp Log: Implemented BGLView::DirectConnected(). I don't know if it works, since the gldirect_mode test app crashes at startup (also before this commit). Style changes. Modified: haiku/trunk/src/kits/opengl/GLView.cpp =================================================================== --- haiku/trunk/src/kits/opengl/GLView.cpp 2007-04-10 13:36:53 UTC (rev 20635) +++ haiku/trunk/src/kits/opengl/GLView.cpp 2007-04-10 14:11:32 UTC (rev 20636) @@ -26,13 +26,25 @@ #include #include +#include #include #include + #include "GLRendererRoster.h" +struct glview_direct_info { + direct_buffer_info *direct_info; + bool direct_connected; + + glview_direct_info(); + ~glview_direct_info(); +}; + + BGLView::BGLView(BRect rect, char *name, ulong resizingMode, ulong mode, ulong options) : BView(rect, name, B_FOLLOW_ALL_SIDES, mode | B_WILL_DRAW | B_FRAME_EVENTS), // | B_FULL_UPDATE_ON_RESIZE) - fRenderer(NULL) + m_clip_info(NULL), + fRenderer(NULL) { fRoster = new GLRendererRoster(this, options); } @@ -40,11 +52,14 @@ BGLView::~BGLView() { + delete (glview_direct_info *)m_clip_info; if (fRenderer) fRenderer->Release(); } -void BGLView::LockGL() + +void +BGLView::LockGL() { // TODO: acquire the OpenGL API lock it on this glview @@ -52,7 +67,9 @@ fRenderer->LockGL(); } -void BGLView::UnlockGL() + +void +BGLView::UnlockGL() { if (fRenderer) fRenderer->UnlockGL(); @@ -60,23 +77,31 @@ // TODO: release the GL API lock to others glviews } -void BGLView::SwapBuffers() + +void +BGLView::SwapBuffers() { SwapBuffers(false); } -void BGLView::SwapBuffers(bool vSync) + +void +BGLView::SwapBuffers(bool vSync) { if (fRenderer) fRenderer->SwapBuffers(vSync); } -BView * BGLView::EmbeddedView() + +BView * +BGLView::EmbeddedView() { return NULL; } -status_t BGLView::CopyPixelsOut(BPoint source, BBitmap *dest) + +status_t +BGLView::CopyPixelsOut(BPoint source, BBitmap *dest) { if (!fRenderer) return B_ERROR; @@ -87,7 +112,9 @@ return fRenderer->CopyPixelsOut(source, dest); } -status_t BGLView::CopyPixelsIn(BBitmap *source, BPoint dest) + +status_t +BGLView::CopyPixelsIn(BBitmap *source, BPoint dest) { if (!fRenderer) return B_ERROR; @@ -98,12 +125,14 @@ return fRenderer->CopyPixelsIn(source, dest); } + /* Mesa's GLenum is not ulong but uint, so we can't use GLenum without breaking this method signature. Instead, we have to use the effective BeOS's SGI OpenGL GLenum type: unsigned long. */ -void BGLView::ErrorCallback(unsigned long errorCode) +void +BGLView::ErrorCallback(unsigned long errorCode) { char msg[32]; sprintf(msg, "GL: Error code $%04lx.", errorCode); @@ -111,7 +140,9 @@ fprintf(stderr, "%s\n", msg); } -void BGLView::Draw(BRect updateRect) + +void +BGLView::Draw(BRect updateRect) { if (fRenderer) return fRenderer->Draw(updateRect); @@ -121,7 +152,9 @@ DrawString("No OpenGL renderer available!"); } -void BGLView::AttachedToWindow() + +void +BGLView::AttachedToWindow() { BView::AttachedToWindow(); @@ -143,12 +176,16 @@ // SetFontSize(16); } -void BGLView::AllAttached() + +void +BGLView::AllAttached() { BView::AllAttached(); } -void BGLView::DetachedFromWindow() + +void +BGLView::DetachedFromWindow() { if (fRenderer) fRenderer->Release(); @@ -157,106 +194,155 @@ BView::DetachedFromWindow(); } -void BGLView::AllDetached() + +void +BGLView::AllDetached() { BView::AllDetached(); } -void BGLView::FrameResized(float width, float height) + +void +BGLView::FrameResized(float width, float height) { + m_bounds.Set(0, 0, width, height); if (fRenderer) fRenderer->FrameResized(width, height); BView::FrameResized(width, height); } -status_t BGLView::Perform(perform_code d, void *arg) + +status_t +BGLView::Perform(perform_code d, void *arg) { return BView::Perform(d, arg); } -status_t BGLView::Archive(BMessage *data, bool deep) const +status_t +BGLView::Archive(BMessage *data, bool deep) const { return BView::Archive(data, deep); } -void BGLView::MessageReceived(BMessage *msg) + +void +BGLView::MessageReceived(BMessage *msg) { BView::MessageReceived(msg); } -void BGLView::SetResizingMode(uint32 mode) + +void +BGLView::SetResizingMode(uint32 mode) { BView::SetResizingMode(mode); } -void BGLView::Show() + +void +BGLView::Show() { BView::Show(); } -void BGLView::Hide() + +void +BGLView::Hide() { BView::Hide(); } -BHandler *BGLView::ResolveSpecifier(BMessage *msg, int32 index, + +BHandler * +BGLView::ResolveSpecifier(BMessage *msg, int32 index, BMessage *specifier, int32 form, const char *property) { return BView::ResolveSpecifier(msg, index, specifier, form, property); } -status_t BGLView::GetSupportedSuites(BMessage *data) + +status_t +BGLView::GetSupportedSuites(BMessage *data) { return BView::GetSupportedSuites(data); } -void BGLView::DirectConnected( direct_buffer_info *info ) + +void +BGLView::DirectConnected(direct_buffer_info *info) { - /* TODO: - - update local copy of caller's BDirectWindow's direct_buffer_info - - clip it against BGLView's visible region - - pass the view's clipped direct_buffer_info to renderer's DirectConnect() - */ - -#if 0 - if (! m_direct_connected && m_direct_connection_disabled) + // TODO: Locking !!!!! + // TODO: We should probably prevent the renderer to draw anything + // (lock_draw() ??) while we are in this method + + if (!m_clip_info/* && m_direct_connection_disabled*/) return; - direct_info_locker->Lock(); + glview_direct_info *glviewDirectInfo = (glview_direct_info *)m_clip_info; + direct_buffer_info *localInfo = glviewDirectInfo->direct_info; + //direct_info_locker->Lock(); switch(info->buffer_state & B_DIRECT_MODE_MASK) { - case B_DIRECT_START: - m_direct_connected = true; - case B_DIRECT_MODIFY: - // Get clipping information - if (m_clip_list) - free(m_clip_list); - m_clip_list_count = info->clip_list_count; - m_clip_list = (clipping_rect *) malloc(m_clip_list_count*sizeof(clipping_rect)); - if (m_clip_list) { - memcpy(m_clip_list, info->clip_list, m_clip_list_count*sizeof(clipping_rect)); - fBits = (uint8 *) info->bits; - fRowBytes = info->bytes_per_row; - fFormat = info->pixel_format; - fBounds = info->window_bounds; - fDirty = true; - } - break; - case B_DIRECT_STOP: - fConnected = false; - break; + case B_DIRECT_START: + glviewDirectInfo->direct_connected = true; + case B_DIRECT_MODIFY: + { + localInfo->buffer_state = info->buffer_state; + localInfo->driver_state = info->driver_state; + localInfo->bits = info->bits; + localInfo->pci_bits = info->pci_bits; + localInfo->bytes_per_row = info->bytes_per_row; + localInfo->bits_per_pixel = info->bits_per_pixel; + localInfo->pixel_format = info->pixel_format; + localInfo->layout = info->layout; + localInfo->orientation = info->orientation; + //memcpy(&localInfo->_reserved, info->_reserved, sizeof(info->_reserved)); + //localInfo->_dd_type_ = info->_dd_type_; + //localInfo->_dd_token_ = info->_dd_token_; + + localInfo->window_bounds = info->window_bounds; + + // Collect the rects into a BRegion, then clip to the view's bounds + BRegion region; + for (uint32 c = 0; c < info->clip_list_count; c++) + region.Include(info->clip_list[c]); + // TODO: I have the feeling that this Bounds() call won't work here. + // Probably m_bounds should be used, but it should then be maintained correctly + // on view resizing/moving... + BRegion boundsRegion = Bounds(); + region.IntersectWith(&boundsRegion); + + localInfo->clip_list_count = region.CountRects(); + localInfo->clip_bounds = region.FrameInt(); + + for (uint32 c = 0; c < localInfo->clip_list_count; c++) + localInfo->clip_list[c] = region.RectAtInt(c); + + break; + } + case B_DIRECT_STOP: + glviewDirectInfo->direct_connected = false; + break; } - direct_info_locker->Unlock(); -#endif + //direct_info_locker->Unlock(); if (fRenderer) - fRenderer->DirectConnected(info); + fRenderer->DirectConnected(localInfo); } -void BGLView::EnableDirectMode( bool enabled ) + +void +BGLView::EnableDirectMode(bool enabled) { + if (!m_clip_info && enabled) + m_clip_info = new glview_direct_info(); + else if (m_clip_info && !enabled) { + delete (glview_direct_info *)m_clip_info; + m_clip_info = NULL; + } + if (fRenderer) fRenderer->EnableDirectMode(enabled); } @@ -413,3 +499,16 @@ }; +glview_direct_info::glview_direct_info() +{ + // TODO: See direct_window_data() in app_server's ServerWindow.cpp + direct_info = (direct_buffer_info *)malloc(sizeof(B_PAGE_SIZE)); + direct_connected = false; +} + + +glview_direct_info::~glview_direct_info() +{ + free(direct_info); +} + From axeld at mail.berlios.de Tue Apr 10 17:01:22 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Tue, 10 Apr 2007 17:01:22 +0200 Subject: [Haiku-commits] r20637 - haiku/trunk/src/bin/network/telnetd Message-ID: <200704101501.l3AF1M93013871@sheep.berlios.de> Author: axeld Date: 2007-04-10 17:01:22 +0200 (Tue, 10 Apr 2007) New Revision: 20637 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20637&view=rev Modified: haiku/trunk/src/bin/network/telnetd/telnetd.c Log: Fixed build (IP_TOS is defined now). Modified: haiku/trunk/src/bin/network/telnetd/telnetd.c =================================================================== --- haiku/trunk/src/bin/network/telnetd/telnetd.c 2007-04-10 14:11:32 UTC (rev 20636) +++ haiku/trunk/src/bin/network/telnetd/telnetd.c 2007-04-10 15:01:22 UTC (rev 20637) @@ -138,11 +138,11 @@ int ch; #ifndef __BEOS__ u_long ultmp; -# if defined(IPPROTO_IP) && defined(IP_TOS) - int tos = -1; -# endif char *ep; #endif +#if defined(IPPROTO_IP) && defined(IP_TOS) + int tos = -1; +#endif pfrontp = pbackp = ptyobuf; netip = netibuf; From stippi at mail.berlios.de Tue Apr 10 18:20:40 2007 From: stippi at mail.berlios.de (stippi at BerliOS) Date: Tue, 10 Apr 2007 18:20:40 +0200 Subject: [Haiku-commits] r20638 - haiku/trunk/src/apps/abouthaiku Message-ID: <200704101620.l3AGKeVr021331@sheep.berlios.de> Author: stippi Date: 2007-04-10 18:20:40 +0200 (Tue, 10 Apr 2007) New Revision: 20638 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20638&view=rev Modified: haiku/trunk/src/apps/abouthaiku/AboutHaiku.cpp Log: added Hugo Santos to the list of developers Modified: haiku/trunk/src/apps/abouthaiku/AboutHaiku.cpp =================================================================== --- haiku/trunk/src/apps/abouthaiku/AboutHaiku.cpp 2007-04-10 15:01:22 UTC (rev 20637) +++ haiku/trunk/src/apps/abouthaiku/AboutHaiku.cpp 2007-04-10 16:20:40 UTC (rev 20638) @@ -364,6 +364,7 @@ "Ryan Leavengood\n" "Michael Lotz\n" "Niels Reedijk\n" + "Hugo Santos\n" "Bryan Varner\n" "\n"); From hugosantos at mail.berlios.de Tue Apr 10 18:48:11 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Tue, 10 Apr 2007 18:48:11 +0200 Subject: [Haiku-commits] r20639 - in haiku/trunk/src/add-ons/kernel/network: protocols/tcp stack Message-ID: <200704101648.l3AGmBEg020587@sheep.berlios.de> Author: hugosantos Date: 2007-04-10 18:47:47 +0200 (Tue, 10 Apr 2007) New Revision: 20639 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20639&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/EndpointManager.cpp haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h haiku/trunk/src/add-ons/kernel/network/stack/net_buffer.cpp Log: even more TCP fixage. - don't try to remove spawned sockets from Endpoints hashtable. - return B_WOULD_BLOCK (EAGAIN) when we time out in acquire_sem(). - use B_RELEASE_IF_WAITING_ONLY in the TCP WaitList. - fixed a off by one issue in ReadData() which could result in more than needed iterations (and waiting). - implemented prepending new buffers to a net_buffer. Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/EndpointManager.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/EndpointManager.cpp 2007-04-10 16:20:40 UTC (rev 20638) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/EndpointManager.cpp 2007-04-10 16:47:47 UTC (rev 20639) @@ -319,25 +319,27 @@ RecursiveLocker locker(&fLock); - TCPEndpoint *other = _LookupEndpoint(gAddressModule->get_port( - (sockaddr *)&endpoint->socket->address)); - if (other != endpoint) { - // remove endpoint from the list of endpoints with the same port - while (other != NULL && other->fEndpointNextWithSamePort != endpoint) { - other = other->fEndpointNextWithSamePort; - } + if (!endpoint->fSpawned) { + TCPEndpoint *other = _LookupEndpoint(gAddressModule->get_port( + (sockaddr *)&endpoint->socket->address)); + if (other != endpoint) { + // remove endpoint from the list of endpoints with the same port + while (other != NULL && other->fEndpointNextWithSamePort != endpoint) { + other = other->fEndpointNextWithSamePort; + } - if (other != NULL) - other->fEndpointNextWithSamePort = endpoint->fEndpointNextWithSamePort; - else - panic("bound endpoint %p not in hash!", endpoint); - } else { - // we need to replace the first endpoint in the list - hash_remove(fEndpointHash, endpoint); + if (other != NULL) + other->fEndpointNextWithSamePort = endpoint->fEndpointNextWithSamePort; + else + panic("bound endpoint %p not in hash!", endpoint); + } else { + // we need to replace the first endpoint in the list + hash_remove(fEndpointHash, endpoint); - other = endpoint->fEndpointNextWithSamePort; - if (other != NULL) - hash_insert(fEndpointHash, other); + other = endpoint->fEndpointNextWithSamePort; + if (other != NULL) + hash_insert(fEndpointHash, other); + } } endpoint->fEndpointNextWithSamePort = NULL; Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-10 16:20:40 UTC (rev 20638) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-10 16:47:47 UTC (rev 20639) @@ -49,8 +49,9 @@ //#define TRACE_TCP #ifdef TRACE_TCP -// the space after 'this' is important in order for this to work with cpp 2.95 -# define TRACE(format, args...) dprintf("TCP:%p:" format "\n", this , ##args) +// the space before ', ##args' is important in order for this to work with cpp 2.95 +# define TRACE(format, args...) dprintf("TCP [%llu] %p (%12s) " format "\n", \ + system_time(), this, name_for_state(fState) , ##args) #else # define TRACE(args...) do { } while (0) #endif @@ -79,8 +80,17 @@ } +static inline status_t +posix_error(status_t error) +{ + if (error == B_TIMED_OUT) + return B_WOULD_BLOCK; + + return error; +} + + WaitList::WaitList(const char *name) - : fWaiting(0) { fSem = create_sem(0, name); } @@ -100,15 +110,13 @@ status_t -WaitList::Wait(RecursiveLocker &locker, bigtime_t timeout) +WaitList::Wait(RecursiveLocker &locker, bigtime_t timeout, bool wakeNext) { - // this function is called with `locker' held. - fWaiting++; locker.Unlock(); - status_t status = acquire_sem_etc(fSem, 1, B_ABSOLUTE_TIMEOUT | - B_CAN_INTERRUPT, timeout); + status_t status = acquire_sem_etc(fSem, 1, B_ABSOLUTE_TIMEOUT + | B_CAN_INTERRUPT, timeout); locker.Lock(); - if (status == B_OK) + if (wakeNext && status == B_OK) Signal(); return status; } @@ -117,14 +125,8 @@ void WaitList::Signal() { - // the same locker used with Wait() must be held - // when calling this function. - - if (fWaiting == 0) - return; - - fWaiting--; - release_sem_etc(fSem, 1, B_DO_NOT_RESCHEDULE); + release_sem_etc(fSem, 1, B_DO_NOT_RESCHEDULE + | B_RELEASE_IF_WAITING_ONLY); } @@ -152,7 +154,8 @@ fRoundTripTime(TCP_INITIAL_RTT), fState(CLOSED), fFlags(0), //FLAG_OPTION_WINDOW_SHIFT), - fError(B_OK) + fError(B_OK), + fSpawned(false) { //gStackModule->init_timer(&fTimer, _TimeWait, this); @@ -228,7 +231,7 @@ if (status != B_OK) return status; - TRACE("Close(): Entering state %s", name_for_state(fState)); + TRACE("Close() after Shutdown()"); if (socket->options & SO_LINGER) { TRACE("Close(): Lingering for %i secs", socket->linger); @@ -277,13 +280,8 @@ TRACE("Connect() on address %s", AddressString(gDomain, address, true).Data()); - if (address->sa_family != AF_INET) - return EAFNOSUPPORT; - RecursiveLocker locker(&fLock); - TRACE(" Connect(): in state %s", name_for_state(fState)); - // Can only call connect() from CLOSED or LISTEN states // otherwise endpoint is considered already connected if (fState == LISTEN) { @@ -355,7 +353,7 @@ TRACE(" Connect(): Connection complete: %s", strerror(status)); - return status; + return posix_error(status); } @@ -506,7 +504,7 @@ while (fSendQueue.Free() < chunk->size) { status_t status = fSendList.Wait(lock, timeout); if (status < B_OK) - return status; + return posix_error(status); } // TODO: check state! @@ -569,7 +567,7 @@ // we need to wait until the connection becomes established status_t status = fSendList.Wait(locker, timeout); if (status < B_OK) - return status; + return posix_error(status); } } @@ -589,8 +587,8 @@ return B_OK; } - if (fReceiveQueue.Available() > dataNeeded || - (fReceiveQueue.PushedData() > 0 + if (fReceiveQueue.Available() >= dataNeeded || + ((fReceiveQueue.PushedData() > 0) && (fReceiveQueue.PushedData() >= fReceiveQueue.Available()))) break; @@ -603,7 +601,7 @@ if (flags & MSG_DONTWAIT) return B_WOULD_BLOCK; - status_t status = fReceiveList.Wait(locker, timeout); + status_t status = fReceiveList.Wait(locker, timeout, false); if (status < B_OK) { // The Open Group base specification mentions that EINTR should be // returned if the recv() is interrupted before _any data_ is @@ -613,7 +611,7 @@ && fReceiveQueue.Available() > 0) break; - return status; + return posix_error(status); } } @@ -707,8 +705,8 @@ int32 TCPEndpoint::ListenReceive(tcp_segment_header &segment, net_buffer *buffer) { - TRACE("ListenReceive(): Connection in state %s received packet %p (%lu bytes) with flags 0x%x, seq %lu, ack %lu!", - name_for_state(fState), buffer, buffer->size, segment.flags, segment.sequence, segment.acknowledge); + TRACE("ListenReceive(): packet %p (%lu bytes) with flags 0x%x, seq %lu, ack %lu!", + buffer, buffer->size, segment.flags, segment.sequence, segment.acknowledge); // Essentially, we accept only TCP_FLAG_SYNCHRONIZE in this state, // but the error behaviour differs @@ -733,6 +731,8 @@ TCPEndpoint *endpoint = (TCPEndpoint *)newSocket->first_protocol; + endpoint->fSpawned = true; + // TODO: proper error handling! endpoint->fRoute = gDatalinkModule->get_route(gDomain, @@ -796,6 +796,9 @@ int32 TCPEndpoint::SynchronizeSentReceive(tcp_segment_header &segment, net_buffer *buffer) { + TRACE("SynchronizeReceive(): packet %p (%lu bytes) with flags 0x%x, seq %lu, ack %lu!", + buffer, buffer->size, segment.flags, segment.sequence, segment.acknowledge); + if ((segment.flags & TCP_FLAG_ACKNOWLEDGE) != 0 && (fInitialSendSequence >= segment.acknowledge || fSendMax < segment.acknowledge)) @@ -855,8 +858,8 @@ int32 TCPEndpoint::Receive(tcp_segment_header &segment, net_buffer *buffer) { - TRACE("Receive(): Connection in state %s received packet %p (%lu bytes) with flags 0x%x, seq %lu, ack %lu!", - name_for_state(fState), buffer, buffer->size, segment.flags, segment.sequence, segment.acknowledge); + TRACE("Receive(): packet %p (%lu bytes) with flags 0x%x, seq %lu, ack %lu!", + buffer, buffer->size, segment.flags, segment.sequence, segment.acknowledge); // TODO: rethink locking! @@ -1146,7 +1149,7 @@ if (buffer->size > 0 || (segment.flags & TCP_FLAG_SYNCHRONIZE) != 0) action |= ACKNOWLEDGE; - TRACE("Receive():Entering state %s, segment action %ld", name_for_state(fState), action); + TRACE("Receive() Action %ld", action); return action; } Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h 2007-04-10 16:20:40 UTC (rev 20638) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h 2007-04-10 16:47:47 UTC (rev 20639) @@ -30,12 +30,11 @@ status_t InitCheck() const; - status_t Wait(RecursiveLocker &, bigtime_t timeout); + status_t Wait(RecursiveLocker &, bigtime_t timeout, bool wakeNext = true); void Signal(); private: sem_id fSem; - int32 fWaiting; }; @@ -143,6 +142,8 @@ uint32 fFlags; status_t fError; + bool fSpawned; + // timer net_timer fRetransmitTimer; net_timer fPersistTimer; Modified: haiku/trunk/src/add-ons/kernel/network/stack/net_buffer.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/net_buffer.cpp 2007-04-10 16:20:40 UTC (rev 20638) +++ haiku/trunk/src/add-ons/kernel/network/stack/net_buffer.cpp 2007-04-10 16:47:47 UTC (rev 20639) @@ -632,13 +632,47 @@ if (node->header_space < size) { // we need to prepend a new buffer - // TODO: implement me! - panic("prepending buffer not implemented\n"); + size_t bytesLeft = size; + do { + if (node->header_space == 0) { + size_t headerSpace = BUFFER_SIZE - sizeof(data_header); + // no more space, need another data node + data_header *header = create_data_header(headerSpace); + if (header == NULL) { + // TODO: free up headers we already allocated! + return B_NO_MEMORY; + } + data_node *previous = node; + node = (data_node *)add_data_node(header); + + init_data_node(node, headerSpace); + node->header_space = header->data_space; + header->first_node = node; + + list_insert_item_before(&buffer->buffers, previous, node); + } else { + size_t willConsume = min_c(size, node->header_space); + + node->header_space -= willConsume; + node->start -= willConsume; + node->used += willConsume; + bytesLeft -= willConsume; + } + } while (bytesLeft > 0); + + size_t offset = 0; + for (node = (data_node *)list_get_first_item(&buffer->buffers); + node != NULL; node = (data_node *) + list_get_next_item(&buffer->buffers, node)) { + node->offset = offset; + offset += node->used; + } + if (_contiguousBuffer) *_contiguousBuffer = NULL; - return B_ERROR; + return B_OK; } // the data fits into this buffer From laplace at mail.berlios.de Tue Apr 10 18:51:10 2007 From: laplace at mail.berlios.de (laplace at BerliOS) Date: Tue, 10 Apr 2007 18:51:10 +0200 Subject: [Haiku-commits] r20640 - haiku/trunk/src/apps/abouthaiku Message-ID: <200704101651.l3AGpAj8024066@sheep.berlios.de> Author: laplace Date: 2007-04-10 18:51:09 +0200 (Tue, 10 Apr 2007) New Revision: 20640 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20640&view=rev Modified: haiku/trunk/src/apps/abouthaiku/AboutHaiku.cpp Log: Added Hartmut Reh to list of contributors. He contributed to the printing sub-system with ideas, implementations and testing. Modified: haiku/trunk/src/apps/abouthaiku/AboutHaiku.cpp =================================================================== --- haiku/trunk/src/apps/abouthaiku/AboutHaiku.cpp 2007-04-10 16:47:47 UTC (rev 20639) +++ haiku/trunk/src/apps/abouthaiku/AboutHaiku.cpp 2007-04-10 16:51:09 UTC (rev 20640) @@ -409,6 +409,7 @@ "Michael Paine\n" "Michael Phipps\n" "Jeremy Rand\n" + "Hartmut Reh\n" "David Reid\n" "Daniel Reinhold\n" "Fran?ois Revol\n" From hugosantos at gmail.com Tue Apr 10 18:51:29 2007 From: hugosantos at gmail.com (Hugo Santos) Date: Tue, 10 Apr 2007 17:51:29 +0100 Subject: [Haiku-commits] r20638 - haiku/trunk/src/apps/abouthaiku In-Reply-To: <200704101620.l3AGKeVr021331@sheep.berlios.de> References: <200704101620.l3AGKeVr021331@sheep.berlios.de> Message-ID: <9c46321e0704100951u788de528v5f2770a358af490c@mail.gmail.com> Hi Stephan, Thank you, it was unexpected. I hope i can continue to help the project. Thanks again, Hugo On 4/10/07, stippi at BerliOS wrote: > Author: stippi > Date: 2007-04-10 18:20:40 +0200 (Tue, 10 Apr 2007) > New Revision: 20638 > ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20638&view=rev > > Modified: > haiku/trunk/src/apps/abouthaiku/AboutHaiku.cpp > Log: > added Hugo Santos to the list of developers > > > Modified: haiku/trunk/src/apps/abouthaiku/AboutHaiku.cpp > =================================================================== > --- haiku/trunk/src/apps/abouthaiku/AboutHaiku.cpp 2007-04-10 15:01:22 UTC (rev 20637) > +++ haiku/trunk/src/apps/abouthaiku/AboutHaiku.cpp 2007-04-10 16:20:40 UTC (rev 20638) > @@ -364,6 +364,7 @@ > "Ryan Leavengood\n" > "Michael Lotz\n" > "Niels Reedijk\n" > + "Hugo Santos\n" > "Bryan Varner\n" > "\n"); > > > _______________________________________________ > Haiku-commits mailing list > Haiku-commits at lists.berlios.de > https://lists.berlios.de/mailman/listinfo/haiku-commits > From hugosantos at gmail.com Tue Apr 10 18:55:12 2007 From: hugosantos at gmail.com (Hugo Santos) Date: Tue, 10 Apr 2007 17:55:12 +0100 Subject: [Haiku-commits] r20639 - in haiku/trunk/src/add-ons/kernel/network: protocols/tcp stack In-Reply-To: <200704101648.l3AGmBEg020587@sheep.berlios.de> References: <200704101648.l3AGmBEg020587@sheep.berlios.de> Message-ID: <9c46321e0704100955w77a786aagf122150e91527694@mail.gmail.com> Axel, can you have a look at the adding new buffers code in prepend_size please? Just to make sure it makes sense from a data_node/data_header POV. (Ignore the fact that the else branches.. i'll fix that in a subsequent commit). Thanks, Hugo On 4/10/07, hugosantos at mail.berlios.de wrote: > Author: hugosantos > Date: 2007-04-10 18:47:47 +0200 (Tue, 10 Apr 2007) > New Revision: 20639 > ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20639&view=rev > > Modified: > haiku/trunk/src/add-ons/kernel/network/protocols/tcp/EndpointManager.cpp > haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp > haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h > haiku/trunk/src/add-ons/kernel/network/stack/net_buffer.cpp > Log: > even more TCP fixage. > > - don't try to remove spawned sockets from Endpoints hashtable. > - return B_WOULD_BLOCK (EAGAIN) when we time out in acquire_sem(). > - use B_RELEASE_IF_WAITING_ONLY in the TCP WaitList. > - fixed a off by one issue in ReadData() which could result in more than needed iterations (and waiting). > - implemented prepending new buffers to a net_buffer. > > > Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/EndpointManager.cpp > =================================================================== > --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/EndpointManager.cpp 2007-04-10 16:20:40 UTC (rev 20638) > +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/EndpointManager.cpp 2007-04-10 16:47:47 UTC (rev 20639) > @@ -319,25 +319,27 @@ > > RecursiveLocker locker(&fLock); > > - TCPEndpoint *other = _LookupEndpoint(gAddressModule->get_port( > - (sockaddr *)&endpoint->socket->address)); > - if (other != endpoint) { > - // remove endpoint from the list of endpoints with the same port > - while (other != NULL && other->fEndpointNextWithSamePort != endpoint) { > - other = other->fEndpointNextWithSamePort; > - } > + if (!endpoint->fSpawned) { > + TCPEndpoint *other = _LookupEndpoint(gAddressModule->get_port( > + (sockaddr *)&endpoint->socket->address)); > + if (other != endpoint) { > + // remove endpoint from the list of endpoints with the same port > + while (other != NULL && other->fEndpointNextWithSamePort != endpoint) { > + other = other->fEndpointNextWithSamePort; > + } > > - if (other != NULL) > - other->fEndpointNextWithSamePort = endpoint->fEndpointNextWithSamePort; > - else > - panic("bound endpoint %p not in hash!", endpoint); > - } else { > - // we need to replace the first endpoint in the list > - hash_remove(fEndpointHash, endpoint); > + if (other != NULL) > + other->fEndpointNextWithSamePort = endpoint->fEndpointNextWithSamePort; > + else > + panic("bound endpoint %p not in hash!", endpoint); > + } else { > + // we need to replace the first endpoint in the list > + hash_remove(fEndpointHash, endpoint); > > - other = endpoint->fEndpointNextWithSamePort; > - if (other != NULL) > - hash_insert(fEndpointHash, other); > + other = endpoint->fEndpointNextWithSamePort; > + if (other != NULL) > + hash_insert(fEndpointHash, other); > + } > } > > endpoint->fEndpointNextWithSamePort = NULL; > > Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp > =================================================================== > --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-10 16:20:40 UTC (rev 20638) > +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-10 16:47:47 UTC (rev 20639) > @@ -49,8 +49,9 @@ > //#define TRACE_TCP > > #ifdef TRACE_TCP > -// the space after 'this' is important in order for this to work with cpp 2.95 > -# define TRACE(format, args...) dprintf("TCP:%p:" format "\n", this , ##args) > +// the space before ', ##args' is important in order for this to work with cpp 2.95 > +# define TRACE(format, args...) dprintf("TCP [%llu] %p (%12s) " format "\n", \ > + system_time(), this, name_for_state(fState) , ##args) > #else > # define TRACE(args...) do { } while (0) > #endif > @@ -79,8 +80,17 @@ > } > > > +static inline status_t > +posix_error(status_t error) > +{ > + if (error == B_TIMED_OUT) > + return B_WOULD_BLOCK; > + > + return error; > +} > + > + > WaitList::WaitList(const char *name) > - : fWaiting(0) > { > fSem = create_sem(0, name); > } > @@ -100,15 +110,13 @@ > > > status_t > -WaitList::Wait(RecursiveLocker &locker, bigtime_t timeout) > +WaitList::Wait(RecursiveLocker &locker, bigtime_t timeout, bool wakeNext) > { > - // this function is called with `locker' held. > - fWaiting++; > locker.Unlock(); > - status_t status = acquire_sem_etc(fSem, 1, B_ABSOLUTE_TIMEOUT | > - B_CAN_INTERRUPT, timeout); > + status_t status = acquire_sem_etc(fSem, 1, B_ABSOLUTE_TIMEOUT > + | B_CAN_INTERRUPT, timeout); > locker.Lock(); > - if (status == B_OK) > + if (wakeNext && status == B_OK) > Signal(); > return status; > } > @@ -117,14 +125,8 @@ > void > WaitList::Signal() > { > - // the same locker used with Wait() must be held > - // when calling this function. > - > - if (fWaiting == 0) > - return; > - > - fWaiting--; > - release_sem_etc(fSem, 1, B_DO_NOT_RESCHEDULE); > + release_sem_etc(fSem, 1, B_DO_NOT_RESCHEDULE > + | B_RELEASE_IF_WAITING_ONLY); > } > > > @@ -152,7 +154,8 @@ > fRoundTripTime(TCP_INITIAL_RTT), > fState(CLOSED), > fFlags(0), //FLAG_OPTION_WINDOW_SHIFT), > - fError(B_OK) > + fError(B_OK), > + fSpawned(false) > { > //gStackModule->init_timer(&fTimer, _TimeWait, this); > > @@ -228,7 +231,7 @@ > if (status != B_OK) > return status; > > - TRACE("Close(): Entering state %s", name_for_state(fState)); > + TRACE("Close() after Shutdown()"); > > if (socket->options & SO_LINGER) { > TRACE("Close(): Lingering for %i secs", socket->linger); > @@ -277,13 +280,8 @@ > TRACE("Connect() on address %s", > AddressString(gDomain, address, true).Data()); > > - if (address->sa_family != AF_INET) > - return EAFNOSUPPORT; > - > RecursiveLocker locker(&fLock); > > - TRACE(" Connect(): in state %s", name_for_state(fState)); > - > // Can only call connect() from CLOSED or LISTEN states > // otherwise endpoint is considered already connected > if (fState == LISTEN) { > @@ -355,7 +353,7 @@ > > TRACE(" Connect(): Connection complete: %s", strerror(status)); > > - return status; > + return posix_error(status); > } > > > @@ -506,7 +504,7 @@ > while (fSendQueue.Free() < chunk->size) { > status_t status = fSendList.Wait(lock, timeout); > if (status < B_OK) > - return status; > + return posix_error(status); > } > > // TODO: check state! > @@ -569,7 +567,7 @@ > // we need to wait until the connection becomes established > status_t status = fSendList.Wait(locker, timeout); > if (status < B_OK) > - return status; > + return posix_error(status); > } > } > > @@ -589,8 +587,8 @@ > return B_OK; > } > > - if (fReceiveQueue.Available() > dataNeeded || > - (fReceiveQueue.PushedData() > 0 > + if (fReceiveQueue.Available() >= dataNeeded || > + ((fReceiveQueue.PushedData() > 0) > && (fReceiveQueue.PushedData() >= fReceiveQueue.Available()))) > break; > > @@ -603,7 +601,7 @@ > if (flags & MSG_DONTWAIT) > return B_WOULD_BLOCK; > > - status_t status = fReceiveList.Wait(locker, timeout); > + status_t status = fReceiveList.Wait(locker, timeout, false); > if (status < B_OK) { > // The Open Group base specification mentions that EINTR should be > // returned if the recv() is interrupted before _any data_ is > @@ -613,7 +611,7 @@ > && fReceiveQueue.Available() > 0) > break; > > - return status; > + return posix_error(status); > } > } > > @@ -707,8 +705,8 @@ > int32 > TCPEndpoint::ListenReceive(tcp_segment_header &segment, net_buffer *buffer) > { > - TRACE("ListenReceive(): Connection in state %s received packet %p (%lu bytes) with flags 0x%x, seq %lu, ack %lu!", > - name_for_state(fState), buffer, buffer->size, segment.flags, segment.sequence, segment.acknowledge); > + TRACE("ListenReceive(): packet %p (%lu bytes) with flags 0x%x, seq %lu, ack %lu!", > + buffer, buffer->size, segment.flags, segment.sequence, segment.acknowledge); > > // Essentially, we accept only TCP_FLAG_SYNCHRONIZE in this state, > // but the error behaviour differs > @@ -733,6 +731,8 @@ > > TCPEndpoint *endpoint = (TCPEndpoint *)newSocket->first_protocol; > > + endpoint->fSpawned = true; > + > // TODO: proper error handling! > > endpoint->fRoute = gDatalinkModule->get_route(gDomain, > @@ -796,6 +796,9 @@ > int32 > TCPEndpoint::SynchronizeSentReceive(tcp_segment_header &segment, net_buffer *buffer) > { > + TRACE("SynchronizeReceive(): packet %p (%lu bytes) with flags 0x%x, seq %lu, ack %lu!", > + buffer, buffer->size, segment.flags, segment.sequence, segment.acknowledge); > + > if ((segment.flags & TCP_FLAG_ACKNOWLEDGE) != 0 > && (fInitialSendSequence >= segment.acknowledge > || fSendMax < segment.acknowledge)) > @@ -855,8 +858,8 @@ > int32 > TCPEndpoint::Receive(tcp_segment_header &segment, net_buffer *buffer) > { > - TRACE("Receive(): Connection in state %s received packet %p (%lu bytes) with flags 0x%x, seq %lu, ack %lu!", > - name_for_state(fState), buffer, buffer->size, segment.flags, segment.sequence, segment.acknowledge); > + TRACE("Receive(): packet %p (%lu bytes) with flags 0x%x, seq %lu, ack %lu!", > + buffer, buffer->size, segment.flags, segment.sequence, segment.acknowledge); > > // TODO: rethink locking! > > @@ -1146,7 +1149,7 @@ > if (buffer->size > 0 || (segment.flags & TCP_FLAG_SYNCHRONIZE) != 0) > action |= ACKNOWLEDGE; > > - TRACE("Receive():Entering state %s, segment action %ld", name_for_state(fState), action); > + TRACE("Receive() Action %ld", action); > > return action; > } > > Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h > =================================================================== > --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h 2007-04-10 16:20:40 UTC (rev 20638) > +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h 2007-04-10 16:47:47 UTC (rev 20639) > @@ -30,12 +30,11 @@ > > status_t InitCheck() const; > > - status_t Wait(RecursiveLocker &, bigtime_t timeout); > + status_t Wait(RecursiveLocker &, bigtime_t timeout, bool wakeNext = true); > void Signal(); > > private: > sem_id fSem; > - int32 fWaiting; > }; > > > @@ -143,6 +142,8 @@ > uint32 fFlags; > status_t fError; > > + bool fSpawned; > + > // timer > net_timer fRetransmitTimer; > net_timer fPersistTimer; > > Modified: haiku/trunk/src/add-ons/kernel/network/stack/net_buffer.cpp > =================================================================== > --- haiku/trunk/src/add-ons/kernel/network/stack/net_buffer.cpp 2007-04-10 16:20:40 UTC (rev 20638) > +++ haiku/trunk/src/add-ons/kernel/network/stack/net_buffer.cpp 2007-04-10 16:47:47 UTC (rev 20639) > @@ -632,13 +632,47 @@ > if (node->header_space < size) { > // we need to prepend a new buffer > > - // TODO: implement me! > - panic("prepending buffer not implemented\n"); > + size_t bytesLeft = size; > + do { > + if (node->header_space == 0) { > + size_t headerSpace = BUFFER_SIZE - sizeof(data_header); > + // no more space, need another data node > + data_header *header = create_data_header(headerSpace); > + if (header == NULL) { > + // TODO: free up headers we already allocated! > + return B_NO_MEMORY; > + } > > + data_node *previous = node; > + node = (data_node *)add_data_node(header); > + > + init_data_node(node, headerSpace); > + node->header_space = header->data_space; > + header->first_node = node; > + > + list_insert_item_before(&buffer->buffers, previous, node); > + } else { > + size_t willConsume = min_c(size, node->header_space); > + > + node->header_space -= willConsume; > + node->start -= willConsume; > + node->used += willConsume; > + bytesLeft -= willConsume; > + } > + } while (bytesLeft > 0); > + > + size_t offset = 0; > + for (node = (data_node *)list_get_first_item(&buffer->buffers); > + node != NULL; node = (data_node *) > + list_get_next_item(&buffer->buffers, node)) { > + node->offset = offset; > + offset += node->used; > + } > + > if (_contiguousBuffer) > *_contiguousBuffer = NULL; > > - return B_ERROR; > + return B_OK; > } > > // the data fits into this buffer > > _______________________________________________ > Haiku-commits mailing list > Haiku-commits at lists.berlios.de > https://lists.berlios.de/mailman/listinfo/haiku-commits > From hugosantos at mail.berlios.de Tue Apr 10 19:00:43 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Tue, 10 Apr 2007 19:00:43 +0200 Subject: [Haiku-commits] r20641 - haiku/trunk/src/add-ons/kernel/network/stack Message-ID: <200704101700.l3AH0hC4031730@sheep.berlios.de> Author: hugosantos Date: 2007-04-10 19:00:22 +0200 (Tue, 10 Apr 2007) New Revision: 20641 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20641&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/stack/net_buffer.cpp Log: eat header space in each iteration in prepend_size(). Modified: haiku/trunk/src/add-ons/kernel/network/stack/net_buffer.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/net_buffer.cpp 2007-04-10 16:51:09 UTC (rev 20640) +++ haiku/trunk/src/add-ons/kernel/network/stack/net_buffer.cpp 2007-04-10 17:00:22 UTC (rev 20641) @@ -651,14 +651,14 @@ header->first_node = node; list_insert_item_before(&buffer->buffers, previous, node); - } else { - size_t willConsume = min_c(size, node->header_space); + } - node->header_space -= willConsume; - node->start -= willConsume; - node->used += willConsume; - bytesLeft -= willConsume; - } + size_t willConsume = min_c(bytesLeft, node->header_space); + + node->header_space -= willConsume; + node->start -= willConsume; + node->used += willConsume; + bytesLeft -= willConsume; } while (bytesLeft > 0); size_t offset = 0; From hugosantos at mail.berlios.de Tue Apr 10 20:27:56 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Tue, 10 Apr 2007 20:27:56 +0200 Subject: [Haiku-commits] r20642 - in haiku/trunk/src/add-ons/kernel/network: protocols/tcp stack Message-ID: <200704101827.l3AIRu2t011542@sheep.berlios.de> Author: hugosantos Date: 2007-04-10 20:27:41 +0200 (Tue, 10 Apr 2007) New Revision: 20642 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20642&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp haiku/trunk/src/add-ons/kernel/network/stack/net_buffer.cpp Log: update buffer size when prepending buffers. Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-10 17:00:22 UTC (rev 20641) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-10 18:27:41 UTC (rev 20642) @@ -796,7 +796,7 @@ int32 TCPEndpoint::SynchronizeSentReceive(tcp_segment_header &segment, net_buffer *buffer) { - TRACE("SynchronizeReceive(): packet %p (%lu bytes) with flags 0x%x, seq %lu, ack %lu!", + TRACE("SynchronizeSentReceive(): packet %p (%lu bytes) with flags 0x%x, seq %lu, ack %lu!", buffer, buffer->size, segment.flags, segment.sequence, segment.acknowledge); if ((segment.flags & TCP_FLAG_ACKNOWLEDGE) != 0 @@ -1306,10 +1306,6 @@ gAddressModule->set_to((sockaddr *)&buffer->source, (sockaddr *)&socket->address); gAddressModule->set_to((sockaddr *)&buffer->destination, (sockaddr *)&socket->peer); - TRACE("SendQueued() flags %x, buffer %p, size %lu, from address %s to %s", - segment.flags, buffer, buffer->size, - AddressString(gDomain, (sockaddr *)&buffer->source, true).Data(), - AddressString(gDomain, (sockaddr *)&buffer->destination, true).Data()); uint32 size = buffer->size; if (length > 0 && fSendNext + segmentLength == fSendQueue.LastSequence()) { @@ -1329,6 +1325,11 @@ } } + TRACE("SendQueued() flags %x, buffer %p, size %lu, from address %s to %s", + segment.flags, buffer, buffer->size, + AddressString(gDomain, (sockaddr *)&buffer->source, true).Data(), + AddressString(gDomain, (sockaddr *)&buffer->destination, true).Data()); + status = add_tcp_header(segment, buffer); if (status != B_OK) { gBufferModule->free(buffer); Modified: haiku/trunk/src/add-ons/kernel/network/stack/net_buffer.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/net_buffer.cpp 2007-04-10 17:00:22 UTC (rev 20641) +++ haiku/trunk/src/add-ons/kernel/network/stack/net_buffer.cpp 2007-04-10 18:27:41 UTC (rev 20642) @@ -626,17 +626,17 @@ net_buffer_private *buffer = (net_buffer_private *)_buffer; data_node *node = (data_node *)list_get_first_item(&buffer->buffers); - TRACE(("prepend_size(buffer %p, size %ld)\n", buffer, size)); + TRACE(("prepend_size(buffer %p, size %ld) [has %ld]\n", buffer, size, + node->header_space)); //dump_buffer(buffer); if (node->header_space < size) { - // we need to prepend a new buffer + // we need to prepend new buffers size_t bytesLeft = size; do { if (node->header_space == 0) { size_t headerSpace = BUFFER_SIZE - sizeof(data_header); - // no more space, need another data node data_header *header = create_data_header(headerSpace); if (header == NULL) { // TODO: free up headers we already allocated! @@ -671,21 +671,19 @@ if (_contiguousBuffer) *_contiguousBuffer = NULL; + } else { + // the data fits into this buffer + node->header_space -= size; + node->start -= size; + node->used += size; - return B_OK; - } + if (_contiguousBuffer) + *_contiguousBuffer = node->start; - // the data fits into this buffer - node->header_space -= size; - node->start -= size; - node->used += size; - - if (_contiguousBuffer) - *_contiguousBuffer = node->start; - - // adjust offset of following nodes - while ((node = (data_node *)list_get_next_item(&buffer->buffers, node)) != NULL) { - node->offset += size; + // adjust offset of following nodes + while ((node = (data_node *)list_get_next_item(&buffer->buffers, node)) != NULL) { + node->offset += size; + } } buffer->size += size; From hugosantos at mail.berlios.de Tue Apr 10 21:04:38 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Tue, 10 Apr 2007 21:04:38 +0200 Subject: [Haiku-commits] r20643 - in haiku/trunk: headers/private/net src/add-ons/kernel/network/protocols/tcp Message-ID: <200704101904.l3AJ4cnx013827@sheep.berlios.de> Author: hugosantos Date: 2007-04-10 21:04:13 +0200 (Tue, 10 Apr 2007) New Revision: 20643 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20643&view=rev Modified: haiku/trunk/headers/private/net/NetBufferUtilities.h haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.cpp Log: fixed add_tcp_header() as it wasn't considering the possibility that prepending data would not result in a contiguous buffer. This would result in wrong checksums for apparent no reason. Modified: haiku/trunk/headers/private/net/NetBufferUtilities.h =================================================================== --- haiku/trunk/headers/private/net/NetBufferUtilities.h 2007-04-10 18:27:41 UTC (rev 20642) +++ haiku/trunk/headers/private/net/NetBufferUtilities.h 2007-04-10 19:04:13 UTC (rev 20643) @@ -81,21 +81,24 @@ Type fDataBuffer; }; -//! A class to add a header to a buffer -template class NetBufferPrepend { +//! A class to access a header safely across data node boundaries +template +class NetBufferSafeHeader { public: - NetBufferPrepend(net_buffer *buffer, size_t size = 0) + NetBufferSafeHeader(net_buffer *buffer) : - fBuffer(buffer), - fData(NULL) + fBuffer(buffer) { - if (size == 0) - size = sizeof(Type); - - fStatus = Module::Get()->prepend_size(buffer, size, (void **)&fData); + fStatus = Module::Get()->direct_access(fBuffer, 0, + sizeof(Type), (void **)&fData); + if (fStatus != B_OK) { + fData = NULL; + fStatus = Module::Get()->read(fBuffer, 0, &fDataBuffer, + sizeof(Type)); + } } - ~NetBufferPrepend() + ~NetBufferSafeHeader() { if (fBuffer != NULL) Detach(); @@ -116,8 +119,6 @@ return fDataBuffer; } - // TODO: I'm not sure it's a good idea to have Detach() routines - // in NetBufferHeader and here with such a different outcome... void Detach() { @@ -126,11 +127,29 @@ fBuffer = NULL; } - private: + protected: + NetBufferSafeHeader() {} + net_buffer *fBuffer; status_t fStatus; Type *fData; Type fDataBuffer; }; +//! A class to add a header to a buffer +template +class NetBufferPrepend : public NetBufferSafeHeader { + public: + NetBufferPrepend(net_buffer *buffer, size_t size = 0) + { + fBuffer = buffer; + fData = NULL; + + if (size == 0) + size = sizeof(Type); + + fStatus = Module::Get()->prepend_size(buffer, size, (void **)&fData); + } +}; + #endif // NET_BUFFER_UTILITIES_H Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.cpp 2007-04-10 18:27:41 UTC (rev 20642) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.cpp 2007-04-10 19:04:13 UTC (rev 20643) @@ -148,6 +148,10 @@ header.urgent_offset = 0; // TODO: urgent pointer not yet supported + // we must detach before calculating the checksum as we may + // not have a contiguous buffer. + bufferHeader.Detach(); + if (optionsLength > 0) gBufferModule->write(buffer, sizeof(tcp_header), optionsBuffer, optionsLength); @@ -162,8 +166,11 @@ << (uint16)htons(IPPROTO_TCP) << (uint16)htons(buffer->size) << Checksum::BufferHelper(buffer, gBufferModule); - header.checksum = checksum; + // we are pretty sure the header is there. + NetBufferSafeHeader headerRef(buffer); + headerRef.Data().checksum = checksum; + return B_OK; } From axeld at mail.berlios.de Tue Apr 10 23:12:14 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Tue, 10 Apr 2007 23:12:14 +0200 Subject: [Haiku-commits] r20644 - haiku/trunk/src/add-ons/translators/raw Message-ID: <200704102112.l3ALCEau024406@sheep.berlios.de> Author: axeld Date: 2007-04-10 23:12:12 +0200 (Tue, 10 Apr 2007) New Revision: 20644 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20644&view=rev Modified: haiku/trunk/src/add-ons/translators/raw/RAW.cpp haiku/trunk/src/add-ons/translators/raw/RAW.h haiku/trunk/src/add-ons/translators/raw/RAWTranslator.cpp haiku/trunk/src/add-ons/translators/raw/RAWTranslator.h Log: Implemented a progress monitor - I'll implement support for this in ShowImage next. Modified: haiku/trunk/src/add-ons/translators/raw/RAW.cpp =================================================================== --- haiku/trunk/src/add-ons/translators/raw/RAW.cpp 2007-04-10 19:04:13 UTC (rev 20643) +++ haiku/trunk/src/add-ons/translators/raw/RAW.cpp 2007-04-10 21:12:12 UTC (rev 20644) @@ -93,6 +93,20 @@ } +#if 0 +void +dump_to_disk(void* data, size_t length) +{ + FILE* file = fopen("/tmp/RAW.out", "wb"); + if (file == NULL) + return; + + fwrite(data, length, 1, file); + fclose(file); +} +#endif + + // #pragma mark - @@ -105,7 +119,7 @@ fDNGVersion(0), fIsTIFF(false), fThreshold(0), - fHalfSize(true), + fHalfSize(false), fUseCameraWhiteBalance(true), fUseAutoWhiteBalance(true), fRawColor(true), @@ -126,7 +140,8 @@ fDecodeLeaf(0), fDecodeBitsZeroAfterMax(false), fFilters(~0), - fEXIFOffset(-1) + fEXIFOffset(-1), + fProgressMonitor(NULL) { fImages = new image_data_info[kImageBufferCount]; fDecodeBuffer = new decode[kDecodeBufferCount]; @@ -888,6 +903,9 @@ void DCRaw::_ScaleColors() { + if (fProgressMonitor != NULL) + fProgressMonitor("Scale Colors", 5, fProgressData); + int dblack, c, val, sum[8]; uint32 row, col, x, y; double dsum[8], dmin, dmax; @@ -1008,6 +1026,9 @@ void DCRaw::_PreInterpolate() { + if (fProgressMonitor != NULL) + fProgressMonitor("Pre-Interpolate", 10, fProgressData); + uint32 row, col; if (fShrink) { @@ -1488,6 +1509,9 @@ void DCRaw::_AHDInterpolate() { + if (fProgressMonitor != NULL) + fProgressMonitor("Interpolate", 30, fProgressData); + #define TS 256 /* Tile Size */ int i, j, tr, tc, fc, c, d, val, hm[2]; @@ -1508,8 +1532,15 @@ rgb = (ushort(*)[TS][TS][3])buffer; lab = (short (*)[TS][TS][3])(buffer + 12*TS*TS); homo = (char (*)[TS][TS])(buffer + 24*TS*TS); + float percentage = 30; + float percentageStep = 55.0f / (fInputHeight / (TS - 6)); for (top = 0; top < fInputHeight; top += TS - 6) { + if (fProgressMonitor) { + fProgressMonitor("Interpolate", percentage, fProgressData); + percentage += percentageStep; + } + for (left = 0; left < fInputWidth; left += TS - 6) { memset(rgb, 0, 12 * TS * TS); @@ -1677,6 +1708,9 @@ void DCRaw::_ConvertToRGB() { + if (fProgressMonitor != NULL) + fProgressMonitor("Convert to RGB", 85, fProgressData); + uint32 row, col, c, i, j, k; float out[3], out_cam[3][4]; double num, inverse[3][3]; @@ -2190,17 +2224,7 @@ return hasLowBits; } -void -dump_to_disk(void* data, size_t length) -{ - FILE* file = fopen("/tmp/RAW.out", "wb"); - if (file == NULL) - return; - fwrite(data, length, 1, file); - fclose(file); -} - void DCRaw::_LoadRAWCanonCompressed(const image_data_info& image) { @@ -2354,7 +2378,7 @@ } } - dump_to_disk(fImageData, fInputWidth * fColors * 100); + //dump_to_disk(fImageData, fInputWidth * fColors * 100); free(jh.row); if (rawWidth > fInputWidth) @@ -2393,6 +2417,9 @@ void DCRaw::_WriteRGB32(image_data_info& image, uint8* outputBuffer) { + if (fProgressMonitor != NULL) + fProgressMonitor("Write RGB", 95, fProgressData); + uint8* line, lookUpTable[0x10000]; uint32 width = image.flip > 4 ? fOutputHeight : fOutputWidth; @@ -3393,3 +3420,17 @@ return B_OK; } + +void +DCRaw::SetProgressMonitor(monitor_hook hook, void* data) +{ + fProgressMonitor = hook; + fProgressData = data; +} + + +void +DCRaw::SetHalfSize(bool half) +{ + fHalfSize = half; +} Modified: haiku/trunk/src/add-ons/translators/raw/RAW.h =================================================================== --- haiku/trunk/src/add-ons/translators/raw/RAW.h 2007-04-10 19:04:13 UTC (rev 20643) +++ haiku/trunk/src/add-ons/translators/raw/RAW.h 2007-04-10 21:12:12 UTC (rev 20644) @@ -50,6 +50,8 @@ bool is_raw; }; +typedef void (*monitor_hook)(const char* message, float percentage, void* data); + class DCRaw { public: DCRaw(BPositionIO& stream); @@ -65,7 +67,10 @@ status_t GetEXIFTag(off_t& offset, size_t& length, bool& bigEndian) const; + void SetProgressMonitor(monitor_hook hook, void* data); + void SetHalfSize(bool half); + private: int32 _AllocateImage(); image_data_info& _Raw(); @@ -185,6 +190,9 @@ uint32 fEXIFLength; off_t fCurveOffset; + + monitor_hook fProgressMonitor; + void* fProgressData; }; #endif // RAW_H Modified: haiku/trunk/src/add-ons/translators/raw/RAWTranslator.cpp =================================================================== --- haiku/trunk/src/add-ons/translators/raw/RAWTranslator.cpp 2007-04-10 19:04:13 UTC (rev 20643) +++ haiku/trunk/src/add-ons/translators/raw/RAWTranslator.cpp 2007-04-10 21:12:12 UTC (rev 20644) @@ -16,9 +16,11 @@ // Extensions that ShowImage supports -const char *kDocumentCount = "/documentCount"; -const char *kDocumentIndex = "/documentIndex"; +const char* kDocumentCount = "/documentCount"; +const char* kDocumentIndex = "/documentIndex"; +const char* kProgressMonitor = "/progressMonitor"; + // The input formats that this translator supports. translation_format sInputFormats[] = { { @@ -62,6 +64,10 @@ const uint32 kNumDefaultSettings = sizeof(sDefaultSettings) / sizeof(TranSetting); + +// #pragma mark - + + RAWTranslator::RAWTranslator() : BaseTranslator("RAW Images", "RAW Image Translator", RAW_TRANSLATOR_VERSION, @@ -133,6 +139,37 @@ } +bigtime_t gStart; + + +/*static*/ void +RAWTranslator::_ProgressMonitor(const char* message, float percentage, + void* data) +{ + BMessenger& messenger = *(BMessenger*)data; + + BMessage update; + update.AddString("message", message); + update.AddFloat("percent", percentage); + update.AddInt64("time", system_time()); + +#if 1 + static bigtime_t last; + static int32 lastHash; + int32 hash = *(int32*)message; + + if (system_time() - last > 500000 || hash != lastHash) { + printf("%6.3fs: %3.1f%% %s\n", + (system_time() - gStart) / 1000000.0, percentage, message); + last = system_time(); + lastHash = hash; + } +#endif + + messenger.SendMessage(&update); +} + + status_t RAWTranslator::DerivedTranslate(BPositionIO* source, const translator_info* info, BMessage* settings, @@ -143,17 +180,27 @@ if (outType != B_TRANSLATOR_BITMAP || baseType != 0) return B_NO_TRANSLATOR; + DCRaw raw(*source); + bool headerOnly = false; - if (settings != NULL) + BMessenger monitor; + + if (settings != NULL) { settings->FindBool(B_TRANSLATOR_EXT_HEADER_ONLY, &headerOnly); - DCRaw raw(*source); + if (settings->FindMessenger(kProgressMonitor, &monitor) == B_OK) { + raw.SetProgressMonitor(&_ProgressMonitor, &monitor); + _ProgressMonitor("Reading Image Data", 0, &monitor); + } + } int32 imageIndex = 0; uint8* buffer = NULL; size_t bufferSize; status_t status; + gStart = system_time(); + try { status = raw.Identify(); @@ -176,6 +223,8 @@ if (status < B_OK) return B_NO_TRANSLATOR; + printf("TOTAL: %6.3fs\n", (system_time() - gStart) / 1000000.0); + image_meta_info meta; raw.GetMetaInfo(meta); Modified: haiku/trunk/src/add-ons/translators/raw/RAWTranslator.h =================================================================== --- haiku/trunk/src/add-ons/translators/raw/RAWTranslator.h 2007-04-10 19:04:13 UTC (rev 20643) +++ haiku/trunk/src/add-ons/translators/raw/RAWTranslator.h 2007-04-10 21:12:12 UTC (rev 20644) @@ -18,11 +18,11 @@ #include -#define RAW_TRANSLATOR_VERSION B_TRANSLATION_MAKE_VERSION(0, 1, 0) +#define RAW_TRANSLATOR_VERSION B_TRANSLATION_MAKE_VERSION(0, 5, 0) #define RAW_IMAGE_FORMAT 'RAWI' -#define RAW_IN_QUALITY 0.95 -#define RAW_IN_CAPABILITY 0.95 +#define RAW_IN_QUALITY 0.90 +#define RAW_IN_CAPABILITY 0.90 #define BITS_IN_QUALITY 1 #define BITS_IN_CAPABILITY 1 @@ -45,7 +45,11 @@ const translator_info *inInfo, BMessage *ioExtension, uint32 outType, BPositionIO *outDestination, int32 baseType); - virtual BView *NewConfigView(TranslatorSettings *settings); + virtual BView *NewConfigView(TranslatorSettings *settings); + + private: + static void _ProgressMonitor(const char* message, float percentage, + void* data); }; #endif // RAW_TRANSLATOR_H From axeld at mail.berlios.de Tue Apr 10 23:21:37 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Tue, 10 Apr 2007 23:21:37 +0200 Subject: [Haiku-commits] r20645 - haiku/trunk/src/kits/network/libnetapi Message-ID: <200704102121.l3ALLbp7027560@sheep.berlios.de> Author: axeld Date: 2007-04-10 23:21:36 +0200 (Tue, 10 Apr 2007) New Revision: 20645 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20645&view=rev Modified: haiku/trunk/src/kits/network/libnetapi/NetEndpoint.cpp Log: Fixed several issues pointed out by Olivier "Methe" Milla. Modified: haiku/trunk/src/kits/network/libnetapi/NetEndpoint.cpp =================================================================== --- haiku/trunk/src/kits/network/libnetapi/NetEndpoint.cpp 2007-04-10 21:12:12 UTC (rev 20644) +++ haiku/trunk/src/kits/network/libnetapi/NetEndpoint.cpp 2007-04-10 21:21:36 UTC (rev 20645) @@ -1,5 +1,5 @@ /* - * Copyright 2002-2006, Haiku, Inc. All Rights Reserved. + * Copyright 2002-2007, Haiku, Inc. All Rights Reserved. * Distributed under the terms of the MIT License. */ @@ -216,8 +216,8 @@ BNetEndpoint::SetOption(int32 option, int32 level, const void* data, unsigned int length) { - if (fSocket < 0) - return B_ERROR; + if (fInit < B_OK) + return fInit; if (setsockopt(fSocket, level, option, data, length) < 0) { fLastError = errno; @@ -297,6 +297,9 @@ status_t BNetEndpoint::Bind(const BNetAddress& address) { + if (fInit < B_OK) + return fInit; + struct sockaddr_in addr; status_t status = address.GetAddr(addr); if (status != B_OK) @@ -316,6 +319,7 @@ } if (addr.sin_addr.s_addr == 0) { + // TODO: does this still apply? // Grrr, buggy getsockname! char hostname[MAXHOSTNAMELEN]; gethostname(hostname, sizeof(hostname)); @@ -340,6 +344,9 @@ status_t BNetEndpoint::Connect(const BNetAddress& address) { + if (fInit < B_OK) + return fInit; + sockaddr_in addr; if (address.GetAddr(addr) != B_OK) return B_ERROR; @@ -353,6 +360,7 @@ socklen_t addrSize = sizeof(addr); if (getpeername(fSocket, (sockaddr *) &addr, &addrSize) < 0) { Close(); + fLastError = errno; return B_ERROR; } @@ -372,6 +380,9 @@ status_t BNetEndpoint::Listen(int backlog) { + if (fInit < B_OK) + return fInit; + if (listen(fSocket, backlog) < 0) { Close(); fLastError = errno; @@ -408,8 +419,8 @@ endpoint->fPeer.SetTo(addr); if (getsockname(socket, (struct sockaddr *)&addr, &addrSize) < 0) { - endpoint->Close(); delete endpoint; + fLastError = errno; return NULL; } From korli at mail.berlios.de Tue Apr 10 23:53:56 2007 From: korli at mail.berlios.de (korli at BerliOS) Date: Tue, 10 Apr 2007 23:53:56 +0200 Subject: [Haiku-commits] r20646 - haiku/trunk/src/add-ons/kernel/drivers/audio/ac97/auich Message-ID: <200704102153.l3ALru5Z029829@sheep.berlios.de> Author: korli Date: 2007-04-10 23:53:53 +0200 (Tue, 10 Apr 2007) New Revision: 20646 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20646&view=rev Modified: haiku/trunk/src/add-ons/kernel/drivers/audio/ac97/auich/ac97.c haiku/trunk/src/add-ons/kernel/drivers/audio/ac97/auich/auich.c haiku/trunk/src/add-ons/kernel/drivers/audio/ac97/auich/multi.c Log: Applied patch from thq (bug #1146). Thanks a lot! I tested this change on Haiku. Avoids noise on shutdown because the amplifier is left on after shutdown, the amplifier is also turned on directly after init. The patch changes this to be the last thing to be turned on, and the first to be turned off. The creation of controls had an of by 1 error where the last control was skipped. Also made the controls more UI friendly so that the 'boost mic +20dB' is a part of the mic control instead of its own tab, and the AC97 mixer tab is changed to be the first one as it is probably more used than the 'Record' tab, which now is called 'Recording'. Modified: haiku/trunk/src/add-ons/kernel/drivers/audio/ac97/auich/ac97.c =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/audio/ac97/auich/ac97.c 2007-04-10 21:21:36 UTC (rev 20645) +++ haiku/trunk/src/add-ons/kernel/drivers/audio/ac97/auich/ac97.c 2007-04-10 21:53:53 UTC (rev 20646) @@ -279,9 +279,9 @@ } const ac97_source_info source_info[] = { - { "Record", B_MIX_GAIN|B_MIX_MUTE|B_MIX_STEREO|B_MIX_RECORDMUX, 100, AC97_RECORD_GAIN, 0x8000, 4, 0, 1, 0, 0.0, 22.5, 1.5 }, + { "Recording", B_MIX_GAIN|B_MIX_MUTE|B_MIX_STEREO|B_MIX_RECORDMUX, 100, AC97_RECORD_GAIN, 0x8000, 4, 0, 1, 0, 0.0, 22.5, 1.5 }, { "Master", B_MIX_GAIN|B_MIX_MUTE|B_MIX_STEREO, 101, AC97_MASTER_VOLUME, 0x8000, 5, 0, 1, 1,-46.5, 0.0, 1.5 }, - //{ "Bass/Trebble", B_MIX_GAIN|B_MIX_STEREO, 102, AC97_MASTER_TONE, 0x0f0f, 4, 0, 1, 1,-12.0, 10.5, 1.5 }, + //{ "Bass/Treble", B_MIX_GAIN|B_MIX_STEREO, 102, AC97_MASTER_TONE, 0x0f0f, 4, 0, 1, 1,-12.0, 10.5, 1.5 }, //{ "Aux Out", B_MIX_GAIN|B_MIX_MUTE|B_MIX_STEREO, 103, AC97_AUX_OUT_VOLUME, 0x8000, 5, 0, 1, 1,-46.5, 0.0, 1.5 }, { "PCM Out", B_MIX_GAIN|B_MIX_MUTE|B_MIX_STEREO, 104, AC97_PCM_OUT_VOLUME, 0x8808, 5, 0, 1, 1,-34.5, 12.0, 1.5 }, { "CD", B_MIX_GAIN|B_MIX_MUTE|B_MIX_STEREO, 105, AC97_CD_VOLUME, 0x8808, 5, 0, 1, 1,-34.5, 12.0, 1.5 }, Modified: haiku/trunk/src/add-ons/kernel/drivers/audio/ac97/auich/auich.c =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/audio/ac97/auich/auich.c 2007-04-10 21:21:36 UTC (rev 20645) +++ haiku/trunk/src/add-ons/kernel/drivers/audio/ac97/auich/auich.c 2007-04-10 21:53:53 UTC (rev 20646) @@ -659,7 +659,6 @@ snooze(50000); // 50 ms ac97_init(&card->config); - ac97_amp_enable(&card->config, true); rv = auich_reg_read_32(&card->config, AUICH_REG_GLOB_STA); if (!(rv & STA_S0CR)) { /* reset failure */ @@ -698,6 +697,7 @@ PRINT(("codec record gain = %#04x\n",auich_codec_read(&card->config, 0x1c)));*/ PRINT(("writing codec registers\n")); + // TODO : to move with AC97 /* enable master output */ auich_codec_write(&card->config, AC97_MASTER_VOLUME, 0x0000); @@ -714,6 +714,8 @@ /* set record gain */ //auich_codec_write(&card->config, AC97_RECORD_GAIN, 0x0000); + ac97_amp_enable(&card->config, true); + PRINT(("codec master output = %#04x\n",auich_codec_read(&card->config, AC97_MASTER_VOLUME))); PRINT(("codec aux output = %#04x\n",auich_codec_read(&card->config, AC97_AUX_OUT_VOLUME))); PRINT(("codec mono output = %#04x\n",auich_codec_read(&card->config, AC97_MONO_VOLUME))); @@ -830,6 +832,7 @@ auich_shutdown(auich_dev *card) { PRINT(("shutdown(%p)\n", card)); + ac97_amp_enable(&card->config, false); card->interrupt_mask = 0; if (current_settings.use_thread) { Modified: haiku/trunk/src/add-ons/kernel/drivers/audio/ac97/auich/multi.c =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/audio/ac97/auich/multi.c 2007-04-10 21:21:36 UTC (rev 20645) +++ haiku/trunk/src/add-ons/kernel/drivers/audio/ac97/auich/multi.c 2007-04-10 21:53:53 UTC (rev 20646) @@ -194,10 +194,82 @@ { uint32 i = 0, index = 0, count, id, parent, parent2, parent3; const ac97_source_info *info; + + /* AC97 Mixer */ + parent = auich_create_group_control(multi, &index, 0, 0, "AC97 Mixer"); + + count = source_info_size; + //Note that we ignore first item in source_info + //It's for recording, but do match this with ac97.c's source_info + for(i=1; i < count ; i++) { + info = &source_info[i]; + PRINT(("name : %s\n", info->name)); - parent = auich_create_group_control(multi, &index, 0, 0, "Record"); + parent2 = auich_create_group_control(multi, &index, parent, 0, info->name); + + if(info->type & B_MIX_GAIN) { + if(info->type & B_MIX_MUTE) { + multi->controls[index].mix_control.id = EMU_MULTI_CONTROL_FIRSTID + index; + multi->controls[index].mix_control.flags = B_MULTI_MIX_ENABLE; + multi->controls[index].mix_control.master = EMU_MULTI_CONTROL_MASTERID; + multi->controls[index].mix_control.parent = parent2; + multi->controls[index].mix_control.string = S_MUTE; + multi->controls[index].cookie = info; + multi->controls[index].type = B_MIX_MUTE; + multi->controls[index].get = &auich_ac97_get_mix; + multi->controls[index].set = &auich_ac97_set_mix; + index++; + } + multi->controls[index].mix_control.id = EMU_MULTI_CONTROL_FIRSTID + index; + multi->controls[index].mix_control.flags = B_MULTI_MIX_GAIN; + multi->controls[index].mix_control.master = EMU_MULTI_CONTROL_MASTERID; + multi->controls[index].mix_control.parent = parent2; + strcpy(multi->controls[index].mix_control.name, info->name); + multi->controls[index].mix_control.u.gain.min_gain = info->min_gain; + multi->controls[index].mix_control.u.gain.max_gain = info->max_gain; + multi->controls[index].mix_control.u.gain.granularity = info->granularity; + multi->controls[index].cookie = info; + multi->controls[index].type = B_MIX_GAIN; + multi->controls[index].get = &auich_ac97_get_mix; + multi->controls[index].set = &auich_ac97_set_mix; + id = multi->controls[index].mix_control.id; + index++; + + if(info->type & B_MIX_STEREO) { + multi->controls[index].mix_control.id = EMU_MULTI_CONTROL_FIRSTID + index; + multi->controls[index].mix_control.flags = B_MULTI_MIX_GAIN; + multi->controls[index].mix_control.master = id; + multi->controls[index].mix_control.parent = parent2; + strcpy(multi->controls[index].mix_control.name, info->name); + multi->controls[index].mix_control.u.gain.min_gain = info->min_gain; + multi->controls[index].mix_control.u.gain.max_gain = info->max_gain; + multi->controls[index].mix_control.u.gain.granularity = info->granularity; + multi->controls[index].cookie = info; + multi->controls[index].type = B_MIX_GAIN; + multi->controls[index].get = &auich_ac97_get_mix; + multi->controls[index].set = &auich_ac97_set_mix; + index++; + } + + if(info->type & B_MIX_MICBOOST) { + multi->controls[index].mix_control.id = EMU_MULTI_CONTROL_FIRSTID + index; + multi->controls[index].mix_control.flags = B_MULTI_MIX_ENABLE; + multi->controls[index].mix_control.master = EMU_MULTI_CONTROL_MASTERID; + multi->controls[index].mix_control.parent = parent2; + strcpy(multi->controls[index].mix_control.name, "+20 dB"); + multi->controls[index].cookie = info; + multi->controls[index].type = B_MIX_MICBOOST; + multi->controls[index].get = &auich_ac97_get_mix; + multi->controls[index].set = &auich_ac97_set_mix; + index++; + } + } + } + /* AC97 Record */ + parent = auich_create_group_control(multi, &index, 0, 0, "Recording"); + info = &source_info[0]; PRINT(("name : %s\n", info->name)); @@ -302,83 +374,7 @@ index++; } } - - parent = auich_create_group_control(multi, &index, 0, 0, "AC97 Mixer"); - - count = source_info_size; - count--; - - for(i=1; i < count ; i++) { - info = &source_info[i]; - PRINT(("name : %s\n", info->name)); - - parent2 = auich_create_group_control(multi, &index, parent, 0, info->name); - - if(info->type & B_MIX_GAIN) { - if(info->type & B_MIX_MUTE) { - multi->controls[index].mix_control.id = EMU_MULTI_CONTROL_FIRSTID + index; - multi->controls[index].mix_control.flags = B_MULTI_MIX_ENABLE; - multi->controls[index].mix_control.master = EMU_MULTI_CONTROL_MASTERID; - multi->controls[index].mix_control.parent = parent2; - multi->controls[index].mix_control.string = S_MUTE; - multi->controls[index].cookie = info; - multi->controls[index].type = B_MIX_MUTE; - multi->controls[index].get = &auich_ac97_get_mix; - multi->controls[index].set = &auich_ac97_set_mix; - index++; - } - multi->controls[index].mix_control.id = EMU_MULTI_CONTROL_FIRSTID + index; - multi->controls[index].mix_control.flags = B_MULTI_MIX_GAIN; - multi->controls[index].mix_control.master = EMU_MULTI_CONTROL_MASTERID; - multi->controls[index].mix_control.parent = parent2; - strcpy(multi->controls[index].mix_control.name, info->name); - multi->controls[index].mix_control.u.gain.min_gain = info->min_gain; - multi->controls[index].mix_control.u.gain.max_gain = info->max_gain; - multi->controls[index].mix_control.u.gain.granularity = info->granularity; - multi->controls[index].cookie = info; - multi->controls[index].type = B_MIX_GAIN; - multi->controls[index].get = &auich_ac97_get_mix; - multi->controls[index].set = &auich_ac97_set_mix; - id = multi->controls[index].mix_control.id; - index++; - - if(info->type & B_MIX_STEREO) { - multi->controls[index].mix_control.id = EMU_MULTI_CONTROL_FIRSTID + index; - multi->controls[index].mix_control.flags = B_MULTI_MIX_GAIN; - multi->controls[index].mix_control.master = id; - multi->controls[index].mix_control.parent = parent2; - strcpy(multi->controls[index].mix_control.name, info->name); - multi->controls[index].mix_control.u.gain.min_gain = info->min_gain; - multi->controls[index].mix_control.u.gain.max_gain = info->max_gain; - multi->controls[index].mix_control.u.gain.granularity = info->granularity; - multi->controls[index].cookie = info; - multi->controls[index].type = B_MIX_GAIN; - multi->controls[index].get = &auich_ac97_get_mix; - multi->controls[index].set = &auich_ac97_set_mix; - index++; - } - } - } - - parent = auich_create_group_control(multi, &index, 0, S_SETUP, NULL); - - /* AC97 20db Boost Mic */ - info = &source_info[6]; - - if(info->type & B_MIX_GAIN && info->type & B_MIX_MICBOOST) { - multi->controls[index].mix_control.id = EMU_MULTI_CONTROL_FIRSTID + index; - multi->controls[index].mix_control.flags = B_MULTI_MIX_ENABLE; - multi->controls[index].mix_control.master = EMU_MULTI_CONTROL_MASTERID; - multi->controls[index].mix_control.parent = parent; - strcpy(multi->controls[index].mix_control.name, "Mic +20dB"); - multi->controls[index].cookie = info; - multi->controls[index].type = B_MIX_MICBOOST; - multi->controls[index].get = &auich_ac97_get_mix; - multi->controls[index].set = &auich_ac97_set_mix; - index++; - } - multi->control_count = index; PRINT(("multi->control_count %lu\n", multi->control_count)); return B_OK; From bvarner at mail.berlios.de Wed Apr 11 05:26:27 2007 From: bvarner at mail.berlios.de (bvarner at BerliOS) Date: Wed, 11 Apr 2007 05:26:27 +0200 Subject: [Haiku-commits] r20647 - haiku/trunk/src/add-ons/kernel/drivers/network/bcm570x Message-ID: <200704110326.l3B3QRMR028920@sheep.berlios.de> Author: bvarner Date: 2007-04-11 05:26:26 +0200 (Wed, 11 Apr 2007) New Revision: 20647 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20647&view=rev Modified: haiku/trunk/src/add-ons/kernel/drivers/network/bcm570x/b57um.c Log: Small adjustment to reduce the number of comparisons when publishing devices. Modified: haiku/trunk/src/add-ons/kernel/drivers/network/bcm570x/b57um.c =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/network/bcm570x/b57um.c 2007-04-10 21:53:53 UTC (rev 20646) +++ haiku/trunk/src/add-ons/kernel/drivers/network/bcm570x/b57um.c 2007-04-11 03:26:26 UTC (rev 20647) @@ -303,11 +303,12 @@ while (pci->get_nth_pci_info(i++, &dev_info) == 0) { is_detected = 0; - for (j = 0; bcm5700_pci_tbl[j].vendor != 0; j++) { - if ((dev_info.class_base == PCI_network) && (dev_info.class_sub == PCI_ethernet) - && (dev_info.vendor_id == bcm5700_pci_tbl[j].vendor) && (dev_info.device_id == bcm5700_pci_tbl[j].device)) { - is_detected = 1; - break; + if ((dev_info.class_base == PCI_network) && (dev_info.class_sub == PCI_ethernet)) { + for (j = 0; bcm5700_pci_tbl[j].vendor != 0; j++) { + if ((dev_info.vendor_id == bcm5700_pci_tbl[j].vendor) && (dev_info.device_id == bcm5700_pci_tbl[j].device)) { + is_detected = 1; + break; + } } } From axeld at mail.berlios.de Wed Apr 11 11:10:15 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Wed, 11 Apr 2007 11:10:15 +0200 Subject: [Haiku-commits] r20648 - haiku/trunk/src/add-ons/translators/raw Message-ID: <200704110910.l3B9AFrP027287@sheep.berlios.de> Author: axeld Date: 2007-04-11 11:10:14 +0200 (Wed, 11 Apr 2007) New Revision: 20648 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20648&view=rev Modified: haiku/trunk/src/add-ons/translators/raw/RAW.cpp haiku/trunk/src/add-ons/translators/raw/RAWTranslator.cpp Log: Improved progress report, the update message now gets a proper "what" field. Modified: haiku/trunk/src/add-ons/translators/raw/RAW.cpp =================================================================== --- haiku/trunk/src/add-ons/translators/raw/RAW.cpp 2007-04-11 03:26:26 UTC (rev 20647) +++ haiku/trunk/src/add-ons/translators/raw/RAW.cpp 2007-04-11 09:10:14 UTC (rev 20648) @@ -1510,7 +1510,7 @@ DCRaw::_AHDInterpolate() { if (fProgressMonitor != NULL) - fProgressMonitor("Interpolate", 30, fProgressData); + fProgressMonitor("Interpolate", 20, fProgressData); #define TS 256 /* Tile Size */ @@ -1532,8 +1532,8 @@ rgb = (ushort(*)[TS][TS][3])buffer; lab = (short (*)[TS][TS][3])(buffer + 12*TS*TS); homo = (char (*)[TS][TS])(buffer + 24*TS*TS); - float percentage = 30; - float percentageStep = 55.0f / (fInputHeight / (TS - 6)); + float percentage = 20; + float percentageStep = 70.0f / (fInputHeight / (TS - 6)); for (top = 0; top < fInputHeight; top += TS - 6) { if (fProgressMonitor) { @@ -1709,7 +1709,7 @@ DCRaw::_ConvertToRGB() { if (fProgressMonitor != NULL) - fProgressMonitor("Convert to RGB", 85, fProgressData); + fProgressMonitor("Convert to RGB", 90, fProgressData); uint32 row, col, c, i, j, k; float out[3], out_cam[3][4]; Modified: haiku/trunk/src/add-ons/translators/raw/RAWTranslator.cpp =================================================================== --- haiku/trunk/src/add-ons/translators/raw/RAWTranslator.cpp 2007-04-11 03:26:26 UTC (rev 20647) +++ haiku/trunk/src/add-ons/translators/raw/RAWTranslator.cpp 2007-04-11 09:10:14 UTC (rev 20648) @@ -20,6 +20,7 @@ const char* kDocumentIndex = "/documentIndex"; const char* kProgressMonitor = "/progressMonitor"; +const uint32 kMsgProgressMonitorUpdate = 'SIup'; // The input formats that this translator supports. translation_format sInputFormats[] = { @@ -148,7 +149,7 @@ { BMessenger& messenger = *(BMessenger*)data; - BMessage update; + BMessage update(kMsgProgressMonitorUpdate); update.AddString("message", message); update.AddFloat("percent", percentage); update.AddInt64("time", system_time()); From axeld at mail.berlios.de Wed Apr 11 11:23:34 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Wed, 11 Apr 2007 11:23:34 +0200 Subject: [Haiku-commits] r20649 - haiku/trunk/src/add-ons/translators/raw Message-ID: <200704110923.l3B9NY8c028461@sheep.berlios.de> Author: axeld Date: 2007-04-11 11:23:33 +0200 (Wed, 11 Apr 2007) New Revision: 20649 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20649&view=rev Modified: haiku/trunk/src/add-ons/translators/raw/RAW.cpp haiku/trunk/src/add-ons/translators/raw/RAWTranslator.cpp Log: * Fixed a few large memory holes (Dano even crashes on low memory...). * Removed printing progress updates to stdout. Modified: haiku/trunk/src/add-ons/translators/raw/RAW.cpp =================================================================== --- haiku/trunk/src/add-ons/translators/raw/RAW.cpp 2007-04-11 09:10:14 UTC (rev 20648) +++ haiku/trunk/src/add-ons/translators/raw/RAW.cpp 2007-04-11 09:23:33 UTC (rev 20649) @@ -118,6 +118,7 @@ fThumbIndex(-1), fDNGVersion(0), fIsTIFF(false), + fImageData(NULL), fThreshold(0), fHalfSize(false), fUseCameraWhiteBalance(true), @@ -170,7 +171,9 @@ delete[] fCurve; delete[] cbrt; + free(fHistogram); + free(fImageData); } @@ -3328,8 +3331,11 @@ } outputBuffer = (uint8*)malloc(bufferSize); - if (outputBuffer == NULL) + if (outputBuffer == NULL) { + free(fImageData); + fImageData = NULL; throw (status_t)B_NO_MEMORY; + } fRead.Seek(image.data_offset, SEEK_SET); @@ -3372,6 +3378,9 @@ _WriteJPEG(image, outputBuffer); } + free(fImageData); + fImageData = NULL; + return B_OK; } Modified: haiku/trunk/src/add-ons/translators/raw/RAWTranslator.cpp =================================================================== --- haiku/trunk/src/add-ons/translators/raw/RAWTranslator.cpp 2007-04-11 09:10:14 UTC (rev 20648) +++ haiku/trunk/src/add-ons/translators/raw/RAWTranslator.cpp 2007-04-11 09:23:33 UTC (rev 20649) @@ -15,6 +15,23 @@ #include +class FreeAllocation { + public: + FreeAllocation(void* buffer) + : + fBuffer(buffer) + { + } + + ~FreeAllocation() + { + free(fBuffer); + } + + private: + void* fBuffer; +}; + // Extensions that ShowImage supports const char* kDocumentCount = "/documentCount"; const char* kDocumentIndex = "/documentIndex"; @@ -65,7 +82,6 @@ const uint32 kNumDefaultSettings = sizeof(sDefaultSettings) / sizeof(TranSetting); - // #pragma mark - @@ -140,9 +156,6 @@ } -bigtime_t gStart; - - /*static*/ void RAWTranslator::_ProgressMonitor(const char* message, float percentage, void* data) @@ -154,19 +167,6 @@ update.AddFloat("percent", percentage); update.AddInt64("time", system_time()); -#if 1 - static bigtime_t last; - static int32 lastHash; - int32 hash = *(int32*)message; - - if (system_time() - last > 500000 || hash != lastHash) { - printf("%6.3fs: %3.1f%% %s\n", - (system_time() - gStart) / 1000000.0, percentage, message); - last = system_time(); - lastHash = hash; - } -#endif - messenger.SendMessage(&update); } @@ -200,8 +200,6 @@ size_t bufferSize; status_t status; - gStart = system_time(); - try { status = raw.Identify(); @@ -211,7 +209,7 @@ imageIndex--; else imageIndex = 0; - + if (imageIndex < 0 || imageIndex >= (int32)raw.CountImages()) status = B_BAD_VALUE; } @@ -224,7 +222,8 @@ if (status < B_OK) return B_NO_TRANSLATOR; - printf("TOTAL: %6.3fs\n", (system_time() - gStart) / 1000000.0); + FreeAllocation _(buffer); + // frees the buffer on destruction image_meta_info meta; raw.GetMetaInfo(meta); From axeld at mail.berlios.de Wed Apr 11 11:25:59 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Wed, 11 Apr 2007 11:25:59 +0200 Subject: [Haiku-commits] r20650 - haiku/trunk/src/apps/showimage Message-ID: <200704110925.l3B9PxPC028625@sheep.berlios.de> Author: axeld Date: 2007-04-11 11:25:57 +0200 (Wed, 11 Apr 2007) New Revision: 20650 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20650&view=rev Added: haiku/trunk/src/apps/showimage/ProgressWindow.cpp haiku/trunk/src/apps/showimage/ProgressWindow.h Modified: haiku/trunk/src/apps/showimage/Jamfile haiku/trunk/src/apps/showimage/ShowImageView.cpp haiku/trunk/src/apps/showimage/ShowImageView.h Log: Implemented a progress window: it will be shown after one second in case the translator supports it - currently, only the RAW image translator does this (as it needs about 10 seconds to open a 6 mio. pixel RAW image on a 2.6 GHz P4). Modified: haiku/trunk/src/apps/showimage/Jamfile =================================================================== --- haiku/trunk/src/apps/showimage/Jamfile 2007-04-11 09:23:33 UTC (rev 20649) +++ haiku/trunk/src/apps/showimage/Jamfile 2007-04-11 09:25:57 UTC (rev 20650) @@ -4,7 +4,8 @@ SetSubDirSupportedPlatformsBeOSCompatible ; -Application ShowImage : ShowImageApp.cpp +Application ShowImage : + ShowImageApp.cpp ShowImageSettings.cpp ShowImageStatusView.cpp ShowImageUndo.cpp @@ -14,6 +15,7 @@ Filter.cpp EntryMenuItem.cpp BackgroundImage.cpp + ProgressWindow.cpp ResizerWindow.cpp : be tracker translation : ShowImage.rdef Added: haiku/trunk/src/apps/showimage/ProgressWindow.cpp =================================================================== --- haiku/trunk/src/apps/showimage/ProgressWindow.cpp 2007-04-11 09:23:33 UTC (rev 20649) +++ haiku/trunk/src/apps/showimage/ProgressWindow.cpp 2007-04-11 09:25:57 UTC (rev 20650) @@ -0,0 +1,116 @@ +/* + * Copyright 2007, Axel D?rfler, axeld at pinc-software.de. All rights reserved. + * Distributed under the terms of the MIT License. + */ + + +#include "ProgressWindow.h" + +#include +#include +#include +#include + +#include + + +static const uint32 kMsgShow = 'show'; +static const uint32 kMsgStatusUpdate = 'SIup'; + + +ProgressWindow::ProgressWindow(BWindow* referenceWindow) + : BWindow(BRect(0, 0, 250, 100), "Progress Monitor", + B_MODAL_WINDOW_LOOK, B_FLOATING_APP_WINDOW_FEEL, + B_NOT_ZOOMABLE | B_NOT_RESIZABLE | B_ASYNCHRONOUS_CONTROLS), + fRunner(NULL) +{ + BRect rect = Bounds(); + + BView *view = new BView(rect, NULL, B_FOLLOW_ALL, B_WILL_DRAW); + view->SetViewColor(ui_color(B_PANEL_BACKGROUND_COLOR)); + AddChild(view); + + rect = view->Bounds().InsetByCopy(5, 5); + fStatusBar = new BStatusBar(rect, "status", NULL, NULL); + float width, height; + fStatusBar->GetPreferredSize(&width, &height); + fStatusBar->ResizeTo(rect.Width(), height); + fStatusBar->SetResizingMode(B_FOLLOW_TOP | B_FOLLOW_LEFT_RIGHT); + view->AddChild(fStatusBar); + + BScreen screen(referenceWindow); + ResizeTo(Bounds().Width(), height + 9); + MoveTo(screen.Frame().left + 5, screen.Frame().bottom - Bounds().Height() - 5); + + Run(); +} + + +ProgressWindow::~ProgressWindow() +{ + delete fRunner; +} + + +void +ProgressWindow::Start() +{ + BAutolock _(this); + + fRetrievedUpdate = false; + fRetrievedShow = false; + delete fRunner; + + BMessage show(kMsgShow); + fRunner = new BMessageRunner(this, &show, 1000000, 1); +} + + +void +ProgressWindow::Stop() +{ + BAutolock _(this); + + delete fRunner; + fRunner = NULL; + + if (!IsHidden()) + Hide(); +} + + +void +ProgressWindow::MessageReceived(BMessage *message) +{ + switch (message->what) { + case kMsgShow: + if (fRetrievedUpdate && IsHidden()) { + Show(); + Minimize(false); + } + + fRetrievedShow = true; + break; + + case kMsgStatusUpdate: + float percent; + if (message->FindFloat("percent", &percent) == B_OK) + fStatusBar->Update(percent - fStatusBar->CurrentValue()); + + const char *text; + if (message->FindString("message", &text) == B_OK) + fStatusBar->SetText(text); + + fRetrievedUpdate = true; + + if (fRetrievedShow && IsHidden()) { + Show(); + Minimize(false); + } + break; + + default: + BWindow::MessageReceived(message); + } +} + Added: haiku/trunk/src/apps/showimage/ProgressWindow.h =================================================================== --- haiku/trunk/src/apps/showimage/ProgressWindow.h 2007-04-11 09:23:33 UTC (rev 20649) +++ haiku/trunk/src/apps/showimage/ProgressWindow.h 2007-04-11 09:25:57 UTC (rev 20650) @@ -0,0 +1,32 @@ +/* + * Copyright 2007, Axel D?rfler, axeld at pinc-software.de. All rights reserved. + * Distributed under the terms of the MIT License. + */ +#ifndef PROGRESS_WINDOW_H +#define PROGRESS_WINDOW_H + + +#include + +class BMessageRunner; +class BStatusBar; + + +class ProgressWindow : public BWindow { + public: + ProgressWindow(BWindow* referenceWindow); + virtual ~ProgressWindow(); + + virtual void MessageReceived(BMessage *message); + + void Start(); + void Stop(); + + private: + BStatusBar* fStatusBar; + BMessageRunner* fRunner; + bool fRetrievedUpdate; + bool fRetrievedShow; +}; + +#endif // PROGRESS_WINDOW_H Modified: haiku/trunk/src/apps/showimage/ShowImageView.cpp =================================================================== --- haiku/trunk/src/apps/showimage/ShowImageView.cpp 2007-04-11 09:23:33 UTC (rev 20649) +++ haiku/trunk/src/apps/showimage/ShowImageView.cpp 2007-04-11 09:25:57 UTC (rev 20650) @@ -14,6 +14,7 @@ */ +#include "ProgressWindow.h" #include "ShowImageApp.h" #include "ShowImageConstants.h" #include "ShowImageView.h" @@ -174,8 +175,9 @@ ShowImageView::ShowImageView(BRect rect, const char *name, uint32 resizingMode, - uint32 flags) - : BView(rect, name, resizingMode, flags) + uint32 flags) + : BView(rect, name, resizingMode, flags), + fProgressWindow(NULL) { ShowImageSettings* settings; settings = my_app->Settings(); @@ -214,7 +216,7 @@ fScaleBilinear = settings->GetBool("ScaleBilinear", fScaleBilinear); settings->Unlock(); } - + SetViewColor(B_TRANSPARENT_COLOR); SetHighColor(kBorderColor); SetLowColor(ui_color(B_PANEL_BACKGROUND_COLOR)); @@ -488,18 +490,29 @@ // if new image, reset to first document fDocumentIndex = 1; } + if (ioExtension.AddInt32("/documentIndex", fDocumentIndex) != B_OK) return B_ERROR; - if (roster->Identify(&file, &ioExtension, &info, 0, NULL, - B_TRANSLATOR_BITMAP) != B_OK) - return B_ERROR; + if (ioExtension.AddMessenger("/progressMonitor", fProgressWindow) == B_OK) + fProgressWindow->Start(); + // Translate image data and create a new ShowImage window + BBitmapStream outstream; - if (roster->Translate(&file, &info, &ioExtension, &outstream, - B_TRANSLATOR_BITMAP) != B_OK) - return B_ERROR; + status_t status = roster->Identify(&file, &ioExtension, &info, 0, NULL, + B_TRANSLATOR_BITMAP); + if (status == B_OK) { + status = roster->Translate(&file, &info, &ioExtension, &outstream, + B_TRANSLATOR_BITMAP); + } + + fProgressWindow->Stop(); + + if (status != B_OK) + return status; + BBitmap *newBitmap = NULL; if (outstream.DetachBitmap(&newBitmap) != B_OK) return B_ERROR; @@ -565,8 +578,8 @@ // get the number of documents (pages) if it has been supplied int32 documentCount = 0; - if (ioExtension.FindInt32("/documentCount", &documentCount) == B_OK && - documentCount > 0) + if (ioExtension.FindInt32("/documentCount", &documentCount) == B_OK + && documentCount > 0) fDocumentCount = documentCount; else fDocumentCount = 1; @@ -719,9 +732,19 @@ { fUndo.SetWindow(Window()); FixupScrollBars(); + + fProgressWindow = new ProgressWindow(Window()); } +void +ShowImageView::DetachedFromWindow() +{ + fProgressWindow->Lock(); + fProgressWindow->Quit(); +} + + BRect ShowImageView::AlignBitmap() { Modified: haiku/trunk/src/apps/showimage/ShowImageView.h =================================================================== --- haiku/trunk/src/apps/showimage/ShowImageView.h 2007-04-11 09:23:33 UTC (rev 20649) +++ haiku/trunk/src/apps/showimage/ShowImageView.h 2007-04-11 09:25:57 UTC (rev 20650) @@ -1,5 +1,5 @@ /* - * Copyright 2003-2006, Haiku, Inc. All Rights Reserved. + * Copyright 2003-2007, Haiku, Inc. All Rights Reserved. * Copyright 2004-2005 yellowTAB GmbH. All Rights Reserverd. * Copyright 2006 Bernd Korz. All Rights Reserved * Distributed under the terms of the MIT License. @@ -36,6 +36,8 @@ // the delay time for hiding the cursor in 1/10 seconds (the pulse rate) #define HIDE_CURSOR_DELAY_TIME 20 +class ProgressWindow; + class ShowImageView : public BView { public: ShowImageView(BRect rect, const char *name, uint32 resizingMode, @@ -43,6 +45,7 @@ virtual ~ShowImageView(); virtual void AttachedToWindow(); + virtual void DetachedFromWindow(); virtual void Draw(BRect updateRect); virtual void FrameResized(float width, float height); virtual void MouseDown(BPoint point); @@ -249,6 +252,8 @@ int fHideCursorCountDown; // Hides the cursor when it reaches zero bool fIsActiveWin; // Is the parent window the active window? + ProgressWindow* fProgressWindow; + enum image_orientation fImageOrientation; static enum image_orientation fTransformation[ ImageProcessor::kNumberOfAffineTransformations][kNumberOfOrientations]; From axeld at mail.berlios.de Wed Apr 11 12:17:26 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Wed, 11 Apr 2007 12:17:26 +0200 Subject: [Haiku-commits] r20651 - haiku/trunk/src/add-ons/kernel/network/stack Message-ID: <200704111017.l3BAHQGI032235@sheep.berlios.de> Author: axeld Date: 2007-04-11 12:17:26 +0200 (Wed, 11 Apr 2007) New Revision: 20651 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20651&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/stack/net_buffer.cpp Log: * init_data_node() is now called init_first_data_node(), and also sets data_header::first_node to that node. It will also remove some of the burden of the callers with regard to setting its members correctly. * Minor cleanup. Modified: haiku/trunk/src/add-ons/kernel/network/stack/net_buffer.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/net_buffer.cpp 2007-04-11 09:25:57 UTC (rev 20650) +++ haiku/trunk/src/add-ons/kernel/network/stack/net_buffer.cpp 2007-04-11 10:17:26 UTC (rev 20651) @@ -1,5 +1,5 @@ /* - * Copyright 2006, Haiku, Inc. All Rights Reserved. + * Copyright 2006-2007, Haiku, Inc. All Rights Reserved. * Distributed under the terms of the MIT License. * * Authors: @@ -55,6 +55,8 @@ data_node *first_node; }; +#define MAX_FREE_BUFFER_SIZE (BUFFER_SIZE - sizeof(data_header)) + struct net_buffer_private : net_buffer { struct list buffers; data_node first_node; @@ -140,6 +142,9 @@ } +/*! + Tries to allocate \a size bytes from the free space in the header. +*/ static uint8 * alloc_data_header_space(data_header *header, size_t size) { @@ -184,14 +189,22 @@ } +/*! + Initializes the first data_node of a data_header. + The node must have been assigned to the header already. +*/ static void -init_data_node(data_node *node, size_t headerSpace) +init_first_data_node(data_node *node) { + data_header *header = node->header; + node->offset = 0; - node->start = (uint8 *)node->header + sizeof(data_header) + headerSpace; + node->start = header->data_end + header->data_space; node->used = 0; - node->header_space = headerSpace; - node->tail_space = BUFFER_SIZE - headerSpace - sizeof(data_header); + node->header_space = header->data_space; + node->tail_space = MAX_FREE_BUFFER_SIZE - header->data_space; + + header->first_node = node; } @@ -201,7 +214,8 @@ if (located == NULL) located = header; - data_node *node = (data_node *)alloc_data_header_space(located, sizeof(data_node)); + data_node *node = (data_node *)alloc_data_header_space(located, + sizeof(data_node)); if (node == NULL) return NULL; @@ -222,7 +236,8 @@ { data_header *located = node->located; - TRACE((" remove data node %p from header %p (located %p)\n", node, node->header, located)); + TRACE((" remove data node %p from header %p (located %p)\n", + node, node->header, located)); if (located != node->header) release_data_header(node->header); @@ -260,7 +275,8 @@ static net_buffer * create_buffer(size_t headerSpace) { - net_buffer_private *buffer = (net_buffer_private *)malloc(sizeof(struct net_buffer_private)); + net_buffer_private *buffer = (net_buffer_private *)malloc( + sizeof(struct net_buffer_private)); if (buffer == NULL) return NULL; @@ -274,8 +290,7 @@ buffer->first_node.header = header; buffer->first_node.located = NULL; - init_data_node(&buffer->first_node, headerSpace); - header->first_node = &buffer->first_node; + init_first_data_node(&buffer->first_node); list_init(&buffer->buffers); list_add_item(&buffer->buffers, &buffer->first_node); @@ -365,7 +380,8 @@ TRACE(("clone_buffer(buffer %p)\n", buffer)); - net_buffer_private *clone = (net_buffer_private *)malloc(sizeof(struct net_buffer_private)); + net_buffer_private *clone = (net_buffer_private *)malloc( + sizeof(struct net_buffer_private)); if (clone == NULL) return NULL; @@ -636,7 +652,7 @@ size_t bytesLeft = size; do { if (node->header_space == 0) { - size_t headerSpace = BUFFER_SIZE - sizeof(data_header); + size_t headerSpace = MAX_FREE_BUFFER_SIZE; data_header *header = create_data_header(headerSpace); if (header == NULL) { // TODO: free up headers we already allocated! @@ -644,12 +660,10 @@ } data_node *previous = node; + node = (data_node *)add_data_node(header); + init_first_data_node(node); - init_data_node(node, headerSpace); - node->header_space = header->data_space; - header->first_node = node; - list_insert_item_before(&buffer->buffers, previous, node); } @@ -661,10 +675,12 @@ bytesLeft -= willConsume; } while (bytesLeft > 0); + // correct data offset in all nodes + size_t offset = 0; - for (node = (data_node *)list_get_first_item(&buffer->buffers); - node != NULL; node = (data_node *) - list_get_next_item(&buffer->buffers, node)) { + node = NULL; + while ((node = (data_node *)list_get_next_item(&buffer->buffers, + node)) != NULL) { node->offset = offset; offset += node->used; } @@ -734,7 +750,7 @@ uint32 count = (sizeNeeded + BUFFER_SIZE - minimalHeaderSpace - 1) / (BUFFER_SIZE - minimalHeaderSpace); uint32 headerSpace = BUFFER_SIZE - sizeNeeded / count - sizeof(data_header); - uint32 sizeUsed = BUFFER_SIZE - sizeof(data_header) - headerSpace; + uint32 sizeUsed = MAX_FREE_BUFFER_SIZE - headerSpace; uint32 sizeAdded = tailSpace; // allocate space left in the node @@ -748,7 +764,7 @@ if (i == count - 1) { // last data_header - compensate rounding errors sizeUsed = size - sizeAdded; - headerSpace = BUFFER_SIZE - sizeof(data_header) - sizeUsed; + headerSpace = MAX_FREE_BUFFER_SIZE - sizeUsed; } data_header *header = create_data_header(headerSpace); @@ -760,13 +776,11 @@ node = (data_node *)add_data_node(header); // this can't fail as we made sure there will be enough header space - init_data_node(node, headerSpace); - node->header_space = header->data_space; + init_first_data_node(node); node->tail_space -= sizeUsed; node->used = sizeUsed; node->offset = buffer->size; - header->first_node = node; buffer->size += sizeUsed; sizeAdded += sizeUsed; From axeld at pinc-software.de Wed Apr 11 12:18:41 2007 From: axeld at pinc-software.de (Axel =?iso-8859-15?q?D=F6rfler?=) Date: Wed, 11 Apr 2007 12:18:41 +0200 CEST Subject: [Haiku-commits] =?iso-8859-15?q?r20639_-_in_haiku/trunk/src/add-o?= =?iso-8859-15?q?ns/kernel/network=3A_protocols/tcp_stack?= In-Reply-To: <9c46321e0704100955w77a786aagf122150e91527694@mail.gmail.com> Message-ID: <4417144318-BeMail@zon> "Hugo Santos" wrote: > Axel, can you have a look at the adding new buffers code in > prepend_size please? Just to make sure it makes sense from a > data_node/data_header POV. (Ignore the fact that the else branches.. > i'll fix that in a subsequent commit). Looks good - I've improved init_first_data_node() a bit, which makes the whole thing (and its other usages) a bit clearer. > > - use B_RELEASE_IF_WAITING_ONLY in the TCP WaitList. Note that this feature is only available on Haiku. Bye, Axel. From axeld at mail.berlios.de Wed Apr 11 16:11:39 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Wed, 11 Apr 2007 16:11:39 +0200 Subject: [Haiku-commits] r20652 - haiku/trunk/src/libs/icon Message-ID: <200704111411.l3BEBd2e028770@sheep.berlios.de> Author: axeld Date: 2007-04-11 16:11:39 +0200 (Wed, 11 Apr 2007) New Revision: 20652 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20652&view=rev Modified: haiku/trunk/src/libs/icon/IconUtils.cpp Log: Fixed build under BeOS. Modified: haiku/trunk/src/libs/icon/IconUtils.cpp =================================================================== --- haiku/trunk/src/libs/icon/IconUtils.cpp 2007-04-11 10:17:26 UTC (rev 20651) +++ haiku/trunk/src/libs/icon/IconUtils.cpp 2007-04-11 14:11:39 UTC (rev 20652) @@ -23,6 +23,10 @@ #include "IconRenderer.h" #include "FlatIconImporter.h" +#ifndef HAIKU_TARGET_PLATFORM_HAIKU +# define B_MINI_ICON_TYPE 'MICN' +# define B_LARGE_ICON_TYPE 'ICON' +#endif using namespace BPrivate::Icon; using std::nothrow; @@ -72,8 +76,12 @@ size, result); if (ret < B_OK) { // try to fallback to vector icon +#ifdef HAIKU_TARGET_PLATFORM_HAIKU BBitmap temp(result->Bounds(), B_BITMAP_NO_SERVER_LINK, B_RGBA32); +#else + BBitmap temp(result->Bounds(), B_RGBA32); +#endif ret = temp.InitCheck(); if (ret < B_OK) break; From hugosantos at mail.berlios.de Wed Apr 11 16:58:49 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Wed, 11 Apr 2007 16:58:49 +0200 Subject: [Haiku-commits] r20653 - haiku/trunk/src/add-ons/kernel/network/protocols/tcp Message-ID: <200704111458.l3BEwnou032441@sheep.berlios.de> Author: hugosantos Date: 2007-04-11 16:58:39 +0200 (Wed, 11 Apr 2007) New Revision: 20653 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20653&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp Log: non-writeable states are always non-blockable from a write() POV. Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-11 14:11:39 UTC (rev 20652) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-11 14:58:39 UTC (rev 20653) @@ -64,7 +64,7 @@ FLAG_OPTION_WINDOW_SHIFT = 0x01, FLAG_OPTION_TIMESTAMP = 0x02, // TODO: Should FLAG_NO_RECEIVE apply as well to received connections? - // That is, what is excepected from accept() after a shutdown() + // That is, what is expected from accept() after a shutdown() // is performed on a listen()ing socket. FLAG_NO_RECEIVE = 0x04, }; @@ -540,8 +540,18 @@ TCPEndpoint::SendAvailable() { RecursiveLocker locker(fLock); - TRACE("SendAvailable(): %li", fSendQueue.Free()); - return fSendQueue.Free(); + + ssize_t available; + + if (fState == FINISH_SENT || fState == FINISH_ACKNOWLEDGED + || fState == CLOSING || fState == WAIT_FOR_FINISH_ACKNOWLEDGE + || fState == TIME_WAIT || fState == LISTEN || fState == CLOSED) + available = EPIPE; + else + available = fSendQueue.Free(); + + TRACE("SendAvailable(): %li", available); + return available; } From axeld at mail.berlios.de Wed Apr 11 17:50:12 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Wed, 11 Apr 2007 17:50:12 +0200 Subject: [Haiku-commits] r20654 - haiku/trunk/src/system/kernel/vm Message-ID: <200704111550.l3BFoC6r003424@sheep.berlios.de> Author: axeld Date: 2007-04-11 17:50:11 +0200 (Wed, 11 Apr 2007) New Revision: 20654 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20654&view=rev Modified: haiku/trunk/src/system/kernel/vm/vm_cache.c Log: The busy page could also be in another cache that is layered upon the merged one, so we can't easily check if the remaining mappings are valid - therefore I disabled the check completely. Modified: haiku/trunk/src/system/kernel/vm/vm_cache.c =================================================================== --- haiku/trunk/src/system/kernel/vm/vm_cache.c 2007-04-11 14:58:39 UTC (rev 20653) +++ haiku/trunk/src/system/kernel/vm/vm_cache.c 2007-04-11 15:50:11 UTC (rev 20654) @@ -539,10 +539,12 @@ vm_cache_remove_page(cacheRef, page); vm_cache_insert_page(consumerRef, page, (off_t)page->cache_offset << PAGE_SHIFT); +#if 0 } else if (consumerPage->state != PAGE_STATE_BUSY && (page->mappings != 0 || page->wired_count != 0)) { panic("page %p has still mappings (consumer cache %p)!", page, consumerRef); +#endif } } From axeld at mail.berlios.de Wed Apr 11 18:01:04 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Wed, 11 Apr 2007 18:01:04 +0200 Subject: [Haiku-commits] r20655 - in haiku/trunk/src: apps apps/networkstatus servers/net Message-ID: <200704111601.l3BG14ZU004563@sheep.berlios.de> Author: axeld Date: 2007-04-11 18:01:02 +0200 (Wed, 11 Apr 2007) New Revision: 20655 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20655&view=rev Added: haiku/trunk/src/apps/networkstatus/ haiku/trunk/src/apps/networkstatus/Jamfile haiku/trunk/src/apps/networkstatus/NetworkStatus.cpp haiku/trunk/src/apps/networkstatus/NetworkStatus.h haiku/trunk/src/apps/networkstatus/NetworkStatus.rdef haiku/trunk/src/apps/networkstatus/NetworkStatusIcons.h haiku/trunk/src/apps/networkstatus/NetworkStatusIcons.rdef haiku/trunk/src/apps/networkstatus/NetworkStatusView.cpp haiku/trunk/src/apps/networkstatus/NetworkStatusView.h haiku/trunk/src/apps/networkstatus/NetworkStatusWindow.cpp haiku/trunk/src/apps/networkstatus/NetworkStatusWindow.h Removed: haiku/trunk/src/servers/net/NetworkStatusIcons.h haiku/trunk/src/servers/net/NetworkStatusIcons.rdef haiku/trunk/src/servers/net/StatusReplicant.cpp haiku/trunk/src/servers/net/StatusReplicant.h Modified: haiku/trunk/src/apps/Jamfile haiku/trunk/src/servers/net/AutoconfigLooper.cpp haiku/trunk/src/servers/net/DHCPClient.cpp haiku/trunk/src/servers/net/Jamfile haiku/trunk/src/servers/net/NetServer.cpp haiku/trunk/src/servers/net/NetServer.h Log: * Moved the network status replicant into its own application, similar to what ProcessController and PowerStatus are doing. * Currently polls for info only - later, the stack should support listeners for interface related changes. * Also works under BONE (although it doesn't make much sense to use it there). Modified: haiku/trunk/src/apps/Jamfile =================================================================== --- haiku/trunk/src/apps/Jamfile 2007-04-11 15:50:11 UTC (rev 20654) +++ haiku/trunk/src/apps/Jamfile 2007-04-11 16:01:02 UTC (rev 20655) @@ -17,6 +17,7 @@ SubInclude HAIKU_TOP src apps mail ; SubInclude HAIKU_TOP src apps mediaplayer ; SubInclude HAIKU_TOP src apps midiplayer ; +SubInclude HAIKU_TOP src apps networkstatus ; SubInclude HAIKU_TOP src apps people ; SubInclude HAIKU_TOP src apps poorman ; SubInclude HAIKU_TOP src apps powerstatus ; Added: haiku/trunk/src/apps/networkstatus/Jamfile =================================================================== --- haiku/trunk/src/apps/networkstatus/Jamfile 2007-04-11 15:50:11 UTC (rev 20654) +++ haiku/trunk/src/apps/networkstatus/Jamfile 2007-04-11 16:01:02 UTC (rev 20655) @@ -0,0 +1,19 @@ +SubDir HAIKU_TOP src apps networkstatus ; + +SetSubDirSupportedPlatformsBeOSCompatible ; + +UsePrivateHeaders shared ; +UseLibraryHeaders agg icon ; + +local icon_libs ; +if $(TARGET) != haiku { + icon_libs = libicon.a libagg.a ; +} + +Application NetworkStatus : + NetworkStatusWindow.cpp + NetworkStatusView.cpp + NetworkStatus.cpp + : be $(icon_libs) $(NETWORK_LIBS) + : NetworkStatus.rdef NetworkStatusIcons.rdef + ; Added: haiku/trunk/src/apps/networkstatus/NetworkStatus.cpp =================================================================== --- haiku/trunk/src/apps/networkstatus/NetworkStatus.cpp 2007-04-11 15:50:11 UTC (rev 20654) +++ haiku/trunk/src/apps/networkstatus/NetworkStatus.cpp 2007-04-11 16:01:02 UTC (rev 20655) @@ -0,0 +1,135 @@ +/* + * Copyright 2006-2007, Haiku, Inc. All Rights Reserved. + * Distributed under the terms of the MIT License. + * + * Authors: + * Axel D?rfler, axeld at pinc-software.de + */ + + +#include "NetworkStatus.h" +#include "NetworkStatusWindow.h" + +#include +#include +#include +#include + +#include +#include +#include + + +class NetworkStatus : public BApplication { + public: + NetworkStatus(); + virtual ~NetworkStatus(); + + virtual void ReadyToRun(); + virtual void AboutRequested(); +}; + + +const char* kSignature = "application/x-vnd.Haiku-NetworkStatus"; +const char* kDeskbarSignature = "application/x-vnd.Be-TSKB"; +const char* kDeskbarItemName = "NetworkStatus"; + + +status_t +our_image(image_info& image) +{ + int32 cookie = 0; + while (get_next_image_info(B_CURRENT_TEAM, &cookie, &image) == B_OK) { + if ((char *)our_image >= (char *)image.text + && (char *)our_image <= (char *)image.text + image.text_size) + return B_OK; + } + + return B_ERROR; +} + + +// #pragma mark - + + +NetworkStatus::NetworkStatus() + : BApplication(kSignature) +{ +} + + +NetworkStatus::~NetworkStatus() +{ +} + + +void +NetworkStatus::ReadyToRun() +{ + bool isInstalled = false; + bool isDeskbarRunning = true; + + { + // if the Deskbar is not alive at this point, it might be after having + // acknowledged the requester below + BDeskbar deskbar; +#ifdef HAIKU_TARGET_PLATFORM_HAIKU + isDeskbarRunning = deskbar.IsRunning(); +#endif + isInstalled = deskbar.HasItem(kDeskbarItemName); + } + + if (isDeskbarRunning && !isInstalled) { + BAlert* alert = new BAlert("", "Do you want NetworkStatus to live in the Deskbar?", + "Don't", "Install", NULL, B_WIDTH_AS_USUAL, B_WARNING_ALERT); + alert->SetShortcut(0, B_ESCAPE); + + if (alert->Go()) { + image_info info; + entry_ref ref; + + if (our_image(info) == B_OK + && get_ref_for_path(info.name, &ref) == B_OK) { + BDeskbar deskbar; + deskbar.AddItem(&ref); + } + + Quit(); + return; + } + } + + BWindow* window = new NetworkStatusWindow(); + window->Show(); +} + + +void +NetworkStatus::AboutRequested() +{ + BWindow* window = WindowAt(0); + if (window == NULL) + return; + + BView* view = window->FindView(kDeskbarItemName); + if (view == NULL) + return; + + BMessenger target((BHandler*)view); + BMessage about(B_ABOUT_REQUESTED); + target.SendMessage(&about); +} + + +// #pragma mark - + + +int +main(int, char**) +{ + NetworkStatus app; + app.Run(); + + return 0; +} + Added: haiku/trunk/src/apps/networkstatus/NetworkStatus.h =================================================================== --- haiku/trunk/src/apps/networkstatus/NetworkStatus.h 2007-04-11 15:50:11 UTC (rev 20654) +++ haiku/trunk/src/apps/networkstatus/NetworkStatus.h 2007-04-11 16:01:02 UTC (rev 20655) @@ -0,0 +1,20 @@ +/* + * Copyright 2007, Haiku, Inc. All Rights Reserved. + * Distributed under the terms of the MIT License. + * + * Authors: + * Axel D?rfler, axeld at pinc-software.de + */ +#ifndef NETWORK_STATUS_H +#define NETWORK_STATUS_H + + +#include + + +extern const char* kSignature; +extern const char* kDeskbarItemName; + +status_t our_image(image_info& image); + +#endif // NETWORK_STATUS_H Added: haiku/trunk/src/apps/networkstatus/NetworkStatus.rdef =================================================================== --- haiku/trunk/src/apps/networkstatus/NetworkStatus.rdef 2007-04-11 15:50:11 UTC (rev 20654) +++ haiku/trunk/src/apps/networkstatus/NetworkStatus.rdef 2007-04-11 16:01:02 UTC (rev 20655) @@ -0,0 +1,42 @@ + +resource(1, "BEOS:APP_SIG") #'MIMS' "application/x-vnd.Haiku-NetworkStatus"; + +resource app_flags B_SINGLE_LAUNCH; + +resource app_version { + major = 1, + middle = 0, + minor = 0, + + variety = B_APPV_DEVELOPMENT, + internal = 0, + + short_info = "NetworkStatus", + long_info = "NetworkStatus ?2007 Haiku" +}; + +#ifdef HAIKU_TARGET_PLATFORM_HAIKU + +resource vector_icon { + $"6E63696608050005B8020016023A692E36692FBA2ECD3E2ECD4B89A449631800" + $"5CFF8305E7020106023C00000000000000003C00004680004680000029B6FFFF" + $"035492020106023C00000000000000003C0000468000468000009FF699FF049A" + $"4304016E020006023959B6382F60BA2F603B59B647C1424B11D30056FF22FF05" + $"D0050C0A044C60516060505C4E02043334BD6E34B7B534263926BBDC26BE0F33" + $"3EB7B53EBD6E3E403940BE0F40BBDC0A06513A5A3D5A504C5E425842440A044C" + $"484C5E425842440A04513A5A3D4C4842440A044C485A3D5A504C5E0404BE404A" + $"3246324A323E4236423C42323A3202042E22BB3722B5F022222E22B5F022BB37" + $"2E3AB5F03ABB373A3A2E3ABB373AB5F00608BFDBB506B560B506B560B443B639" + $"222E22B75822BAB3B718BD20B52EBC80B718BD20283628322A34263024302E28" + $"28282A2826060CA2EBAF2E28B98632263428302E302C303036323436BBB3BC32" + $"BBB3BC32BCB7BB523A2E3ABA063AB668B9EEB3FDBBE9B493B9EEB3FD2E243026" + $"0614BFDDAFABE82E22B90C22B72B22B506B560B5E6B468B506B5602828282628" + $"2A242E30283226302A3436B718BD20B718BD20B78FBD462E3AB80F3AB9C53ABB" + $"B3BC32BADCBCECBBB3BC3234363632302E3030302C34283226B953282E30262E" + $"24B9EEB3FDB9EEB3FDB980B3DD02042A50B84D50B5AA50B49756B497C732B497" + $"C9D52A5CB5AA5CB84D5C305630C9D530C732090A06020001000A000306020710" + $"01178400040A010103000A030104000A020105000A04010A000A05020809000A" + $"00010B1001178800040A07010B00" +}; + +#endif Copied: haiku/trunk/src/apps/networkstatus/NetworkStatusIcons.h (from rev 20647, haiku/trunk/src/servers/net/NetworkStatusIcons.h) Copied: haiku/trunk/src/apps/networkstatus/NetworkStatusIcons.rdef (from rev 20647, haiku/trunk/src/servers/net/NetworkStatusIcons.rdef) Added: haiku/trunk/src/apps/networkstatus/NetworkStatusView.cpp =================================================================== --- haiku/trunk/src/apps/networkstatus/NetworkStatusView.cpp 2007-04-11 15:50:11 UTC (rev 20654) +++ haiku/trunk/src/apps/networkstatus/NetworkStatusView.cpp 2007-04-11 16:01:02 UTC (rev 20655) @@ -0,0 +1,469 @@ +/* + * Copyright 2006-2007, Haiku, Inc. All Rights Reserved. + * Distributed under the terms of the MIT License. + * + * Authors: + * Axel D?rfler, axeld at pinc-software.de + * Hugo Santos, hugosantos at gmail.com + */ + + +#include "NetworkStatusView.h" + +#include "NetworkStatus.h" +#include "NetworkStatusIcons.h" + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#include +#include +#include +#include +#include +#include +#include +#include + +#ifndef HAIKU_TARGET_PLATFORM_HAIKU +// BONE compatibility +# define IF_NAMESIZE IFNAMSIZ +# define IFF_LINK 0 +# define IFF_CONFIGURING 0 +# define ifc_value ifc_val +#endif + +static const char *kStatusDescriptions[] = { + "Unknown", + "No Link", + "No stateful configuration", + "Configuring", + "Ready" +}; + +extern "C" _EXPORT BView *instantiate_deskbar_item(void); + + +const uint32 kMsgUpdate = 'updt'; +const uint32 kMsgShowConfiguration = 'shcf'; + +const uint32 kMinIconWidth = 16; +const uint32 kMinIconHeight = 16; + +const bigtime_t kUpdateInterval = 1000000; + // every second + + +NetworkStatusView::NetworkStatusView(BRect frame, int32 resizingMode, + bool inDeskbar) + : BView(frame, kDeskbarItemName, resizingMode, + B_WILL_DRAW | B_FRAME_EVENTS | B_FULL_UPDATE_ON_RESIZE), + fInDeskbar(inDeskbar), + fStatus(kStatusUnknown) +{ + _Init(); + + if (!inDeskbar) { + // we were obviously added to a standard window - let's add a dragger + frame.OffsetTo(B_ORIGIN); + frame.top = frame.bottom - 7; + frame.left = frame.right - 7; + BDragger* dragger = new BDragger(frame, this, + B_FOLLOW_RIGHT | B_FOLLOW_BOTTOM); + AddChild(dragger); + } else + _Update(); +} + + +NetworkStatusView::NetworkStatusView(BMessage* archive) + : BView(archive) +{ + _Init(); +} + + +NetworkStatusView::~NetworkStatusView() +{ +} + + +void +NetworkStatusView::_Init() +{ + fMessageRunner = NULL; + + for (int i = 0; i < kStatusCount; i++) { + fBitmaps[i] = NULL; + } + + _UpdateBitmaps(); +} + + +void +NetworkStatusView::_UpdateBitmaps() +{ + for (int i = 0; i < kStatusCount; i++) { + delete fBitmaps[i]; + fBitmaps[i] = NULL; + } + + image_info info; + if (our_image(info) != B_OK) + return; + + BFile file(info.name, B_READ_ONLY); + if (file.InitCheck() < B_OK) + return; + + BResources resources(&file); +#ifdef HAIKU_TARGET_PLATFORM_HAIKU + if (resources.InitCheck() < B_OK) + return; +#endif + + for (int i = 0; i < kStatusCount; i++) { + const void* data = NULL; + size_t size; + data = resources.LoadResource(B_VECTOR_ICON_TYPE, + kNetworkStatusNoDevice + i, &size); + if (data != NULL) { + BBitmap* icon = new BBitmap(Bounds(), B_RGB32); + if (icon->InitCheck() == B_OK + && BIconUtils::GetVectorIcon((const uint8 *)data, + size, icon) == B_OK) { + fBitmaps[i] = icon; + } else + delete icon; + } + } +} + + +void +NetworkStatusView::_Quit() +{ + if (fInDeskbar) { + BDeskbar deskbar; + deskbar.RemoveItem(kDeskbarItemName); + } else + be_app->PostMessage(B_QUIT_REQUESTED); +} + + +NetworkStatusView * +NetworkStatusView::Instantiate(BMessage* archive) +{ + if (!validate_instantiation(archive, "NetworkStatusView")) + return NULL; + + return new NetworkStatusView(archive); +} + + +status_t +NetworkStatusView::Archive(BMessage* archive, bool deep) const +{ + status_t status = BView::Archive(archive, deep); + if (status == B_OK) + status = archive->AddString("add_on", kSignature); + if (status == B_OK) + status = archive->AddString("class", "NetworkStatusView"); + + return status; +} + + +void +NetworkStatusView::AttachedToWindow() +{ + BView::AttachedToWindow(); + if (Parent()) + SetViewColor(Parent()->ViewColor()); + else + SetViewColor(ui_color(B_PANEL_BACKGROUND_COLOR)); + + SetLowColor(ViewColor()); + + BMessage update(kMsgUpdate); + fMessageRunner = new BMessageRunner(this, &update, kUpdateInterval); + + fSocket = socket(AF_INET, SOCK_DGRAM, 0); + _Update(); +} + + +void +NetworkStatusView::DetachedFromWindow() +{ + delete fMessageRunner; + close(fSocket); +} + + +void +NetworkStatusView::MessageReceived(BMessage* message) +{ + switch (message->what) { + case kMsgUpdate: + _Update(); + break; + + case kMsgShowConfiguration: + _ShowConfiguration(message); + break; + + case B_ABOUT_REQUESTED: + _AboutRequested(); + break; + + case B_QUIT_REQUESTED: + _Quit(); + break; + + default: + BView::MessageReceived(message); + } +} + + +void +NetworkStatusView::FrameResized(float width, float height) +{ + _UpdateBitmaps(); +} + + +void +NetworkStatusView::Draw(BRect updateRect) +{ + if (fBitmaps[fStatus] == NULL) + return; + + SetDrawingMode(B_OP_ALPHA); + DrawBitmap(fBitmaps[fStatus]); + SetDrawingMode(B_OP_COPY); +} + + +void +NetworkStatusView::_ShowConfiguration(BMessage* message) +{ + static const struct information_entry { + const char *label; + int32 control; + } kInformationEntries[] = { + { "Address", SIOCGIFADDR }, + { "Broadcast", SIOCGIFBRDADDR }, + { "Netmask", SIOCGIFNETMASK }, + { NULL } + }; + + const char *name; + if (message->FindString("interface", &name) != B_OK) + return; + + ifreq request; + if (!_PrepareRequest(request, name)) + return; + + BString text = name; + text += " information:\n"; + size_t boldLength = text.Length(); + + for (int i = 0; kInformationEntries[i].label; i++) { + if (ioctl(fSocket, kInformationEntries[i].control, &request, + sizeof(request)) < 0) { + continue; + } + + char address[32]; + sockaddr_in* inetAddress = NULL; + switch (kInformationEntries[i].control) { + case SIOCGIFNETMASK: + inetAddress = (sockaddr_in*)&request.ifr_mask; + break; + default: + inetAddress = (sockaddr_in*)&request.ifr_addr; + break; + } + + if (inet_ntop(AF_INET, &inetAddress->sin_addr, address, + sizeof(address)) == NULL) { + return; + } + + text += "\n"; + text += kInformationEntries[i].label; + text += ": "; + text += address; + } + + BAlert* alert = new BAlert(name, text.String(), "Ok"); + BTextView* view = alert->TextView(); + BFont font; + + view->SetStylable(true); + view->GetFont(&font); + font.SetFace(B_BOLD_FACE); + view->SetFontAndColor(0, boldLength, &font); + + alert->Go(NULL); +} + + +void +NetworkStatusView::MouseDown(BPoint point) +{ + BPopUpMenu *menu = new BPopUpMenu(B_EMPTY_STRING, false, false); + menu->SetFont(be_plain_font); + + for (int32 i = 0; i < fInterfaces.CountItems(); i++) { + BString& name = *fInterfaces.ItemAt(i); + + BString label = name; + label += ": "; + label += kStatusDescriptions[ + _DetermineInterfaceStatus(name.String())]; + + BMessage* info = new BMessage(kMsgShowConfiguration); + info->AddString("interface", name.String()); + menu->AddItem(new BMenuItem(label.String(), info)); + } + + menu->AddSeparatorItem(); + menu->AddItem(new BMenuItem("About" B_UTF8_ELLIPSIS, + new BMessage(B_ABOUT_REQUESTED))); + if (fInDeskbar) + menu->AddItem(new BMenuItem("Quit", new BMessage(B_QUIT_REQUESTED))); + menu->SetTargetForItems(this); + + ConvertToScreen(&point); + menu->Go(point, true, false, true); +} + + +void +NetworkStatusView::_AboutRequested() +{ + BAlert *alert = new BAlert("about", "NetworkStatus\n" + "\twritten by Axel D?rfler and Hugo Santos\n" + "\tCopyright 2007, Haiku, Inc.\n", "Ok"); + BTextView *view = alert->TextView(); + BFont font; + + view->SetStylable(true); + + view->GetFont(&font); + font.SetSize(18); + font.SetFace(B_BOLD_FACE); + view->SetFontAndColor(0, 13, &font); + + alert->Go(); +} + + +bool +NetworkStatusView::_PrepareRequest(struct ifreq& request, const char* name) +{ + if (strlen(name) > IF_NAMESIZE) + return false; + + strcpy(request.ifr_name, name); + return true; +} + + +int32 +NetworkStatusView::_DetermineInterfaceStatus(const char* name) +{ + ifreq request; + if (!_PrepareRequest(request, name)) + return kStatusUnknown; + + uint32 flags = 0; + if (ioctl(fSocket, SIOCGIFFLAGS, &request, sizeof(struct ifreq)) == 0) + flags = request.ifr_flags; + + int32 status = kStatusNoLink; + + // TODO: no kStatusLinkNoConfig yet + + if (flags & IFF_CONFIGURING) + status = kStatusConnecting; + else if (flags & (IFF_UP | IFF_LINK) == IFF_UP | IFF_LINK) + status = kStatusReady; + + return status; +} + + +void +NetworkStatusView::_Update(bool force) +{ + // iterate over all interfaces and retrieve minimal status + + ifconf config; + config.ifc_len = sizeof(config.ifc_value); + if (ioctl(fSocket, SIOCGIFCOUNT, &config, sizeof(struct ifconf)) < 0) + return; + + uint32 count = (uint32)config.ifc_value; + if (count == 0) + return; + + void *buffer = malloc(count * sizeof(struct ifreq)); + if (buffer == NULL) + return; + + config.ifc_len = count * sizeof(struct ifreq); + config.ifc_buf = buffer; + if (ioctl(fSocket, SIOCGIFCONF, &config, sizeof(struct ifconf)) < 0) + return; + + ifreq *interface = (ifreq *)buffer; + + int32 oldStatus = fStatus; + fStatus = kStatusUnknown; + fInterfaces.MakeEmpty(); + + for (uint32 i = 0; i < count; i++) { + if (strncmp(interface->ifr_name, "loop", 4) && interface->ifr_name[0]) { + fInterfaces.AddItem(new BString(interface->ifr_name)); + int32 status = _DetermineInterfaceStatus(interface->ifr_name); + if (status > fStatus) + fStatus = status; + } + + interface = (ifreq *)((addr_t)interface + IF_NAMESIZE + + interface->ifr_addr.sa_len); + } + + free(buffer); + + if (fStatus != oldStatus) + Invalidate(); +} + + +// #pragma mark - + + +extern "C" _EXPORT BView * +instantiate_deskbar_item(void) +{ + return new NetworkStatusView(BRect(0, 0, 15, 15), B_FOLLOW_NONE, true); +} + Added: haiku/trunk/src/apps/networkstatus/NetworkStatusView.h =================================================================== --- haiku/trunk/src/apps/networkstatus/NetworkStatusView.h 2007-04-11 15:50:11 UTC (rev 20654) +++ haiku/trunk/src/apps/networkstatus/NetworkStatusView.h 2007-04-11 16:01:02 UTC (rev 20655) @@ -0,0 +1,65 @@ +/* + * Copyright 2006-2007, Haiku, Inc. All Rights Reserved. + * Distributed under the terms of the MIT License. + * + * Authors: + * Axel D?rfler, axeld at pinc-software.de + */ +#ifndef NETWORK_STATUS_VIEW_H +#define NETWORK_STATUS_VIEW_H + + +#include +#include + +class BMessageRunner; + + +enum { + kStatusUnknown = 0, + kStatusNoLink, + kStatusLinkNoConfig, + kStatusConnecting, + kStatusReady, + + kStatusCount +}; + +class NetworkStatusView : public BView { + public: + NetworkStatusView(BRect frame, int32 resizingMode, + bool inDeskbar = false); + NetworkStatusView(BMessage* archive); + virtual ~NetworkStatusView(); + + static NetworkStatusView* Instantiate(BMessage* archive); + virtual status_t Archive(BMessage* archive, bool deep = true) const; + + virtual void AttachedToWindow(); + virtual void DetachedFromWindow(); + + virtual void MessageReceived(BMessage* message); + virtual void FrameResized(float width, float height); + virtual void MouseDown(BPoint where); + virtual void Draw(BRect updateRect); + + private: + void _AboutRequested(); + void _Quit(); + void _Init(); + void _UpdateBitmaps(); + void _ShowConfiguration(BMessage* message); + bool _PrepareRequest(struct ifreq& request, + const char* name); + int32 _DetermineInterfaceStatus(const char* name); + void _Update(bool force = false); + + BMessageRunner* fMessageRunner; + BObjectList fInterfaces; + bool fInDeskbar; + BBitmap* fBitmaps[kStatusCount]; + int32 fStatus; + int fSocket; +}; + +#endif // NETWORK_STATUS_VIEW_H Added: haiku/trunk/src/apps/networkstatus/NetworkStatusWindow.cpp =================================================================== --- haiku/trunk/src/apps/networkstatus/NetworkStatusWindow.cpp 2007-04-11 15:50:11 UTC (rev 20654) +++ haiku/trunk/src/apps/networkstatus/NetworkStatusWindow.cpp 2007-04-11 16:01:02 UTC (rev 20655) @@ -0,0 +1,41 @@ +/* + * Copyright 2006-2007, Haiku, Inc. All Rights Reserved. + * Distributed under the terms of the MIT License. + * + * Authors: + * Axel D?rfler, axeld at pinc-software.de + */ + + +#include "NetworkStatusWindow.h" +#include "NetworkStatusView.h" + +#include + + +NetworkStatusWindow::NetworkStatusWindow() + : BWindow(BRect(150, 150, 249, 249), "NetworkStatus", B_TITLED_WINDOW, + B_NOT_ZOOMABLE | B_ASYNCHRONOUS_CONTROLS) +{ + BView* topView = new BView(Bounds(), NULL, B_FOLLOW_ALL, B_WILL_DRAW); + topView->SetViewColor(ui_color(B_PANEL_BACKGROUND_COLOR)); + AddChild(topView); + + SetSizeLimits(25, 265, 25, 265); + + topView->AddChild(new NetworkStatusView(Bounds().InsetByCopy(5, 5), + B_FOLLOW_ALL)); +} + + +NetworkStatusWindow::~NetworkStatusWindow() +{ +} + + +bool +NetworkStatusWindow::QuitRequested() +{ + be_app->PostMessage(B_QUIT_REQUESTED); + return true; +} Added: haiku/trunk/src/apps/networkstatus/NetworkStatusWindow.h =================================================================== --- haiku/trunk/src/apps/networkstatus/NetworkStatusWindow.h 2007-04-11 15:50:11 UTC (rev 20654) +++ haiku/trunk/src/apps/networkstatus/NetworkStatusWindow.h 2007-04-11 16:01:02 UTC (rev 20655) @@ -0,0 +1,23 @@ +/* + * Copyright 2006-2007, Haiku, Inc. All Rights Reserved. + * Distributed under the terms of the MIT License. + * + * Authors: + * Axel D?rfler, axeld at pinc-software.de + */ +#ifndef NETWORK_STATUS_WINDOW_H +#define NETWORK_STATUS_WINDOW_H + + +#include + + +class NetworkStatusWindow : public BWindow { + public: + NetworkStatusWindow(); + virtual ~NetworkStatusWindow(); + + virtual bool QuitRequested(); +}; + +#endif // NETWORK_STATUS_WINDOW_H Modified: haiku/trunk/src/servers/net/AutoconfigLooper.cpp =================================================================== --- haiku/trunk/src/servers/net/AutoconfigLooper.cpp 2007-04-11 15:50:11 UTC (rev 20654) +++ haiku/trunk/src/servers/net/AutoconfigLooper.cpp 2007-04-11 16:01:02 UTC (rev 20655) @@ -1,5 +1,5 @@ /* - * Copyright 2006, Haiku, Inc. All Rights Reserved. + * Copyright 2006-2007, Haiku, Inc. All Rights Reserved. * Distributed under the terms of the MIT License. * * Authors: @@ -40,11 +40,23 @@ void AutoconfigLooper::_ReadyToRun() { - BMessage interface(kMsgConfigureInterface); - interface.AddString("device", fDevice.String()); - interface.AddInt32("net:status", kStatusPreparing); - fTarget.SendMessage(&interface); + ifreq request; + if (!prepare_request(request, fDevice.String())) + return; + // set IFF_CONFIGURING flag on interface + + int socket = ::socket(AF_LINK, SOCK_DGRAM, 0); + if (socket < 0) + return; + + if (ioctl(socket, SIOCGIFFLAGS, &request, sizeof(struct ifreq)) == 0) { + request.ifr_flags |= IFF_CONFIGURING; + ioctl(socket, SIOCSIFFLAGS, &request, sizeof(struct ifreq)); + } + + close(socket); + // start with DHCP DHCPClient* client = new DHCPClient(fTarget, fDevice.String()); @@ -62,7 +74,9 @@ // TODO: have a look at zeroconf // TODO: this could also be done add-on based - interface.ReplaceInt32("net:status", kStatusLinkNoConfig); + BMessage interface(kMsgConfigureInterface); + interface.AddString("device", fDevice.String()); + interface.AddBool("auto", true); uint8 mac[6]; uint8 last = 56; Modified: haiku/trunk/src/servers/net/DHCPClient.cpp =================================================================== --- haiku/trunk/src/servers/net/DHCPClient.cpp 2007-04-11 15:50:11 UTC (rev 20654) +++ haiku/trunk/src/servers/net/DHCPClient.cpp 2007-04-11 16:01:02 UTC (rev 20655) @@ -474,7 +474,7 @@ fConfiguration.MakeEmpty(); fConfiguration.AddString("device", fDevice.String()); - fConfiguration.AddInt32("net:status", kStatusConnected); + fConfiguration.AddBool("auto", true); BMessage address; address.AddString("family", "inet"); Modified: haiku/trunk/src/servers/net/Jamfile =================================================================== --- haiku/trunk/src/servers/net/Jamfile 2007-04-11 15:50:11 UTC (rev 20654) +++ haiku/trunk/src/servers/net/Jamfile 2007-04-11 16:01:02 UTC (rev 20655) @@ -1,13 +1,12 @@ SubDir HAIKU_TOP src servers net ; UsePrivateHeaders app net ; -UseLibraryHeaders icon ; #UseHeaders [ FDirName $(HAIKU_TOP) src add-ons kernel network ppp shared libppp headers ] ; #UseHeaders [ FDirName $(HAIKU_TOP) src add-ons kernel network ppp shared libkernelppp headers ] ; #UseHeaders [ FDirName $(HAIKU_TOP) src tests kits net DialUpPreflet ] ; -AddResources net_server : net_server.rdef NetworkStatusIcons.rdef ; +AddResources net_server : net_server.rdef ; Server net_server : NetServer.cpp @@ -15,7 +14,6 @@ AutoconfigLooper.cpp DHCPClient.cpp Services.cpp - StatusReplicant.cpp : be libnetwork.so $(TARGET_LIBSTDC++) # for PPP Modified: haiku/trunk/src/servers/net/NetServer.cpp =================================================================== --- haiku/trunk/src/servers/net/NetServer.cpp 2007-04-11 15:50:11 UTC (rev 20654) +++ haiku/trunk/src/servers/net/NetServer.cpp 2007-04-11 16:01:02 UTC (rev 20655) @@ -11,7 +11,6 @@ #include "NetServer.h" #include "Services.h" #include "Settings.h" -#include "StatusReplicant.h" #include #include @@ -39,12 +38,10 @@ #include -const char *kSignature = "application/x-vnd.haiku-net_server"; -static const char *kDeskbarSignature = "application/x-vnd.Be-TSKB"; +static const char *kSignature = "application/x-vnd.haiku-net_server"; typedef std::map LooperMap; -typedef std::map StatusMap; class NetServer : public BServer { @@ -69,15 +66,10 @@ void _ConfigureInterfaces(int socket, BMessage* _missingDevice = NULL); [... truncated: 238 lines follow ...] From axeld at mail.berlios.de Wed Apr 11 18:07:59 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Wed, 11 Apr 2007 18:07:59 +0200 Subject: [Haiku-commits] r20656 - haiku/trunk/build/jam Message-ID: <200704111607.l3BG7xwH005170@sheep.berlios.de> Author: axeld Date: 2007-04-11 18:07:58 +0200 (Wed, 11 Apr 2007) New Revision: 20656 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20656&view=rev Modified: haiku/trunk/build/jam/HaikuImage Log: * Added telnetd (does not work yet for whatever reason), and NetworkStatus to the image. * Moved "nc" to the alphabetically ordered position. Modified: haiku/trunk/build/jam/HaikuImage =================================================================== --- haiku/trunk/build/jam/HaikuImage 2007-04-11 16:01:02 UTC (rev 20655) +++ haiku/trunk/build/jam/HaikuImage 2007-04-11 16:07:58 UTC (rev 20656) @@ -29,13 +29,13 @@ idestatus ifconfig install installsound iroster isvolume join keymap kill less lessecho lesskey link listarea listattr listdev listimage listport listres listsem ln locate logger logname ls lsindex m4 make - makebootable nc md5sum merge mimeset mkdos mkdir mkindex modifiers mount - mount_nfs mountvolume mv netstat nl od open pack_cis paste patch pathchk pc + makebootable md5sum merge mimeset mkdos mkdir mkindex modifiers mount + mount_nfs mountvolume mv nc netstat nl od open pack_cis paste patch pathchk pc ping play playfile playsound playwav pr prio printenv printf ps ptx pwd query quit release renice rescan rlog rm rmattr rmindex rmdir roster route safemode screen_blanker sed settype setversion setvolume seq sh shar shutdown sleep sort split strace stty su sum sync sysinfo tac tail tar - tcpdump tee telnet test top touch tput tr traceroute translate true tsort + tcpdump tee telnet telnetd test top touch tput tr traceroute translate true tsort tty uname unchop unexpand unmount uniq unrar unshar unzip unzipsfx updatedb uptime usb_dev_info uudecode uuencode vdir version vim waitfor wc wget whoami xargs xres yes zdiff zforce zgrep zip zipcloak zipgrep zipnote @@ -45,7 +45,7 @@ BEOS_APPS = Terminal Expander People ShowImage Pulse ProcessController SoundRecorder Magnify DiskProbe AboutHaiku StyledEdit Installer Workspaces $(X86_ONLY)Cortex $(X86_ONLY)CortexAddOnHost MediaPlayer DeskCalc MidiPlayer - Icon-O-Matic Mail CDPlayer + Icon-O-Matic Mail CDPlayer NetworkStatus ; BEOS_PREFERENCES = Appearance Backgrounds DataTranslations E-mail FileTypes Fonts Media Menu Mouse Keyboard Keymap Printers Screen ScreenSaver Sounds From hugosantos at mail.berlios.de Wed Apr 11 18:41:17 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Wed, 11 Apr 2007 18:41:17 +0200 Subject: [Haiku-commits] r20657 - in haiku/trunk: headers/private/net src/add-ons/kernel/network/datalink_protocols/arp src/add-ons/kernel/network/datalink_protocols/ethernet_frame src/add-ons/kernel/network/protocols/icmp src/add-ons/kernel/network/protocols/ipv4 src/add-ons/kernel/network/protocols/tcp src/add-ons/kernel/network/protocols/udp src/add-ons/kernel/network/stack Message-ID: <200704111641.l3BGfHUg029994@sheep.berlios.de> Author: hugosantos Date: 2007-04-11 18:40:40 +0200 (Wed, 11 Apr 2007) New Revision: 20657 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20657&view=rev Modified: haiku/trunk/headers/private/net/NetBufferUtilities.h haiku/trunk/src/add-ons/kernel/network/datalink_protocols/arp/arp.cpp haiku/trunk/src/add-ons/kernel/network/datalink_protocols/ethernet_frame/ethernet_frame.cpp haiku/trunk/src/add-ons/kernel/network/protocols/icmp/icmp.cpp haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.cpp haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp haiku/trunk/src/add-ons/kernel/network/stack/net_buffer.cpp Log: some NetBufferUtility revamp. - introduced base NetBufferFieldReader which deals with obtaining a continuguous field to deal with. - renamed Detach() to Sync() to better express the fact that we may be writing to the buffer. - Fixed IPv4's and ICMP's checksum calculation as it assumed the underlying header was contiguous. - ICMP is now able to reply to ICMP Echo Requests which were split across data nodes. - in split_buffer(), make sure we were able to trim() the new buffer before damaging the original one. Modified: haiku/trunk/headers/private/net/NetBufferUtilities.h =================================================================== --- haiku/trunk/headers/private/net/NetBufferUtilities.h 2007-04-11 16:07:58 UTC (rev 20656) +++ haiku/trunk/headers/private/net/NetBufferUtilities.h 2007-04-11 16:40:40 UTC (rev 20657) @@ -16,129 +16,127 @@ static net_buffer_module_info *Get() { return gBufferModule; } }; -//! A class to retrieve and remove a header from a buffer -template class NetBufferHeader { +//! A class to access a field safely across node boundaries +template +class NetBufferFieldReader { public: - NetBufferHeader(net_buffer *buffer) + NetBufferFieldReader(net_buffer *buffer) : - fBuffer(buffer) + fBuffer(buffer), + fStatus(B_BAD_VALUE) { + if ((Offset + sizeof(Type)) <= buffer->size) { + fStatus = Module::Get()->direct_access(fBuffer, Offset, + sizeof(Type), (void **)&fData); + if (fStatus != B_OK) { + fData = NULL; + fStatus = Module::Get()->read(fBuffer, Offset, + &fDataBuffer, sizeof(Type)); + } + } } - ~NetBufferHeader() - { - Remove(); - } - status_t Status() { - return fBuffer->size < sizeof(Type) ? B_BAD_VALUE : B_OK; + return fStatus; } - status_t - SetTo(net_buffer *buffer) - { - fBuffer = buffer; - return Status(); - } - Type & Data() { - Type *data; - if (Module::Get()->direct_access(fBuffer, 0, sizeof(Type), - (void **)&data) == B_OK) - return *data; + if (fData != NULL) + return *fData; - Module::Get()->read(fBuffer, 0, &fDataBuffer, sizeof(Type)); return fDataBuffer; } - void - Remove() + Type * + operator->() { - Remove(sizeof(Type)); + return &Data(); } - void - Remove(size_t bytes) + Type & + operator*() { - if (fBuffer != NULL) { - Module::Get()->remove_header(fBuffer, bytes); - fBuffer = NULL; - } + return Data(); } void - Detach() + Sync() { + if (fBuffer == NULL) + return; + + if (fData == NULL) + Module::Get()->write(fBuffer, Offset, &fDataBuffer, + sizeof(Type)); + fBuffer = NULL; } - private: + protected: + NetBufferFieldReader() {} + net_buffer *fBuffer; + status_t fStatus; + Type *fData; Type fDataBuffer; }; -//! A class to access a header safely across data node boundaries -template -class NetBufferSafeHeader { +template +class NetBufferField : public NetBufferFieldReader { public: - NetBufferSafeHeader(net_buffer *buffer) - : - fBuffer(buffer) - { - fStatus = Module::Get()->direct_access(fBuffer, 0, - sizeof(Type), (void **)&fData); - if (fStatus != B_OK) { - fData = NULL; - fStatus = Module::Get()->read(fBuffer, 0, &fDataBuffer, - sizeof(Type)); - } - } + NetBufferField(net_buffer *buffer) + : NetBufferFieldReader(buffer) + {} - ~NetBufferSafeHeader() + ~NetBufferField() { - if (fBuffer != NULL) - Detach(); + Sync(); } +}; - status_t - Status() - { - return fStatus; - } +template +class NetBufferHeaderReader : public NetBufferFieldReader { + public: + NetBufferHeaderReader(net_buffer *buffer) + : NetBufferFieldReader(buffer) + {} - Type & - Data() + void + Remove() { - if (fData != NULL) - return *fData; - - return fDataBuffer; + Remove(sizeof(Type)); } void - Detach() + Remove(size_t bytes) { - if (fData == NULL) - Module::Get()->write(fBuffer, 0, &fDataBuffer, sizeof(Type)); - fBuffer = NULL; + if (fBuffer != NULL) { + Module::Get()->remove_header(fBuffer, bytes); + fBuffer = NULL; + } } +}; - protected: - NetBufferSafeHeader() {} +template +class NetBufferHeaderRemover : public NetBufferHeaderReader { + public: + NetBufferHeaderRemover(net_buffer *buffer) + : NetBufferHeaderReader(buffer) + {} - net_buffer *fBuffer; - status_t fStatus; - Type *fData; - Type fDataBuffer; + ~NetBufferHeaderRemover() + { + Remove(); + } }; //! A class to add a header to a buffer template -class NetBufferPrepend : public NetBufferSafeHeader { +class NetBufferPrepend : public NetBufferFieldReader { public: NetBufferPrepend(net_buffer *buffer, size_t size = 0) { @@ -150,6 +148,11 @@ fStatus = Module::Get()->prepend_size(buffer, size, (void **)&fData); } + + ~NetBufferPrepend() + { + Sync(); + } }; #endif // NET_BUFFER_UTILITIES_H Modified: haiku/trunk/src/add-ons/kernel/network/datalink_protocols/arp/arp.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/datalink_protocols/arp/arp.cpp 2007-04-11 16:07:58 UTC (rev 20656) +++ haiku/trunk/src/add-ons/kernel/network/datalink_protocols/arp/arp.cpp 2007-04-11 16:40:40 UTC (rev 20657) @@ -353,7 +353,7 @@ { TRACE(("ARP receive\n")); - NetBufferHeader bufferHeader(buffer); + NetBufferHeaderReader bufferHeader(buffer); if (bufferHeader.Status() < B_OK) return bufferHeader.Status(); @@ -383,8 +383,6 @@ || header.protocol_length != sizeof(in_addr_t)) return B_BAD_DATA; - bufferHeader.Detach(); - // handle packet switch (opcode) { Modified: haiku/trunk/src/add-ons/kernel/network/datalink_protocols/ethernet_frame/ethernet_frame.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/datalink_protocols/ethernet_frame/ethernet_frame.cpp 2007-04-11 16:07:58 UTC (rev 20656) +++ haiku/trunk/src/add-ons/kernel/network/datalink_protocols/ethernet_frame/ethernet_frame.cpp 2007-04-11 16:40:40 UTC (rev 20657) @@ -38,7 +38,7 @@ { //dprintf("asked to deframe buffer for device %s\n", device->name); - NetBufferHeader bufferHeader(buffer); + NetBufferHeaderRemover bufferHeader(buffer); if (bufferHeader.Status() < B_OK) return bufferHeader.Status(); @@ -138,7 +138,7 @@ else memcpy(header.destination, destination.sdl_data, ETHER_ADDRESS_LENGTH); - bufferHeader.Detach(); + bufferHeader.Sync(); // make sure the framing is already written to the buffer at this point return protocol->next->module->send_data(protocol->next, buffer); Modified: haiku/trunk/src/add-ons/kernel/network/protocols/icmp/icmp.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/icmp/icmp.cpp 2007-04-11 16:07:58 UTC (rev 20656) +++ haiku/trunk/src/add-ons/kernel/network/protocols/icmp/icmp.cpp 2007-04-11 16:40:40 UTC (rev 20657) @@ -48,6 +48,8 @@ }; }; +typedef NetBufferField ICMPChecksumField; + #define ICMP_TYPE_ECHO_REPLY 0 #define ICMP_TYPE_UNREACH 3 #define ICMP_TYPE_REDIRECT 5 @@ -211,13 +213,11 @@ { TRACE(("ICMP received some data, buffer length %lu\n", buffer->size)); - NetBufferHeader bufferHeader(buffer); + NetBufferHeaderReader bufferHeader(buffer); if (bufferHeader.Status() < B_OK) return bufferHeader.Status(); icmp_header &header = bufferHeader.Data(); - bufferHeader.Detach(); - // the pointer stays valid after this TRACE((" got type %u, code %u, checksum %u\n", header.type, header.code, ntohs(header.checksum))); @@ -249,19 +249,18 @@ memcpy(&reply->destination, &buffer->source, buffer->source.ss_len); // There already is an ICMP header, and we'll reuse it - icmp_header *header; - status_t status = gBufferModule->direct_access(reply, - 0, sizeof(icmp_header), (void **)&header); - if (status == B_OK) { - header->type = ICMP_TYPE_ECHO_REPLY; - header->code = 0; - header->checksum = 0; - header->checksum = gBufferModule->checksum(reply, 0, reply->size, true); - } + NetBufferHeaderReader header(reply); - if (status == B_OK) - status = domain->module->send_data(NULL, reply); + header->type = ICMP_TYPE_ECHO_REPLY; + header->code = 0; + header->checksum = 0; + header.Sync(); + + ICMPChecksumField checksum(reply); + *checksum = gBufferModule->checksum(reply, 0, reply->size, true); + + status_t status = domain->module->send_data(NULL, reply); if (status < B_OK) { gBufferModule->free(reply); return status; Modified: haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp 2007-04-11 16:07:58 UTC (rev 20656) +++ haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp 2007-04-11 16:40:40 UTC (rev 20657) @@ -74,6 +74,8 @@ typedef DoublyLinkedList > FragmentList; +typedef NetBufferField IPChecksumField; + struct ipv4_packet_key { in_addr_t source; in_addr_t destination; @@ -560,14 +562,11 @@ TRACE(("ipv4 needs to fragment (size %lu, MTU %lu)...\n", buffer->size, mtu)); - NetBufferHeader bufferHeader(buffer); - if (bufferHeader.Status() < B_OK) - return bufferHeader.Status(); + NetBufferHeaderReader originalHeader(buffer); + if (originalHeader.Status() < B_OK) + return originalHeader.Status(); - ipv4_header *header = &bufferHeader.Data(); - bufferHeader.Detach(); - - uint16 headerLength = header->HeaderLength(); + uint16 headerLength = originalHeader->HeaderLength(); uint32 bytesLeft = buffer->size - headerLength; uint32 fragmentOffset = 0; status_t status = B_OK; @@ -576,9 +575,10 @@ if (headerBuffer == NULL) return B_NO_MEMORY; - bufferHeader.SetTo(headerBuffer); - header = &bufferHeader.Data(); - bufferHeader.Detach(); + // TODO we need to make sure ipv4_header is contiguous or + // use another construct. + NetBufferHeaderReader bufferHeader(headerBuffer); + ipv4_header *header = &bufferHeader.Data(); // adapt MTU to be a multiple of 8 (fragment offsets can only be specified this way) mtu -= headerLength; @@ -671,6 +671,15 @@ } +static void +update_checksum(net_buffer *buffer) +{ + IPChecksumField checksum(buffer); + + *checksum = gBufferModule->checksum(buffer, 0, sizeof(ipv4_header), true); +} + + // #pragma mark - @@ -955,27 +964,27 @@ header.destination = ((sockaddr_in *)&buffer->destination)->sin_addr.s_addr; - header.checksum = gBufferModule->checksum(buffer, 0, - sizeof(ipv4_header), true); + bufferHeader.Sync(); + // make sure the IP-header is already written to the + // buffer at this point + + update_checksum(buffer); //dump_ipv4_header(header); - bufferHeader.Detach(); - // make sure the IP-header is already written to the - // buffer at this point } else { // if IP_HDRINCL, check if the source address is set - NetBufferHeader bufferHeader(buffer); - if (bufferHeader.Status() < B_OK) - return bufferHeader.Status(); + NetBufferHeaderReader header(buffer); + if (header.Status() < B_OK) + return header.Status(); - ipv4_header &header = bufferHeader.Data(); - if (header.source == 0) { - header.source = source.sin_addr.s_addr; - header.checksum = gBufferModule->checksum(buffer, - sizeof(ipv4_header), sizeof(ipv4_header), true); + if (header->source == 0) { + header->source = source.sin_addr.s_addr; + header->checksum = 0; + + header.Sync(); + + update_checksum(buffer); } - - bufferHeader.Detach(); } if (buffer->size > 0xffff) @@ -1079,12 +1088,11 @@ { TRACE(("IPv4 received a packet (%p) of %ld size!\n", buffer, buffer->size)); - NetBufferHeader bufferHeader(buffer); + NetBufferHeaderReader bufferHeader(buffer); if (bufferHeader.Status() < B_OK) return bufferHeader.Status(); ipv4_header &header = bufferHeader.Data(); - bufferHeader.Detach(); //dump_ipv4_header(header); if (header.version != IP_VERSION) Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.cpp 2007-04-11 16:07:58 UTC (rev 20656) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.cpp 2007-04-11 16:40:40 UTC (rev 20657) @@ -39,6 +39,9 @@ #endif +typedef NetBufferField TCPChecksumField; + + net_domain *gDomain; net_address_module_info *gAddressModule; net_buffer_module_info *gBufferModule; @@ -150,7 +153,7 @@ // we must detach before calculating the checksum as we may // not have a contiguous buffer. - bufferHeader.Detach(); + bufferHeader.Sync(); if (optionsLength > 0) gBufferModule->write(buffer, sizeof(tcp_header), optionsBuffer, optionsLength); @@ -167,9 +170,8 @@ << (uint16)htons(buffer->size) << Checksum::BufferHelper(buffer, gBufferModule); - // we are pretty sure the header is there. - NetBufferSafeHeader headerRef(buffer); - headerRef.Data().checksum = checksum; + TCPChecksumField checksumField(buffer); + *checksumField = checksum; return B_OK; } @@ -507,7 +509,7 @@ if (gDomain == NULL && set_domain(buffer->interface) != B_OK) return B_ERROR; - NetBufferHeader bufferHeader(buffer); + NetBufferHeaderReader bufferHeader(buffer); if (bufferHeader.Status() < B_OK) return bufferHeader.Status(); Modified: haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp 2007-04-11 16:07:58 UTC (rev 20656) +++ haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp 2007-04-11 16:40:40 UTC (rev 20657) @@ -440,7 +440,7 @@ status_t UdpEndpointManager::ReceiveData(net_buffer *buffer) { - NetBufferHeader bufferHeader(buffer); + NetBufferHeaderReader bufferHeader(buffer); if (bufferHeader.Status() < B_OK) return bufferHeader.Status(); Modified: haiku/trunk/src/add-ons/kernel/network/stack/net_buffer.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/net_buffer.cpp 2007-04-11 16:07:58 UTC (rev 20656) +++ haiku/trunk/src/add-ons/kernel/network/stack/net_buffer.cpp 2007-04-11 16:40:40 UTC (rev 20657) @@ -464,9 +464,10 @@ TRACE(("split_buffer(buffer %p -> %p, offset %ld)\n", from, buffer, offset)); - if (remove_header(from, offset) == B_OK - && trim_data(buffer, offset) == B_OK) - return buffer; + if (trim_data(buffer, offset) == B_OK) { + if (remove_header(from, offset) == B_OK) + return buffer; + } free_buffer(buffer); return NULL; From hugosantos at gmail.com Wed Apr 11 19:25:59 2007 From: hugosantos at gmail.com (Hugo Santos) Date: Wed, 11 Apr 2007 18:25:59 +0100 Subject: [Haiku-commits] r20656 - haiku/trunk/build/jam In-Reply-To: <200704111607.l3BG7xwH005170@sheep.berlios.de> References: <200704111607.l3BG7xwH005170@sheep.berlios.de> Message-ID: <9c46321e0704111025y61051899n68ed20bec3ea27b8@mail.gmail.com> On 4/11/07, axeld at BerliOS wrote: > * Added telnetd (does not work yet for whatever reason), and NetworkStatus to > the image. Since it is trying to getpeername(0, ...) I'm assuming it only runs with inetd. Hugo From axeld at pinc-software.de Wed Apr 11 19:38:09 2007 From: axeld at pinc-software.de (Axel =?iso-8859-15?q?D=F6rfler?=) Date: Wed, 11 Apr 2007 19:38:09 +0200 CEST Subject: [Haiku-commits] r20656 - haiku/trunk/build/jam In-Reply-To: <9c46321e0704111025y61051899n68ed20bec3ea27b8@mail.gmail.com> Message-ID: <30785370274-BeMail@zon> "Hugo Santos" wrote: > On 4/11/07, axeld at BerliOS wrote: > > * Added telnetd (does not work yet for whatever reason), and > > NetworkStatus to > > the image. > Since it is trying to getpeername(0, ...) I'm assuming it only runs > with inetd. It should run as net_server service as well, though. It is started, and it connects, but then it hangs. /boot/common/config/settings/network/services: service { name telnet launch telnetd } Bye, Axel. From hugosantos at gmail.com Wed Apr 11 19:42:28 2007 From: hugosantos at gmail.com (Hugo Santos) Date: Wed, 11 Apr 2007 18:42:28 +0100 Subject: [Haiku-commits] r20656 - haiku/trunk/build/jam In-Reply-To: <30785370274-BeMail@zon> References: <9c46321e0704111025y61051899n68ed20bec3ea27b8@mail.gmail.com> <30785370274-BeMail@zon> Message-ID: <9c46321e0704111042u3693afbfocaa2f84b65273363@mail.gmail.com> I'll check if its TCP's fault in a bit. Thanks for the pointer on the services. Hugo On 4/11/07, Axel D?rfler wrote: > "Hugo Santos" wrote: > > On 4/11/07, axeld at BerliOS wrote: > > > * Added telnetd (does not work yet for whatever reason), and > > > NetworkStatus to > > > the image. > > Since it is trying to getpeername(0, ...) I'm assuming it only runs > > with inetd. > > It should run as net_server service as well, though. It is started, and > it connects, but then it hangs. > > /boot/common/config/settings/network/services: > > service { > name telnet > launch telnetd > } > > Bye, > Axel. > > _______________________________________________ > Haiku-commits mailing list > Haiku-commits at lists.berlios.de > https://lists.berlios.de/mailman/listinfo/haiku-commits > From wkornewald at haiku-os.org Wed Apr 11 19:42:32 2007 From: wkornewald at haiku-os.org (Waldemar Kornewald) Date: Wed, 11 Apr 2007 19:42:32 +0200 Subject: [Haiku-commits] r20657 - in haiku/trunk: headers/private/net src/add-ons/kernel/network/datalink_protocols/arp src/add-ons/kernel/network/datalink_protocols/ethernet_frame src/add-ons/kernel/network/protocols/icmp src/add-ons/kernel/network/proto Message-ID: Hi Hugo, On 4/11/07, hugosantos at mail.berlios.de wrote: > Modified: > haiku/trunk/headers/private/net/NetBufferUtilities.h > haiku/trunk/src/add-ons/kernel/network/datalink_protocols/arp/arp.cpp > haiku/trunk/src/add-ons/kernel/network/datalink_protocols/ethernet_frame/ethernet_frame.cpp > haiku/trunk/src/add-ons/kernel/network/protocols/icmp/icmp.cpp > haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp > haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.cpp > haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp > haiku/trunk/src/add-ons/kernel/network/stack/net_buffer.cpp > Log: > some NetBufferUtility revamp. > > - introduced base NetBufferFieldReader which deals with obtaining a continuguous field to deal with. > - renamed Detach() to Sync() to better express the fact that we may be writing to the buffer. > - Fixed IPv4's and ICMP's checksum calculation as it assumed the underlying header was contiguous. > - ICMP is now able to reply to ICMP Echo Requests which were split across data nodes. I hope there are still a few ICMP tasks left for another GSoC student. :) Bye, Waldemar Kornewald From axeld at pinc-software.de Wed Apr 11 20:15:46 2007 From: axeld at pinc-software.de (Axel =?iso-8859-15?q?D=F6rfler?=) Date: Wed, 11 Apr 2007 20:15:46 +0200 CEST Subject: [Haiku-commits] =?iso-8859-15?q?r20657_-_in_haiku/trunk=3A_header?= =?iso-8859-15?q?s/private/net_src/add-ons/kernel/network/datalink=5Fproto?= =?iso-8859-15?q?cols/arp_src/add-ons/kernel/network/datalink=5Fprotocols/?= =?iso-8859-15?q?ethernet=5Fframe_src/add-ons/kernel/network/protocols/icm?= =?iso-8859-15?q?p_src/add-ons/kernel/network/proto?= In-Reply-To: Message-ID: <33042274104-BeMail@zon> "Waldemar Kornewald" wrote: > I hope there are still a few ICMP tasks left for another GSoC > student. :) Plenty, that was "just" a bug fix :-) Bye, Axel. From axeld at mail.berlios.de Wed Apr 11 20:52:54 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Wed, 11 Apr 2007 20:52:54 +0200 Subject: [Haiku-commits] r20658 - haiku/trunk/src/apps/networkstatus Message-ID: <200704111852.l3BIqsue028010@sheep.berlios.de> Author: axeld Date: 2007-04-11 20:52:53 +0200 (Wed, 11 Apr 2007) New Revision: 20658 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20658&view=rev Modified: haiku/trunk/src/apps/networkstatus/NetworkStatusView.cpp Log: Got fooled by operator precedence - it's now working as expected. Modified: haiku/trunk/src/apps/networkstatus/NetworkStatusView.cpp =================================================================== --- haiku/trunk/src/apps/networkstatus/NetworkStatusView.cpp 2007-04-11 16:40:40 UTC (rev 20657) +++ haiku/trunk/src/apps/networkstatus/NetworkStatusView.cpp 2007-04-11 18:52:53 UTC (rev 20658) @@ -403,7 +403,7 @@ if (flags & IFF_CONFIGURING) status = kStatusConnecting; - else if (flags & (IFF_UP | IFF_LINK) == IFF_UP | IFF_LINK) + else if ((flags & (IFF_UP | IFF_LINK)) == (IFF_UP | IFF_LINK)) status = kStatusReady; return status; From axeld at pinc-software.de Wed Apr 11 21:55:24 2007 From: axeld at pinc-software.de (Axel =?iso-8859-15?q?D=F6rfler?=) Date: Wed, 11 Apr 2007 21:55:24 +0200 CEST Subject: [Haiku-commits] =?iso-8859-15?q?r20620_-_in_haiku/trunk=3A_build/?= =?iso-8859-15?q?jam_src/add-ons/kernel/network/datalink=5Fprotocols_src/a?= =?iso-8859-15?q?dd-ons/kernel/network/datalink=5Fprotocols/arp_src/add-on?= =?iso-8859-15?q?s/kernel/network/datalink=5Fprotocols/ipv4=5Fdatagram_src?= =?iso-8859-15?q?/add-ons/kernel/network/stack?= In-Reply-To: <9c46321e0704091028o55f983l9e0ee44daa3e1056@mail.gmail.com> Message-ID: <39020773494-BeMail@zon> "Hugo Santos" wrote: > Axel, what if we want to support IPv4 over a tunnel for instance? One > that doesn't emulate Ethernet. IPv4 should only be registered once > (most stuff uses ETHER_TYPE_IP's value to identify IP anyway). > I do see the advantage of ETHER_FRAME_TYPE, but maybe the reader > could register type and mask? This way we could install more generic > handlers instead of per L2. Ethernet isn't IPv4 specific, while ARP directly supports it. And since every layer costs a bit (function call overhead), I wouldn't mind not to introduce too many logically possible separations. In case IPv4 should get tunneled, it should just register the IPv4 reader as well (a second time, but with a different mask), that shouldn't hurt anyone either. The service (like ARP or tunneling) should register the protocol; it knows which protocols it supports, but certainly not vice versa. IMO ipv4_datagram doesn't fit too well into the hierarchy. Bye, Axel. From hugosantos at gmail.com Wed Apr 11 22:19:14 2007 From: hugosantos at gmail.com (Hugo Santos) Date: Wed, 11 Apr 2007 21:19:14 +0100 Subject: [Haiku-commits] r20620 - in haiku/trunk: build/jam src/add-ons/kernel/network/datalink_protocols src/add-ons/kernel/network/datalink_protocols/arp src/add-ons/kernel/network/datalink_protocols/ipv4_datagram src/add-ons/kernel/network/stack In-Reply-To: <39020773494-BeMail@zon> References: <9c46321e0704091028o55f983l9e0ee44daa3e1056@mail.gmail.com> <39020773494-BeMail@zon> Message-ID: <9c46321e0704111319h396d7ee9rb383dee2c2845438@mail.gmail.com> On 4/11/07, Axel D?rfler wrote: > Ethernet isn't IPv4 specific, while ARP directly supports it. And since Certainly, and i didn't imply otherwise. :-) I'm not stating ipv4_datagram is a perfect solution, but it brings forward the relationship between network and link layer protocols. You see, i don't quite agree with the statement that Ethernet knows it can run IPv4, because it only carries an opaque number which doesn't mean anything to it. IPv4 was designed to run over different types of links and there is a different standard for each such relationship, which dictates for instance what is the protocol identifier used in the link layer to identify IPv4. For IPv6 this is even clearer as there is a RFC which for instance defines how IPv6 runs over Ethernet (RFC 2464). Instead of adding ipv4_datagram i was going to change protocols/ipv4 to do this, but preferred to distinguish between the protocol implementation and the glue that allows it to be used over specific links. It seems to me that if i develop a generic link type, i shouldn't add the information that IPv4 is capable of being run over it, it should be agnostic to this, the same way IPv4 is agnostic towards UDP or TCP. In ARP's case, it probably makes sense for it to register IPv4 since it is part of the glue that allows IPv4 to run over Ethernet. But please note that there is no such separate protocol in IPv6, the neighbor resolution is all done within IPv6 itself, so this doesn't apply to all network protocols. And what about point-to-point interfaces? PPP for instance is able to run IPv4, IPv6, etc. Hugo From axeld at pinc-software.de Wed Apr 11 22:26:31 2007 From: axeld at pinc-software.de (Axel =?iso-8859-15?q?D=F6rfler?=) Date: Wed, 11 Apr 2007 22:26:31 +0200 CEST Subject: [Haiku-commits] r20545 - buildtools/trunk/jam In-Reply-To: <20070404190126.3198.9@cs.tu-berlin.de> Message-ID: <40887606593-BeMail@zon> Ingo Weinhold wrote: > > I can only report that I had this error :-) > > I could try to reproduce it again by reverting my local changes to > > HaikuImage, and eventually find out which command triggers it. > Don't worry. I'm not really in the mood for hunting obscure Jam bugs, > as > long as we can work around so easily. :-) Removing binaries isn't exactly a nice solution, but as it seems to work... :-) Bye, Axel. From jackburton at mail.berlios.de Wed Apr 11 23:06:36 2007 From: jackburton at mail.berlios.de (jackburton at BerliOS) Date: Wed, 11 Apr 2007 23:06:36 +0200 Subject: [Haiku-commits] r20659 - haiku/trunk/src/preferences/mouse Message-ID: <200704112106.l3BL6aZg004842@sheep.berlios.de> Author: jackburton Date: 2007-04-11 23:06:35 +0200 (Wed, 11 Apr 2007) New Revision: 20659 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20659&view=rev Modified: haiku/trunk/src/preferences/mouse/MouseWindow.cpp haiku/trunk/src/preferences/mouse/SettingsView.cpp haiku/trunk/src/preferences/mouse/SettingsView.h Log: Patch by Lucasz Zemczak which fixes font sensitiveness issues in Mouse preflet. Thank you! Modified: haiku/trunk/src/preferences/mouse/MouseWindow.cpp =================================================================== --- haiku/trunk/src/preferences/mouse/MouseWindow.cpp 2007-04-11 18:52:53 UTC (rev 20658) +++ haiku/trunk/src/preferences/mouse/MouseWindow.cpp 2007-04-11 21:06:35 UTC (rev 20659) @@ -56,6 +56,7 @@ rect.OffsetBy(button->Bounds().Width() + kItemSpace, 0); fRevertButton = new BButton(rect, "revert", "Revert", new BMessage(kMsgRevert)); fRevertButton->SetEnabled(false); + fRevertButton->ResizeToPreferred(); view->AddChild(fRevertButton); SetPulseRate(100000); @@ -72,10 +73,15 @@ rect.bottom -= 20; BPoint position = fSettings.WindowPosition(); - if (!rect.Contains(position)) { + if (!rect.Contains(BRect(position, + Bounds().OffsetBySelf(position).RightBottom()))) { // center window on screen as it doesn't fit on the saved position position.x = (rect.Width() - Bounds().Width()) / 2; position.y = (rect.Height() - Bounds().Height()) / 2; + if (position.x < 0) + position.x = 0; + if (position.y < 0) + position.y = 15; } MoveTo(position); } Modified: haiku/trunk/src/preferences/mouse/SettingsView.cpp =================================================================== --- haiku/trunk/src/preferences/mouse/SettingsView.cpp 2007-04-11 18:52:53 UTC (rev 20658) +++ haiku/trunk/src/preferences/mouse/SettingsView.cpp 2007-04-11 21:06:35 UTC (rev 20659) @@ -71,72 +71,115 @@ fTypeMenu->AddItem(new BMenuItem("3-Button", new BMessage(kMsgMouseType))); BMenuField *field = new BMenuField(BRect(7, 8, 155, 190), "mouse_type", "Mouse type:", fTypeMenu); - field->ResizeToPreferred(); + field->SetDivider(field->StringWidth(field->Label()) + kItemSpace); field->SetAlignment(B_ALIGN_RIGHT); AddChild(field); - fMouseView = new MouseView(BRect(7, 28, 155, 190), fSettings); - fMouseView->ResizeToPreferred(); - fMouseView->MoveBy((142 - fMouseView->Bounds().Width()) / 2, - (108 - fMouseView->Bounds().Height()) / 2); - AddChild(fMouseView); + BFont font = be_plain_font; + float length = font.StringWidth("Mouse type: [3-Button]") + 20; + fLeftArea.Set(8, 7, length + 8, 198); + if (fLeftArea.Width() < 125) + fLeftArea.right = fLeftArea.left + 125; - // Add the "Focus follows mouse" pop up menu - fFocusMenu = new BPopUpMenu("Disabled"); - - const char *focusLabels[] = {"Disabled", "Enabled", "Warping", "Instant-Warping"}; - const mode_mouse focusModes[] = {B_NORMAL_MOUSE, B_FOCUS_FOLLOWS_MOUSE, - B_WARP_MOUSE, B_INSTANT_WARP_MOUSE}; + fRightArea.Set(fLeftArea.right + 10, 11, 200, 7); - for (int i = 0; i < 4; i++) { - BMessage *message = new BMessage(kMsgMouseFocusMode); - message->AddInt32("mode", focusModes[i]); - - fFocusMenu->AddItem(new BMenuItem(focusLabels[i], message)); - } - - BRect frame(165, 208, 440, 200); - field = new BMenuField(frame, "ffm", "Focus follows mouse:", fFocusMenu); - field->SetDivider(field->StringWidth(field->Label()) + kItemSpace); - field->SetAlignment(B_ALIGN_RIGHT); - AddChild(field); - // Create the "Double-click speed slider... - frame.Set(166, 11, 328, 50); - fClickSpeedSlider = new BSlider(frame, "double_click_speed", "Double-click speed", + fClickSpeedSlider = new BSlider(fRightArea, "double_click_speed", "Double-click speed", new BMessage(kMsgDoubleClickSpeed), 0, 1000); fClickSpeedSlider->SetHashMarks(B_HASH_MARKS_BOTTOM); fClickSpeedSlider->SetHashMarkCount(5); fClickSpeedSlider->SetLimitLabels("Slow", "Fast"); AddChild(fClickSpeedSlider); + length = fClickSpeedSlider->Bounds().Height() + 6; + fDoubleClickBmpPoint.y = fRightArea.top + + (length - fDoubleClickBitmap->Bounds().Height()) / 2; + fRightArea.top += length; + // Create the "Mouse Speed" slider... - frame.Set(166,76,328,125); - fMouseSpeedSlider = new BSlider(frame, "mouse_speed", "Mouse Speed", + fMouseSpeedSlider = new BSlider(fRightArea, "mouse_speed", "Mouse Speed", new BMessage(kMsgMouseSpeed), 0, 1000); fMouseSpeedSlider->SetHashMarks(B_HASH_MARKS_BOTTOM); fMouseSpeedSlider->SetHashMarkCount(7); fMouseSpeedSlider->SetLimitLabels("Slow", "Fast"); AddChild(fMouseSpeedSlider); + fSpeedBmpPoint.y = fRightArea.top + + (length - fSpeedBitmap->Bounds().Height()) / 2; + fRightArea.top += length; + // Create the "Mouse Acceleration" slider... - frame.Set(166, 141, 328, 190); - fAccelerationSlider = new BSlider(frame, "mouse_acceleration", "Mouse Acceleration", + fAccelerationSlider = new BSlider(fRightArea, "mouse_acceleration", "Mouse Acceleration", new BMessage(kMsgAccelerationFactor), 0, 1000); fAccelerationSlider->SetHashMarks(B_HASH_MARKS_BOTTOM); fAccelerationSlider->SetHashMarkCount(5); fAccelerationSlider->SetLimitLabels("Slow", "Fast"); AddChild(fAccelerationSlider); + fAccelerationBmpPoint.y = fRightArea.top + + (length - fAccelerationBitmap->Bounds().Height()) / 2; + fRightArea.top += length - 3; + + // Add the "Focus follows mouse" pop up menu + fFocusMenu = new BPopUpMenu("Disabled"); + + const char *focusLabels[] = {"Disabled", "Enabled", "Warping", "Instant-Warping"}; + const mode_mouse focusModes[] = {B_NORMAL_MOUSE, B_FOCUS_FOLLOWS_MOUSE, + B_WARP_MOUSE, B_INSTANT_WARP_MOUSE}; + + for (int i = 0; i < 4; i++) { + BMessage *message = new BMessage(kMsgMouseFocusMode); + message->AddInt32("mode", focusModes[i]); + + fFocusMenu->AddItem(new BMenuItem(focusLabels[i], message)); + } + + BRect frame(fRightArea.left, fRightArea.top + 10, fRightArea.left + + font.StringWidth("Focus follows mouse:") + + font.StringWidth(focusLabels[0]) + 30, 200); + field = new BMenuField(frame, "ffm", "Focus follows mouse:", fFocusMenu, true); + field->SetDivider(field->StringWidth(field->Label()) + kItemSpace); + field->SetAlignment(B_ALIGN_RIGHT); + AddChild(field); + + // Finalize the areas + fRightArea.bottom = fRightArea.top; + fRightArea.top = 11; + fRightArea.right = frame.right + 8; + if (fRightArea.Width() < 200) + fRightArea.right = fRightArea.left + 200; + fLeftArea.bottom = fRightArea.bottom; + + // Position mouse bitmaps + fDoubleClickBmpPoint.x = fRightArea.right - fDoubleClickBitmap->Bounds().right - 15; + fSpeedBmpPoint.x = fRightArea.right - fSpeedBitmap->Bounds().right - 15; + fAccelerationBmpPoint.x = fRightArea.right - fAccelerationBitmap->Bounds().right - 15; + + // Resize sliders to equal size + length = fRightArea.left - 5; + fClickSpeedSlider->ResizeTo(fDoubleClickBmpPoint.x - length - 11, + fClickSpeedSlider->Bounds().Height()); + fMouseSpeedSlider->ResizeTo(fSpeedBmpPoint.x - length, + fMouseSpeedSlider->Bounds().Height()); + fAccelerationSlider->ResizeTo(fAccelerationBmpPoint.x - length, + fAccelerationSlider->Bounds().Height()); + + // Mouse image... + frame.Set(0, 0, 148, 162); + fMouseView = new MouseView(frame, fSettings); + fMouseView->ResizeToPreferred(); + fMouseView->MoveBy((fLeftArea.right - fMouseView->Bounds().Width()) / 2, + (fLeftArea.bottom - fMouseView->Bounds().Height()) / 2); + AddChild(fMouseView); + // Create the "Double-click test area" text box... - frame = Bounds(); - frame.left = frame.left + 9; - frame.right = frame.right - 230; - frame.top = frame.bottom - 30; + frame.Set(fLeftArea.left, fLeftArea.bottom + 10, fLeftArea.right, 0); BTextControl *textControl = new BTextControl(frame, "double_click_test_area", NULL, "Double-click test area", NULL); textControl->SetAlignment(B_ALIGN_LEFT, B_ALIGN_CENTER); AddChild(textControl); + + ResizeTo(fRightArea.right + 5, fLeftArea.bottom + 60); } @@ -158,11 +201,10 @@ void SettingsView::GetPreferredSize(float *_width, float *_height) { - // ToDo: fixed values for now if (_width) - *_width = 397 - 22; + *_width = fRightArea.right + 5; if (_height) - *_height = 293 - 55; + *_height = fLeftArea.bottom + 60; } @@ -173,36 +215,47 @@ SetHighColor(120, 120, 120); SetLowColor(255, 255, 255); + // Line above the test area - StrokeLine(BPoint(8, 198), BPoint(149, 198), B_SOLID_HIGH); - StrokeLine(BPoint(8, 199), BPoint(149, 199), B_SOLID_LOW); + fLeft = fLeftArea.LeftBottom(); + fRight = fLeftArea.RightBottom(); + StrokeLine(fLeft, fRight, B_SOLID_HIGH); + fLeft.y++; fRight.y++; + StrokeLine(fLeft, fRight, B_SOLID_LOW); + // Line above focus follows mouse - StrokeLine(BPoint(164, 198), BPoint(367, 198), B_SOLID_HIGH); - StrokeLine(BPoint(164, 199), BPoint(367, 199), B_SOLID_LOW); + fLeft = fRightArea.LeftBottom(); + fRight = fRightArea.RightBottom(); + StrokeLine(fLeft, fRight, B_SOLID_HIGH); + fLeft.y++; fRight.y++; + StrokeLine(fLeft, fRight, B_SOLID_LOW); + // Line in the middle - StrokeLine(BPoint(156, 10), BPoint(156, 230), B_SOLID_HIGH); - StrokeLine(BPoint(157, 11), BPoint(157, 230), B_SOLID_LOW); + fLeft = fLeftArea.RightTop(); + fRight = fLeftArea.RightBottom(); + fLeft.x += 5; + fRight.x += 5; + StrokeLine(fLeft, fRight, B_SOLID_HIGH); + fLeft.x++; fRight.x++; + StrokeLine(fLeft, fRight, B_SOLID_LOW); SetDrawingMode(B_OP_OVER); // Draw the icons - BPoint doubleClickBmpPoint(344, 16); if (fDoubleClickBitmap != NULL - && updateFrame.Intersects(BRect(doubleClickBmpPoint, - doubleClickBmpPoint + fDoubleClickBitmap->Bounds().RightBottom()))) - DrawBitmapAsync(fDoubleClickBitmap, doubleClickBmpPoint); + && updateFrame.Intersects(BRect(fDoubleClickBmpPoint, + fDoubleClickBmpPoint + fDoubleClickBitmap->Bounds().RightBottom()))) + DrawBitmapAsync(fDoubleClickBitmap, fDoubleClickBmpPoint); - BPoint speedBmpPoint(333, 90); if (fSpeedBitmap != NULL - && updateFrame.Intersects(BRect(speedBmpPoint, - speedBmpPoint + fSpeedBitmap->Bounds().RightBottom()))) - DrawBitmapAsync(fSpeedBitmap, speedBmpPoint); + && updateFrame.Intersects(BRect(fSpeedBmpPoint, + fSpeedBmpPoint + fSpeedBitmap->Bounds().RightBottom()))) + DrawBitmapAsync(fSpeedBitmap, fSpeedBmpPoint); - BPoint accelerationBmpPoint(333, 155); if (fAccelerationBitmap != NULL - && updateFrame.Intersects(BRect(accelerationBmpPoint, - accelerationBmpPoint + fAccelerationBitmap->Bounds().RightBottom()))) - DrawBitmapAsync(fAccelerationBitmap, accelerationBmpPoint); + && updateFrame.Intersects(BRect(fAccelerationBmpPoint, + fAccelerationBmpPoint + fAccelerationBitmap->Bounds().RightBottom()))) + DrawBitmapAsync(fAccelerationBitmap, fAccelerationBmpPoint); SetDrawingMode(B_OP_COPY); Modified: haiku/trunk/src/preferences/mouse/SettingsView.h =================================================================== --- haiku/trunk/src/preferences/mouse/SettingsView.h 2007-04-11 18:52:53 UTC (rev 20658) +++ haiku/trunk/src/preferences/mouse/SettingsView.h 2007-04-11 21:06:35 UTC (rev 20659) @@ -52,6 +52,10 @@ BSlider *fClickSpeedSlider, *fMouseSpeedSlider, *fAccelerationSlider; BBitmap *fDoubleClickBitmap, *fSpeedBitmap, *fAccelerationBitmap; + + BRect fLeftArea, fRightArea; + BPoint fLeft, fRight; + BPoint fDoubleClickBmpPoint, fSpeedBmpPoint, fAccelerationBmpPoint; }; #endif /* SETTINGS_VIEW_H */ From hugosantos at mail.berlios.de Thu Apr 12 00:24:44 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Thu, 12 Apr 2007 00:24:44 +0200 Subject: [Haiku-commits] r20660 - in haiku/trunk: headers/private/net src/add-ons/kernel/network/protocols/icmp src/add-ons/kernel/network/protocols/ipv4 src/add-ons/kernel/network/protocols/tcp src/add-ons/kernel/network/protocols/udp src/add-ons/kernel/network/stack Message-ID: <200704112224.l3BMOiBw009886@sheep.berlios.de> Author: hugosantos Date: 2007-04-12 00:24:12 +0200 (Thu, 12 Apr 2007) New Revision: 20660 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20660&view=rev Modified: haiku/trunk/headers/private/net/NetBufferUtilities.h haiku/trunk/headers/private/net/net_datalink.h haiku/trunk/src/add-ons/kernel/network/protocols/icmp/icmp.cpp haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4_address.cpp haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.cpp haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp haiku/trunk/src/add-ons/kernel/network/stack/routes.cpp haiku/trunk/src/add-ons/kernel/network/stack/routes.h Log: moved address selection logic to a new 'get_buffer_route'. - IPv4 now assumes the addresses it is supplied in send_routed_data are already the appropriate ones. - made the Data(), operator* and operator-> methods in NetBufferFieldReader const so we can use them in the same expression as the constructor. - fixed an issue with UDP where the wrong source address could be used in the calculating the checksum. - changed ipv4_print_address to use the more common 0.0.0.0 format. Modified: haiku/trunk/headers/private/net/NetBufferUtilities.h =================================================================== --- haiku/trunk/headers/private/net/NetBufferUtilities.h 2007-04-11 21:06:35 UTC (rev 20659) +++ haiku/trunk/headers/private/net/NetBufferUtilities.h 2007-04-11 22:24:12 UTC (rev 20660) @@ -22,56 +22,49 @@ public: NetBufferFieldReader(net_buffer *buffer) : - fBuffer(buffer), - fStatus(B_BAD_VALUE) + fBuffer(buffer) { - if ((Offset + sizeof(Type)) <= buffer->size) { - fStatus = Module::Get()->direct_access(fBuffer, Offset, - sizeof(Type), (void **)&fData); - if (fStatus != B_OK) { - fData = NULL; - fStatus = Module::Get()->read(fBuffer, Offset, - &fDataBuffer, sizeof(Type)); - } + fStatus = Module::Get()->direct_access(fBuffer, Offset, + sizeof(Type), (void **)&fData); + if (fStatus != B_OK) { + fStatus = Module::Get()->read(fBuffer, Offset, + &fDataBuffer, sizeof(Type)); + fData = &fDataBuffer; } } status_t - Status() + Status() const { return fStatus; } Type & - Data() + Data() const { - if (fData != NULL) - return *fData; - - return fDataBuffer; + return *fData; } Type * - operator->() + operator->() const { - return &Data(); + return fData; } Type & - operator*() + operator*() const { - return Data(); + return *fData; } void Sync() { - if (fBuffer == NULL) + if (fBuffer == NULL || fStatus < B_OK) return; - if (fData == NULL) - Module::Get()->write(fBuffer, Offset, &fDataBuffer, - sizeof(Type)); + if (fData == &fDataBuffer) + Module::Get()->write(fBuffer, Offset, fData, sizeof(Type)); fBuffer = NULL; } @@ -138,15 +131,14 @@ template class NetBufferPrepend : public NetBufferFieldReader { public: - NetBufferPrepend(net_buffer *buffer, size_t size = 0) + NetBufferPrepend(net_buffer *buffer, size_t size = sizeof(Type)) { fBuffer = buffer; - fData = NULL; - if (size == 0) - size = sizeof(Type); - - fStatus = Module::Get()->prepend_size(buffer, size, (void **)&fData); + fStatus = Module::Get()->prepend_size(buffer, size, + (void **)&fData); + if (fStatus == B_OK && fData == NULL) + fData = &fDataBuffer; } ~NetBufferPrepend() Modified: haiku/trunk/headers/private/net/net_datalink.h =================================================================== --- haiku/trunk/headers/private/net/net_datalink.h 2007-04-11 21:06:35 UTC (rev 20659) +++ haiku/trunk/headers/private/net/net_datalink.h 2007-04-11 22:24:12 UTC (rev 20660) @@ -79,6 +79,8 @@ const struct net_route *route); struct net_route *(*get_route)(struct net_domain *domain, const struct sockaddr *address); + status_t (*get_buffer_route)(struct net_domain *domain, + struct net_buffer *buffer, struct net_route **_route); void (*put_route)(struct net_domain *domain, struct net_route *route); status_t (*register_route_info)(struct net_domain *domain, @@ -118,6 +120,8 @@ status_t (*set_to)(sockaddr *address, const sockaddr *from); status_t (*set_to_empty_address)(sockaddr *address); + status_t (*update_to)(sockaddr *address, const sockaddr *from); + uint32 (*hash_address_pair)(const sockaddr *ourAddress, const sockaddr *peerAddress); Modified: haiku/trunk/src/add-ons/kernel/network/protocols/icmp/icmp.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/icmp/icmp.cpp 2007-04-11 21:06:35 UTC (rev 20659) +++ haiku/trunk/src/add-ons/kernel/network/protocols/icmp/icmp.cpp 2007-04-11 22:24:12 UTC (rev 20660) @@ -257,8 +257,8 @@ header.Sync(); - ICMPChecksumField checksum(reply); - *checksum = gBufferModule->checksum(reply, 0, reply->size, true); + *ICMPChecksumField(reply) = gBufferModule->checksum(reply, 0, + reply->size, true); status_t status = domain->module->send_data(NULL, reply); if (status < B_OK) { Modified: haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp 2007-04-11 21:06:35 UTC (rev 20659) +++ haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp 2007-04-11 22:24:12 UTC (rev 20660) @@ -671,15 +671,6 @@ } -static void -update_checksum(net_buffer *buffer) -{ - IPChecksumField checksum(buffer); - - *checksum = gBufferModule->checksum(buffer, 0, sizeof(ipv4_header), true); -} - - // #pragma mark - @@ -928,49 +919,31 @@ TRACE(("someone tries to send some actual routed data!\n")); sockaddr_in &source = *(sockaddr_in *)&buffer->source; - if (source.sin_addr.s_addr == INADDR_ANY && route->interface->address != NULL) { - // replace an unbound source address with the address of the interface - // TODO: couldn't we replace all addresses here? - source.sin_addr.s_addr = ((sockaddr_in *)route->interface->address)->sin_addr.s_addr; - } + sockaddr_in &destination = *(sockaddr_in *)&buffer->destination; - bool headerIncluded = false; + bool headerIncluded = false, checksumNeeded = true; if (protocol != NULL) headerIncluded = (protocol->flags & IP_FLAG_HEADER_INCLUDED) != 0; // Add IP header (if needed) if (!headerIncluded) { - NetBufferPrepend bufferHeader(buffer); - if (bufferHeader.Status() < B_OK) - return bufferHeader.Status(); + NetBufferPrepend header(buffer); + if (header.Status() < B_OK) + return header.Status(); - ipv4_header &header = bufferHeader.Data(); + header->version = IP_VERSION; + header->header_length = sizeof(ipv4_header) / 4; + header->service_type = protocol ? protocol->service_type : 0; + header->total_length = htons(buffer->size); + header->id = htons(atomic_add(&sPacketID, 1)); + header->fragment_offset = 0; + header->time_to_live = protocol ? protocol->time_to_live : 254; + header->protocol = protocol ? protocol->socket->protocol : buffer->protocol; + header->checksum = 0; - header.version = IP_VERSION; - header.header_length = sizeof(ipv4_header) >> 2; - header.service_type = protocol ? protocol->service_type : 0; - header.total_length = htons(buffer->size); - header.id = htons(atomic_add(&sPacketID, 1)); - header.fragment_offset = 0; - header.time_to_live = protocol ? protocol->time_to_live : 254; - header.protocol = protocol ? protocol->socket->protocol : buffer->protocol; - header.checksum = 0; - if (route->interface->address != NULL) { - header.source = ((sockaddr_in *)route->interface->address)->sin_addr.s_addr; - // always use the actual used source address - } else - header.source = 0; - - header.destination = ((sockaddr_in *)&buffer->destination)->sin_addr.s_addr; - - bufferHeader.Sync(); - // make sure the IP-header is already written to the - // buffer at this point - - update_checksum(buffer); - //dump_ipv4_header(header); - + header->source = source.sin_addr.s_addr; + header->destination = destination.sin_addr.s_addr; } else { // if IP_HDRINCL, check if the source address is set NetBufferHeaderReader header(buffer); @@ -980,22 +953,24 @@ if (header->source == 0) { header->source = source.sin_addr.s_addr; header->checksum = 0; - header.Sync(); - - update_checksum(buffer); - } + } else + checksumNeeded = false; } if (buffer->size > 0xffff) return EMSGSIZE; + if (checksumNeeded) + *IPChecksumField(buffer) = gBufferModule->checksum(buffer, 0, + sizeof(ipv4_header), true); + TRACE(("header chksum: %ld, buffer checksum: %ld\n", gBufferModule->checksum(buffer, 0, sizeof(ipv4_header), true), gBufferModule->checksum(buffer, 0, buffer->size, true))); TRACE(("destination-IP: buffer=%p addr=%p %08lx\n", buffer, &buffer->destination, - ntohl(((sockaddr_in *)&buffer->destination)->sin_addr.s_addr))); + ntohl(destination->sin_addr.s_addr))); uint32 mtu = route->mtu ? route->mtu : interface->mtu; if (buffer->size > mtu) { @@ -1012,15 +987,14 @@ { TRACE(("someone tries to send some actual data!\n")); - // find route - struct net_route *route = sDatalinkModule->get_route(sDomain, - (sockaddr *)&buffer->destination); - if (route == NULL) - return ENETUNREACH; + net_route *route = NULL; + status_t status = sDatalinkModule->get_buffer_route(sDomain, buffer, + &route); + if (status >= B_OK) { + status = ipv4_send_routed_data(protocol, route, buffer); + sDatalinkModule->put_route(sDomain, route); + } - status_t status = ipv4_send_routed_data(protocol, route, buffer); - sDatalinkModule->put_route(sDomain, route); - return status; } Modified: haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4_address.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4_address.cpp 2007-04-11 21:06:35 UTC (rev 20659) +++ haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4_address.cpp 2007-04-11 22:24:12 UTC (rev 20660) @@ -1,5 +1,5 @@ /* - * Copyright 2006, Haiku, Inc. All Rights Reserved. + * Copyright 2006-2007, Haiku, Inc. All Rights Reserved. * Distributed under the terms of the MIT License. * * Authors: @@ -251,24 +251,35 @@ \return B_NO_MEMORY if the buffer could not be allocated */ static status_t -ipv4_print_address(const sockaddr *address, char **_buffer, bool printPort) +ipv4_print_address(const sockaddr *_address, char **_buffer, bool printPort) { + const sockaddr_in *address = (const sockaddr_in *)_address; + if (_buffer == NULL) return B_BAD_VALUE; - int bufLen = printPort ? 15 : 9; - char *buffer = (char *)malloc(bufLen); - if (buffer == NULL) + char tmp[64]; + + if (address == NULL) + strcpy(tmp, ""); + else { + unsigned int addr = ntohl(address->sin_addr.s_addr); + + if (printPort) + sprintf(tmp, "%u.%u.%u.%u:%u", (addr >> 24) & 0xff, + (addr >> 16) & 0xff, (addr >> 8) & 0xff, addr & 0xff, + ntohs(address->sin_port)); + else + sprintf(tmp, "%u.%u.%u.%u", (addr >> 24) & 0xff, + (addr >> 16) & 0xff, (addr >> 8) & 0xff, addr & 0xff); + } + + *_buffer = strdup(tmp); + if (*_buffer == NULL) return B_NO_MEMORY; - if (address == NULL) - strcpy(buffer, ""); - else if (printPort) { - sprintf(buffer, "%08lx:%u", ntohl(((sockaddr_in *)address)->sin_addr.s_addr), - ntohs(((sockaddr_in *)address)->sin_port)); - } else - sprintf(buffer, "%08lx", ntohl(((sockaddr_in *)address)->sin_addr.s_addr)); - *_buffer = buffer; + + return B_OK; } @@ -324,6 +335,31 @@ } +static status_t +ipv4_update_to(sockaddr *_address, const sockaddr *_from) +{ + sockaddr_in *address = (sockaddr_in *)_address; + const sockaddr_in *from = (const sockaddr_in *)_from; + + if (address == NULL || from == NULL) + return B_BAD_VALUE; + + if (from->sin_family != AF_INET) + return B_BAD_VALUE; + + address->sin_family = AF_INET; + address->sin_len = sizeof(sockaddr_in); + + if (address->sin_port == 0) + address->sin_port = from->sin_port; + + if (address->sin_addr.s_addr == INADDR_ANY) + address->sin_addr.s_addr = from->sin_addr.s_addr; + + return B_OK; +} + + /*! Sets \a address to the empty address (0.0.0.0). \return B_OK if \a address has been set @@ -394,6 +430,7 @@ ipv4_set_port, ipv4_set_to, ipv4_set_to_empty_address, + ipv4_update_to, ipv4_hash_address_pair, ipv4_checksum_address, NULL // ipv4_matches_broadcast_address, Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.cpp 2007-04-11 21:06:35 UTC (rev 20659) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.cpp 2007-04-11 22:24:12 UTC (rev 20660) @@ -170,8 +170,7 @@ << (uint16)htons(buffer->size) << Checksum::BufferHelper(buffer, gBufferModule); - TCPChecksumField checksumField(buffer); - *checksumField = checksum; + *TCPChecksumField(buffer) = checksum; return B_OK; } Modified: haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp 2007-04-11 21:06:35 UTC (rev 20659) +++ haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp 2007-04-11 22:24:12 UTC (rev 20660) @@ -47,6 +47,10 @@ } _PACKED; +typedef NetBufferField + UDPChecksumField; + + class UdpEndpoint : public net_protocol { public: UdpEndpoint(net_socket *socket); @@ -766,43 +770,44 @@ { if (buffer->size > (0xffff - sizeof(udp_header))) return EMSGSIZE; - + buffer->protocol = IPPROTO_UDP; - { // scope for lifetime of bufferHeader + // add and fill UDP-specific header: + NetBufferPrepend header(buffer); + if (header.Status() < B_OK) + return header.Status(); - // add and fill UDP-specific header: - NetBufferPrepend bufferHeader(buffer); - if (bufferHeader.Status() < B_OK) - return bufferHeader.Status(); - - udp_header &header = bufferHeader.Data(); - - header.source_port = sAddressModule->get_port((sockaddr *)&buffer->source); - header.destination_port = sAddressModule->get_port( - (sockaddr *)&buffer->destination); - header.udp_length = htons(buffer->size); - // the udp-header is already included in the buffer-size - header.udp_checksum = 0; + header->source_port = sAddressModule->get_port((sockaddr *)&buffer->source); + header->destination_port = sAddressModule->get_port( + (sockaddr *)&buffer->destination); + header->udp_length = htons(buffer->size); + // the udp-header is already included in the buffer-size + header->udp_checksum = 0; - // generate UDP-checksum (simulating a so-called "pseudo-header"): - Checksum udpChecksum; - sAddressModule->checksum_address(&udpChecksum, - (sockaddr *)route->interface->address); - sAddressModule->checksum_address(&udpChecksum, - (sockaddr *)&buffer->destination); - udpChecksum - << (uint16)htons(IPPROTO_UDP) - << (uint16)htons(buffer->size) - // peculiar but correct: UDP-len is used twice for checksum - // (as it is already contained in udp_header) - << Checksum::BufferHelper(buffer, gBufferModule); - header.udp_checksum = udpChecksum; - if (header.udp_checksum == 0) - header.udp_checksum = 0xFFFF; - - TRACE_BLOCK(((char*)&header, sizeof(udp_header), "udp-hdr: ")); - } + header.Sync(); + + // generate UDP-checksum (simulating a so-called "pseudo-header"): + Checksum udpChecksum; + sAddressModule->checksum_address(&udpChecksum, + (sockaddr *)route->interface->address); + sAddressModule->checksum_address(&udpChecksum, + (sockaddr *)&buffer->destination); + udpChecksum + << (uint16)htons(IPPROTO_UDP) + << (uint16)htons(buffer->size) + // peculiar but correct: UDP-len is used twice for checksum + // (as it is already contained in udp_header) + << Checksum::BufferHelper(buffer, gBufferModule); + + uint16 calculatedChecksum = udpChecksum; + if (calculatedChecksum == 0) + calculatedChecksum = 0xffff; + + *UDPChecksumField(buffer) = calculatedChecksum; + + TRACE_BLOCK(((char*)&header, sizeof(udp_header), "udp-hdr: ")); + return next->module->send_routed_data(next, route, buffer); } @@ -966,8 +971,8 @@ net_buffer *buffer) { TRACE(("udp_send_routed_data(%p) size=%lu\n", protocol, buffer->size)); - UdpEndpoint *udpEndpoint = (UdpEndpoint *)protocol; - return udpEndpoint->SendData(buffer, route); + + return ((UdpEndpoint *)protocol)->SendData(buffer, route); } @@ -976,14 +981,14 @@ { TRACE(("udp_send_data(%p) size=%lu\n", protocol, buffer->size)); - struct net_route *route = sDatalinkModule->get_route(sDomain, - (sockaddr *)&buffer->destination); - if (route == NULL) - return ENETUNREACH; + net_route *route = NULL; + status_t status = sDatalinkModule->get_buffer_route(sDomain, buffer, + &route); + if (status >= B_OK) { + status = udp_send_routed_data(protocol, route, buffer); + sDatalinkModule->put_route(sDomain, route); + } - UdpEndpoint *udpEndpoint = (UdpEndpoint *)protocol; - status_t status = udpEndpoint->SendData(buffer, route); - sDatalinkModule->put_route(sDomain, route); return status; } Modified: haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp 2007-04-11 21:06:35 UTC (rev 20659) +++ haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp 2007-04-11 22:24:12 UTC (rev 20660) @@ -749,6 +749,7 @@ add_route, remove_route, get_route, + get_buffer_route, put_route, register_route_info, unregister_route_info, Modified: haiku/trunk/src/add-ons/kernel/network/stack/routes.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/routes.cpp 2007-04-11 21:06:35 UTC (rev 20659) +++ haiku/trunk/src/add-ons/kernel/network/stack/routes.cpp 2007-04-11 22:24:12 UTC (rev 20660) @@ -535,6 +535,43 @@ } +status_t +get_buffer_route(net_domain *_domain, net_buffer *buffer, net_route **_route) +{ + net_domain_private *domain = (net_domain_private *)_domain; + + BenaphoreLocker _(domain->lock); + + net_route *route = get_route_internal(domain, + (sockaddr *)&buffer->destination); + if (route == NULL) + return ENETUNREACH; + + status_t status = B_OK; + sockaddr *source = (sockaddr *)&buffer->source; + + // TODO we are quite relaxed in the address checking here + // as we might proceed with srcaddr=INADDR_ANY. + + if (route->interface && route->interface->address) { + sockaddr *interfaceAddress = route->interface->address; + net_address_module_info *addressModule = domain->address_module; + + if (addressModule->is_empty_address(source, true)) + addressModule->set_to(source, interfaceAddress); + else + status = addressModule->update_to(source, interfaceAddress); + } + + if (status != B_OK) + put_route_internal(domain, route); + else + *_route = route; + + return status; +} + + void put_route(struct net_domain *_domain, net_route *route) { Modified: haiku/trunk/src/add-ons/kernel/network/stack/routes.h =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/routes.h 2007-04-11 21:06:35 UTC (rev 20659) +++ haiku/trunk/src/add-ons/kernel/network/stack/routes.h 2007-04-11 22:24:12 UTC (rev 20660) @@ -42,6 +42,8 @@ void invalidate_routes(net_domain *, net_interface *); struct net_route *get_route(struct net_domain *domain, const struct sockaddr *address); +status_t get_buffer_route(struct net_domain *domain, + struct net_buffer *buffer, struct net_route **_route); void put_route(struct net_domain *domain, struct net_route *route); status_t register_route_info(struct net_domain *domain, From bonefish at cs.tu-berlin.de Thu Apr 12 01:16:16 2007 From: bonefish at cs.tu-berlin.de (Ingo Weinhold) Date: Thu, 12 Apr 2007 01:16:16 +0200 Subject: [Haiku-commits] r20545 - buildtools/trunk/jam In-Reply-To: <40887606593-BeMail@zon> References: <40887606593-BeMail@zon> Message-ID: <20070412011616.1591.4@cs.tu-berlin.de> On 2007-04-11 at 22:26:31 [+0200], Axel D?rfler wrote: > Ingo Weinhold wrote: > > > I can only report that I had this error :-) > > > I could try to reproduce it again by reverting my local changes to > > > HaikuImage, and eventually find out which command triggers it. > > Don't worry. I'm not really in the mood for hunting obscure Jam bugs, > > as > > long as we can work around so easily. :-) > > Removing binaries isn't exactly a nice solution, but as it seems to > work... :-) Since jam is ignorant about targets removed from the build system (including the objects in a static library), fully building the library every time it is updated, is the only way to at least not carry the removed objects about forever. If that also solves your problem, good, but that's not the reason for the change in the first place. CU, Ingo From axeld at pinc-software.de Thu Apr 12 09:37:28 2007 From: axeld at pinc-software.de (Axel =?iso-8859-15?q?D=F6rfler?=) Date: Thu, 12 Apr 2007 09:37:28 +0200 CEST Subject: [Haiku-commits] r20545 - buildtools/trunk/jam In-Reply-To: <20070412011616.1591.4@cs.tu-berlin.de> Message-ID: <974024832-BeMail@zon> Ingo Weinhold wrote: > On 2007-04-11 at 22:26:31 [+0200], Axel D?rfler > > wrote: > > Ingo Weinhold wrote: > > > > I can only report that I had this error :-) > > > > I could try to reproduce it again by reverting my local changes > > > > to > > > > HaikuImage, and eventually find out which command triggers it. > > > Don't worry. I'm not really in the mood for hunting obscure Jam > > > bugs, > > > as long as we can work around so easily. :-) > > Removing binaries isn't exactly a nice solution, but as it seems to > > work... :-) > Since jam is ignorant about targets removed from the build system > (including the objects in a static library), fully building the > library > every time it is updated, is the only way to at least not carry the > removed > objects about forever. If that also solves your problem, good, but > that's > not the reason for the change in the first place. Either I don't understand you, or you misunderstood me: by "removing binaries" I meant to remove targets from the BEOS_BIN variable. Bye, Axel. From hugosantos at mail.berlios.de Thu Apr 12 10:22:56 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Thu, 12 Apr 2007 10:22:56 +0200 Subject: [Haiku-commits] r20661 - haiku/trunk/src/add-ons/kernel/network/protocols/udp Message-ID: <200704120822.l3C8Muv9006041@sheep.berlios.de> Author: hugosantos Date: 2007-04-12 10:22:47 +0200 (Thu, 12 Apr 2007) New Revision: 20661 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20661&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp Log: made UDP agnostic to the underlying network protocol (preparing some work into the future). Modified: haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp 2007-04-11 22:24:12 UTC (rev 20660) +++ haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp 2007-04-12 08:22:47 UTC (rev 20661) @@ -15,6 +15,7 @@ #include #include +#include #include #include @@ -28,14 +29,25 @@ #include #include +// TODO move the locking from the FIFO to the whole Endpoint +// much like we did with the LinkProtocol. //#define TRACE_UDP #ifdef TRACE_UDP -# define TRACE(x) dprintf x # define TRACE_BLOCK(x) dump_block x +// do not remove the space before ', ##args' if you want this +// to compile with gcc 2.95 +# define TRACE_EP(format, args...) dprintf("UDP [%llu] %p " format "\n", \ + system_time(), this , ##args) +# define TRACE_EPM(format, args...) dprintf("UDP [%llu] " format "\n", \ + system_time() , ##args) +# define TRACE_DOMAIN(format, args...) dprintf("UDP [%llu] (%d) " format \ + "\n", system_time(), Domain()->family , ##args) #else -# define TRACE(x) # define TRACE_BLOCK(x) +# define TRACE_EP(args...) do { } while (0) +# define TRACE_EPM(args...) do { } while (0) +# define TRACE_DOMAIN(args...) do { } while (0) #endif @@ -50,12 +62,15 @@ typedef NetBufferField UDPChecksumField; +class UdpDomainSupport; class UdpEndpoint : public net_protocol { public: UdpEndpoint(net_socket *socket); ~UdpEndpoint(); + status_t InitCheck() const; + status_t Bind(sockaddr *newAddr); status_t Unbind(sockaddr *newAddr); status_t Connect(const sockaddr *newAddr); @@ -64,21 +79,35 @@ status_t Close(); status_t Free(); - status_t SendData(net_buffer *buffer, net_route *route); + status_t SendRoutedData(net_buffer *buffer, net_route *route); + status_t SendData(net_buffer *buffer); ssize_t BytesAvailable(); - status_t FetchData(size_t numBytes, uint32 flags, + status_t FetchData(size_t numBytes, uint32 flags, net_buffer **_buffer); status_t StoreData(net_buffer *buffer); - UdpEndpoint *hash_link; + net_domain * Domain() const + { + return socket->first_protocol->module->get_domain(socket->first_protocol); + } + + net_address_module_info *AddressModule() const + { + return Domain()->address_module; + } + + UdpDomainSupport *DomainSupport() const { return fDomain; } + + UdpEndpoint *hash_link; // link required by hash_table (see khash.h) private: status_t _Activate(); status_t _Deactivate(); - - bool fActive; + + UdpDomainSupport *fDomain; + bool fActive; // an active UdpEndpoint is part of the endpoint // hash (and it is bound and optionally connected) net_fifo fFifo; @@ -86,253 +115,227 @@ }; -class UdpEndpointManager { - typedef std::pair HashKey; +class UdpDomainSupport : public DoublyLinkedListLinkImpl { +public: + UdpDomainSupport(net_domain *domain); + ~UdpDomainSupport(); - class Ephemerals { - public: - Ephemerals(); - ~Ephemerals(); - - uint16 GetNext(hash_table *activeEndpoints); - static const uint16 kFirst = 49152; - static const uint16 kLast = 65535; - private: - uint16 fLastUsed; + status_t InitCheck() const; + + net_domain *Domain() const { return fDomain; } + + void Ref() { fEndpointCount++; } + void Put() { fEndpointCount--; } + + bool IsEmpty() const { return fEndpointCount == 0; } + + status_t DemuxIncomingBuffer(net_buffer *buffer); + status_t CheckBindRequest(sockaddr *address, int socketOptions); + status_t ActivateEndpoint(UdpEndpoint *endpoint); + status_t DeactivateEndpoint(UdpEndpoint *endpoint); + + uint16 GetEphemeralPort(); + +private: + struct HashKey { + HashKey() {} + HashKey(net_address_module_info *module, const sockaddr *_local, + const sockaddr *_peer) + : address_module(module), local(_local), peer(_peer) {} + + net_address_module_info *address_module; + const sockaddr *local; + const sockaddr *peer; }; - -public: - UdpEndpointManager(); - ~UdpEndpointManager(); - status_t DemuxBroadcast(net_buffer *buffer); - status_t DemuxMulticast(net_buffer *buffer); - status_t DemuxUnicast(net_buffer *buffer); - status_t DemuxIncomingBuffer(net_buffer *buffer); - status_t ReceiveData(net_buffer *buffer); + UdpEndpoint *_FindActiveEndpoint(sockaddr *ourAddress, + sockaddr *peerAddress); + status_t _DemuxBroadcast(net_buffer *buffer); + status_t _DemuxMulticast(net_buffer *buffer); + status_t _DemuxUnicast(net_buffer *buffer); - static int Compare(void *udpEndpoint, const void *_key); - static uint32 ComputeHash(const sockaddr *ourAddress, - const sockaddr *peerAddress); - static uint32 Hash(void *udpEndpoint, const void *key, uint32 range); + uint16 _GetNextEphemeral(); - UdpEndpoint *FindActiveEndpoint(sockaddr *ourAddress, - sockaddr *peerAddress); - status_t CheckBindRequest(sockaddr *address, int socketOptions); + static int _Compare(void *udpEndpoint, const void *_key); + static uint32 _Hash(void *udpEndpoint, const void *key, uint32 range); - status_t ActivateEndpoint(UdpEndpoint *endpoint); - status_t DeactivateEndpoint(UdpEndpoint *endpoint); + net_address_module_info *AddressModule() const + { + return fDomain->address_module; + } - status_t OpenEndpoint(UdpEndpoint *endpoint); - status_t CloseEndpoint(UdpEndpoint *endpoint); - status_t FreeEndpoint(UdpEndpoint *endpoint); - - uint16 GetEphemeralPort(); + net_domain *fDomain; + uint16 fLastUsedEphemeral; + hash_table *fActiveEndpoints; + uint32 fEndpointCount; - benaphore *Locker(); - status_t InitCheck() const; -private: - benaphore fLock; - hash_table *fActiveEndpoints; - static const uint32 kNumHashBuckets = 0x800; - // if you change this, adjust the shifting in - // Hash() accordingly! - Ephemerals fEphemerals; - status_t fStatus; - uint32 fEndpointCount; + static const uint16 kFirst = 49152; + static const uint16 kLast = 65535; + static const uint32 kNumHashBuckets = 0x800; + // if you change this, adjust the shifting in + // Hash() accordingly! }; -static UdpEndpointManager *sUdpEndpointManager; +typedef DoublyLinkedList UdpDomainList; -static net_domain *sDomain; -static net_address_module_info *sAddressModule; -net_buffer_module_info *gBufferModule; -static net_datalink_module_info *sDatalinkModule; -static net_stack_module_info *sStackModule; +class UdpEndpointManager { +public: + UdpEndpointManager(); + ~UdpEndpointManager(); + status_t DemuxIncomingBuffer(net_domain *domain, + net_buffer *buffer); + status_t ReceiveData(net_buffer *buffer); -// #pragma mark - + UdpDomainSupport *OpenEndpoint(UdpEndpoint *endpoint); + status_t FreeEndpoint(UdpDomainSupport *domain); + uint16 GetEphemeralPort(); -UdpEndpointManager::Ephemerals::Ephemerals() - : - fLastUsed(kLast) -{ -} + benaphore *Locker() { return &fLock; } + status_t InitCheck() const; +private: + UdpDomainSupport *_GetDomain(net_domain *domain, bool create); -UdpEndpointManager::Ephemerals::~Ephemerals() -{ -} + benaphore fLock; + status_t fStatus; + UdpDomainList fDomains; +}; -uint16 -UdpEndpointManager::Ephemerals::GetNext(hash_table *activeEndpoints) -{ - uint16 stop, curr, ncurr; - if (fLastUsed < kLast) { - stop = fLastUsed; - curr = fLastUsed + 1; - } else { - stop = kLast; - curr = kFirst; - } +static UdpEndpointManager *sUdpEndpointManager; - TRACE(("UdpEndpointManager::Ephemerals::GetNext()...\n")); - // TODO: a free list could be used to avoid the impact of these - // two nested loops most of the time... let's see how bad this really is - UdpEndpoint *endpoint; - struct hash_iterator endpointIterator; - hash_open(activeEndpoints, &endpointIterator); - bool found = false; - uint16 endpointPort; - while(!found && curr != stop) { - TRACE(("...trying port %u...\n", curr)); - ncurr = htons(curr); - for(hash_rewind(activeEndpoints, &endpointIterator); !found; ) { - endpoint = (UdpEndpoint *)hash_next(activeEndpoints, &endpointIterator); - if (!endpoint) { - found = true; - break; - } - endpointPort = sAddressModule->get_port( - (sockaddr *)&endpoint->socket->address); - TRACE(("...checking endpoint %p (port=%u)...\n", endpoint, - ntohs(endpointPort))); - if (endpointPort == ncurr) - break; - } - if (!found) { - if (curr < kLast) - curr++; - else - curr = kFirst; - } - } - hash_close(activeEndpoints, &endpointIterator, false); - if (!found) - return 0; - TRACE(("...using port %u\n", curr)); - fLastUsed = curr; - return curr; -} +net_buffer_module_info *gBufferModule; +static net_datalink_module_info *sDatalinkModule; +static net_stack_module_info *sStackModule; // #pragma mark - -UdpEndpointManager::UdpEndpointManager() +UdpDomainSupport::UdpDomainSupport(net_domain *domain) : - fStatus(B_NO_INIT), + fDomain(domain), + fLastUsedEphemeral(kLast), fEndpointCount(0) { - fActiveEndpoints = hash_init(kNumHashBuckets, offsetof(UdpEndpoint, hash_link), - &Compare, &Hash); - if (fActiveEndpoints == NULL) { - fStatus = B_NO_MEMORY; - return; - } - - fStatus = benaphore_init(&fLock, "UDP endpoints"); - if (fStatus < B_OK) - hash_uninit(fActiveEndpoints); + fActiveEndpoints = hash_init(kNumHashBuckets, offsetof(UdpEndpoint, hash_link), + &_Compare, &_Hash); } -UdpEndpointManager::~UdpEndpointManager() +UdpDomainSupport::~UdpDomainSupport() { - benaphore_destroy(&fLock); - hash_uninit(fActiveEndpoints); + if (fActiveEndpoints) + hash_uninit(fActiveEndpoints); } -inline benaphore * -UdpEndpointManager::Locker() +status_t +UdpDomainSupport::InitCheck() const { - return &fLock; + return fActiveEndpoints ? B_OK : B_NO_MEMORY; } -inline status_t -UdpEndpointManager::InitCheck() const +status_t +UdpDomainSupport::DemuxIncomingBuffer(net_buffer *buffer) { - return fStatus; + if (buffer->flags & MSG_BCAST) + return _DemuxBroadcast(buffer); + else if (buffer->flags & MSG_MCAST) + return _DemuxMulticast(buffer); + + return _DemuxUnicast(buffer); } -// #pragma mark - hashing +status_t +UdpDomainSupport::CheckBindRequest(sockaddr *address, int socketOptions) +{ // sUdpEndpointManager->Locker() must be locked! + status_t status = B_OK; + UdpEndpoint *otherEndpoint; + sockaddr *otherAddr; + struct hash_iterator endpointIterator; + // Iterate over all active UDP-endpoints and check if the requested bind + // is allowed (see figure 22.24 in [Stevens - TCP2, p735]): + hash_open(fActiveEndpoints, &endpointIterator); + TRACE_DOMAIN("CheckBindRequest() for %s...", + AddressString(fDomain, address, true).Data()); + while(1) { + otherEndpoint = (UdpEndpoint *)hash_next(fActiveEndpoints, &endpointIterator); + if (!otherEndpoint) + break; + otherAddr = (sockaddr *)&otherEndpoint->socket->address; + TRACE_DOMAIN(" ...checking endpoint %p (port=%u)...", otherEndpoint, + ntohs(AddressModule()->get_port(otherAddr))); + if (AddressModule()->equal_ports(otherAddr, address)) { + // port is already bound, SO_REUSEADDR or SO_REUSEPORT is required: + if (otherEndpoint->socket->options & (SO_REUSEADDR | SO_REUSEPORT) == 0 + || socketOptions & (SO_REUSEADDR | SO_REUSEPORT) == 0) { + status = EADDRINUSE; + break; + } + // if both addresses are the same, SO_REUSEPORT is required: + if (AddressModule()->equal_addresses(otherAddr, address) + && (otherEndpoint->socket->options & SO_REUSEPORT == 0 + || socketOptions & SO_REUSEPORT == 0)) { + status = EADDRINUSE; + break; + } + } + } + hash_close(fActiveEndpoints, &endpointIterator, false); -/*static*/ int -UdpEndpointManager::Compare(void *_udpEndpoint, const void *_key) -{ - struct UdpEndpoint *udpEndpoint = (UdpEndpoint*)_udpEndpoint; - const HashKey *key = (const HashKey *)_key; + TRACE_DOMAIN(" CheckBindRequest done (status=%lx)", status); + return status; +} - sockaddr *ourAddr = (sockaddr *)&udpEndpoint->socket->address; - sockaddr *peerAddr = (sockaddr *)&udpEndpoint->socket->peer; - if (sAddressModule->equal_addresses_and_ports(ourAddr, key->first) - && sAddressModule->equal_addresses_and_ports(peerAddr, key->second)) - return 0; - - return 1; +status_t +UdpDomainSupport::ActivateEndpoint(UdpEndpoint *endpoint) +{ // sUdpEndpointManager->Locker() must be locked! + TRACE_DOMAIN("Endpoint(%s) was activated", + AddressString(fDomain, (sockaddr *)&endpoint->socket->address, true).Data()); + return hash_insert(fActiveEndpoints, endpoint); } -/*static*/ inline uint32 -UdpEndpointManager::ComputeHash(const sockaddr *ourAddress, - const sockaddr *peerAddress) -{ - return sAddressModule->hash_address_pair(ourAddress, peerAddress); +status_t +UdpDomainSupport::DeactivateEndpoint(UdpEndpoint *endpoint) +{ // sUdpEndpointManager->Locker() must be locked! + TRACE_DOMAIN("Endpoint(%s) was deactivated", + AddressString(fDomain, (sockaddr *)&endpoint->socket->address, true).Data()); + return hash_remove(fActiveEndpoints, endpoint); } -/*static*/ uint32 -UdpEndpointManager::Hash(void *_udpEndpoint, const void *_key, uint32 range) +uint16 +UdpDomainSupport::GetEphemeralPort() { - HashKey addresses; - uint32 hash; - - if (_udpEndpoint) { - const UdpEndpoint *udpEndpoint = (const UdpEndpoint *)_udpEndpoint; - addresses = HashKey((const sockaddr *)&udpEndpoint->socket->address, - (const sockaddr *)&udpEndpoint->socket->peer); - } else { - addresses = *(const HashKey *)_key; - } - - hash = ComputeHash(addresses.first, addresses.second); - - // move the bits into the relevant range (as defined by kNumHashBuckets): - hash = (hash & 0x000007FF) ^ (hash & 0x003FF800) >> 11 - ^ (hash & 0xFFC00000UL) >> 22; - - TRACE(("UDP-endpoint hash is %lx\n", hash % range)); - return hash % range; + return _GetNextEphemeral(); } -// #pragma mark - inbound - - UdpEndpoint * -UdpEndpointManager::FindActiveEndpoint(sockaddr *ourAddress, +UdpDomainSupport::_FindActiveEndpoint(sockaddr *ourAddress, sockaddr *peerAddress) { - TRACE(("trying to find UDP-endpoint for (l:%s p:%s)\n", - AddressString(sDomain, ourAddress, true).Data(), - AddressString(sDomain, peerAddress, true).Data())); + TRACE_DOMAIN("finding Endpoint for %s -> %s", + AddressString(fDomain, ourAddress, true).Data(), + AddressString(fDomain, peerAddress, true).Data()); - HashKey key(ourAddress, peerAddress); + HashKey key(AddressModule(), ourAddress, peerAddress); return (UdpEndpoint *)hash_lookup(fActiveEndpoints, &key); } status_t -UdpEndpointManager::DemuxBroadcast(net_buffer *buffer) +UdpDomainSupport::_DemuxBroadcast(net_buffer *buffer) { sockaddr *peerAddr = (sockaddr *)&buffer->source; sockaddr *broadcastAddr = (sockaddr *)&buffer->destination; @@ -340,40 +343,37 @@ if (buffer->interface) mask = (sockaddr *)buffer->interface->mask; - TRACE(("demuxing buffer %p as broadcast...\n", buffer)); + TRACE_DOMAIN("_DemuxBroadcast(%p)", buffer); - uint16 incomingPort = sAddressModule->get_port(broadcastAddr); + uint16 incomingPort = AddressModule()->get_port(broadcastAddr); UdpEndpoint *endpoint; - sockaddr *addr, *connectAddr; - struct hash_iterator endpointIterator; - for(hash_open(fActiveEndpoints, &endpointIterator); ; ) { - endpoint = (UdpEndpoint *)hash_next(fActiveEndpoints, &endpointIterator); - if (!endpoint) - break; + hash_iterator endpointIterator; + hash_open(fActiveEndpoints, &endpointIterator); + while ((endpoint = (UdpEndpoint *)hash_next(fActiveEndpoints, + &endpointIterator)) != NULL) { + sockaddr *addr = (sockaddr *)&endpoint->socket->address; + TRACE_DOMAIN(" _DemuxBroadcast(): checking endpoint %s...", + AddressString(fDomain, addr, true).Data()); - addr = (sockaddr *)&endpoint->socket->address; - TRACE(("UDP-DemuxBroadcast() is checking endpoint %s...\n", - AddressString(sDomain, addr, true).Data())); - - if (incomingPort != sAddressModule->get_port(addr)) { + if (incomingPort != AddressModule()->get_port(addr)) { // ports don't match, so we do not dispatch to this endpoint... continue; } - connectAddr = (sockaddr *)&endpoint->socket->peer; - if (!sAddressModule->is_empty_address(connectAddr, true)) { + sockaddr *connectAddr = (sockaddr *)&endpoint->socket->peer; + if (!AddressModule()->is_empty_address(connectAddr, true)) { // endpoint is connected to a specific destination, we check if // this datagram is from there: - if (!sAddressModule->equal_addresses_and_ports(connectAddr, peerAddr)) { + if (!AddressModule()->equal_addresses_and_ports(connectAddr, peerAddr)) { // no, datagram is from another peer, so we do not dispatch to // this endpoint... continue; } } - if (sAddressModule->equal_masked_addresses(addr, broadcastAddr, mask) - || sAddressModule->is_empty_address(addr, false)) { + if (AddressModule()->equal_masked_addresses(addr, broadcastAddr, mask) + || AddressModule()->is_empty_address(addr, false)) { // address matches, dispatch to this endpoint: endpoint->StoreData(buffer); } @@ -384,39 +384,42 @@ status_t -UdpEndpointManager::DemuxMulticast(net_buffer *buffer) +UdpDomainSupport::_DemuxMulticast(net_buffer *buffer) { // TODO: implement! + TRACE_DOMAIN("_DemuxMulticast(%p)", buffer); + return B_ERROR; } status_t -UdpEndpointManager::DemuxUnicast(net_buffer *buffer) +UdpDomainSupport::_DemuxUnicast(net_buffer *buffer) { struct sockaddr *peerAddr = (struct sockaddr *)&buffer->source; struct sockaddr *localAddr = (struct sockaddr *)&buffer->destination; - TRACE(("demuxing buffer %p as unicast...\n", buffer)); + TRACE_DOMAIN("_DemuxUnicast(%p)", buffer); UdpEndpoint *endpoint; // look for full (most special) match: - endpoint = FindActiveEndpoint(localAddr, peerAddr); + endpoint = _FindActiveEndpoint(localAddr, peerAddr); if (!endpoint) { // look for endpoint matching local address & port: - endpoint = FindActiveEndpoint(localAddr, NULL); + endpoint = _FindActiveEndpoint(localAddr, NULL); if (!endpoint) { // look for endpoint matching peer address & port and local port: sockaddr localPortAddr; - sAddressModule->set_to_empty_address(&localPortAddr); - uint16 localPort = sAddressModule->get_port(localAddr); - sAddressModule->set_port(&localPortAddr, localPort); - endpoint = FindActiveEndpoint(&localPortAddr, peerAddr); + AddressModule()->set_to_empty_address(&localPortAddr); + uint16 localPort = AddressModule()->get_port(localAddr); + AddressModule()->set_port(&localPortAddr, localPort); + endpoint = _FindActiveEndpoint(&localPortAddr, peerAddr); if (!endpoint) { // last chance: look for endpoint matching local port only: - endpoint = FindActiveEndpoint(&localPortAddr, NULL); + endpoint = _FindActiveEndpoint(&localPortAddr, NULL); } } } + if (!endpoint) return B_NAME_NOT_FOUND; @@ -425,25 +428,148 @@ } +uint16 +UdpDomainSupport::_GetNextEphemeral() +{ + uint16 stop, curr, ncurr; + if (fLastUsedEphemeral < kLast) { + stop = fLastUsedEphemeral; + curr = fLastUsedEphemeral + 1; + } else { + stop = kLast; + curr = kFirst; + } + + TRACE_DOMAIN("_GetNextEphemeral()"); + // TODO: a free list could be used to avoid the impact of these + // two nested loops most of the time... let's see how bad this really is + bool found = false; + uint16 endpointPort; + hash_iterator endpointIterator; + hash_open(fActiveEndpoints, &endpointIterator); + while(!found && curr != stop) { + TRACE_DOMAIN(" _GetNextEphemeral(): trying port %hu...", curr); + ncurr = htons(curr); + hash_rewind(fActiveEndpoints, &endpointIterator); + while (!found) { + UdpEndpoint *endpoint = (UdpEndpoint *)hash_next(fActiveEndpoints, + &endpointIterator); + if (!endpoint) { + found = true; + break; + } + endpointPort = AddressModule()->get_port( + (sockaddr *)&endpoint->socket->address); + TRACE_DOMAIN(" _GetNextEphemeral(): checking endpoint %p (port %hu)...", + endpoint, ntohs(endpointPort)); + if (endpointPort == ncurr) + break; + } + if (!found) { + if (curr < kLast) + curr++; + else + curr = kFirst; + } + } + hash_close(fActiveEndpoints, &endpointIterator, false); + if (!found) + return 0; + TRACE_DOMAIN(" _GetNextEphemeral(): ...using port %hu", curr); + fLastUsedEphemeral = curr; + return curr; +} + + +int +UdpDomainSupport::_Compare(void *_udpEndpoint, const void *_key) +{ + struct UdpEndpoint *udpEndpoint = (UdpEndpoint*)_udpEndpoint; + const HashKey *key = (const HashKey *)_key; + + sockaddr *ourAddr = (sockaddr *)&udpEndpoint->socket->address; + sockaddr *peerAddr = (sockaddr *)&udpEndpoint->socket->peer; + + net_address_module_info *addressModule = key->address_module; + + if (addressModule->equal_addresses_and_ports(ourAddr, key->local) + && addressModule->equal_addresses_and_ports(peerAddr, key->peer)) + return 0; + + return 1; +} + + +uint32 +UdpDomainSupport::_Hash(void *_udpEndpoint, const void *_key, uint32 range) +{ + const HashKey *key = (const HashKey *)_key; + HashKey key_storage; + uint32 hash; + + if (_udpEndpoint) { + const UdpEndpoint *udpEndpoint = (const UdpEndpoint *)_udpEndpoint; + key_storage = HashKey(udpEndpoint->DomainSupport()->AddressModule(), + (const sockaddr *)&udpEndpoint->socket->address, + (const sockaddr *)&udpEndpoint->socket->peer); + key = &key_storage; + } + + hash = key->address_module->hash_address_pair(key->local, key->peer); + + // move the bits into the relevant range (as defined by kNumHashBuckets): + hash = (hash & 0x000007FF) ^ (hash & 0x003FF800) >> 11 + ^ (hash & 0xFFC00000UL) >> 22; + + return hash % range; +} + + +// #pragma mark - + + +UdpEndpointManager::UdpEndpointManager() +{ + fStatus = benaphore_init(&fLock, "UDP endpoints"); +} + + +UdpEndpointManager::~UdpEndpointManager() +{ + benaphore_destroy(&fLock); +} + + status_t -UdpEndpointManager::DemuxIncomingBuffer(net_buffer *buffer) +UdpEndpointManager::InitCheck() const { - status_t status; + return fStatus; +} - if (buffer->flags & MSG_BCAST) - status = DemuxBroadcast(buffer); - else if (buffer->flags & MSG_MCAST) - status = DemuxMulticast(buffer); - else - status = DemuxUnicast(buffer); - return status; +// #pragma mark - inbound + + +status_t +UdpEndpointManager::DemuxIncomingBuffer(net_domain *domain, net_buffer *buffer) +{ + UdpDomainSupport *domainSupport = _GetDomain(domain, false); + if (domainSupport == NULL) { + // we don't instantiate domain supports in the + // RX path as we are only interested in delivering + // data to existing sockets. + return B_BAD_VALUE; + } + + return domainSupport->DemuxIncomingBuffer(buffer); } status_t UdpEndpointManager::ReceiveData(net_buffer *buffer) { + TRACE_EPM("ReceiveData(%p [%ld bytes])", buffer, buffer->size); + NetBufferHeaderReader bufferHeader(buffer); if (bufferHeader.Status() < B_OK) return bufferHeader.Status(); @@ -453,44 +579,40 @@ struct sockaddr *source = (struct sockaddr *)&buffer->source; struct sockaddr *destination = (struct sockaddr *)&buffer->destination; - BenaphoreLocker locker(sUdpEndpointManager->Locker()); - if (!sDomain) { - // domain and address module are not known yet, we copy them from - // the buffer's interface (if any): - if (buffer->interface == NULL || buffer->interface->domain == NULL) - sDomain = sStackModule->get_domain(AF_INET); - else - sDomain = buffer->interface->domain; - if (sDomain == NULL) { - // this shouldn't occur, of course, but who knows... - return B_BAD_VALUE; - } - sAddressModule = sDomain->address_module; + if (buffer->interface == NULL || buffer->interface->domain == NULL) { + TRACE_EPM(" ReceiveData(): UDP packed dropped as there was no domain " + "specified (interface %p).", buffer->interface); + return B_BAD_VALUE; } - sAddressModule->set_port(source, header.source_port); - sAddressModule->set_port(destination, header.destination_port); - TRACE(("UDP received data from source %s for destination %s\n", - AddressString(sDomain, source, true).Data(), - AddressString(sDomain, destination, true).Data())); + net_domain *domain = buffer->interface->domain; + net_address_module_info *addressModule = domain->address_module; + + BenaphoreLocker _(fLock); + + addressModule->set_port(source, header.source_port); + addressModule->set_port(destination, header.destination_port); + + TRACE_EPM(" ReceiveData(): data from %s to %s", + AddressString(domain, source, true).Data(), + AddressString(domain, destination, true).Data()); + uint16 udpLength = ntohs(header.udp_length); if (udpLength > buffer->size) { - TRACE(("buffer %p is too short (%lu instead of %u), we drop it!\n", - buffer, buffer->size, udpLength)); + TRACE_EPM(" ReceiveData(): buffer is too short, expected %hu.", + udpLength); return B_MISMATCHED_VALUES; } - if (buffer->size > udpLength) { - TRACE(("buffer %p is too long (%lu instead of %u), trimming it.\n", - buffer, buffer->size, udpLength)); + + if (buffer->size > udpLength) gBufferModule->trim(buffer, udpLength); - } if (header.udp_checksum != 0) { // check UDP-checksum (simulating a so-called "pseudo-header"): Checksum udpChecksum; - sAddressModule->checksum_address(&udpChecksum, source); - sAddressModule->checksum_address(&udpChecksum, destination); - udpChecksum + addressModule->checksum_address(&udpChecksum, source); + addressModule->checksum_address(&udpChecksum, destination); + udpChecksum << (uint16)htons(IPPROTO_UDP) << header.udp_length // peculiar but correct: UDP-len is used twice for checksum @@ -498,7 +620,7 @@ << Checksum::BufferHelper(buffer, gBufferModule); uint16 sum = udpChecksum; if (sum != 0) { - TRACE(("buffer %p has bad checksum (%u), we drop it!\n", buffer, sum)); + TRACE_EPM(" ReceiveData(): bad checksum 0x%hx.", sum); return B_BAD_VALUE; } } @@ -506,9 +628,9 @@ bufferHeader.Remove(); // remove UDP-header from buffer before passing it on - status_t status = DemuxIncomingBuffer(buffer); + status_t status = DemuxIncomingBuffer(domain, buffer); if (status < B_OK) { - TRACE(("no matching endpoint found for buffer %p, we drop it!", buffer)); + TRACE_EPM(" ReceiveData(): no endpoint."); // TODO: send ICMP-error return B_ERROR; } @@ -517,105 +639,66 @@ } -// #pragma mark - activation +UdpDomainSupport * +UdpEndpointManager::OpenEndpoint(UdpEndpoint *endpoint) +{ + BenaphoreLocker _(fLock); + UdpDomainSupport *domain = _GetDomain(endpoint->Domain(), true); + if (domain) + domain->Ref(); + return domain; +} + status_t -UdpEndpointManager::CheckBindRequest(sockaddr *address, int socketOptions) -{ // sUdpEndpointManager->Locker() must be locked! - status_t status = B_OK; - UdpEndpoint *otherEndpoint; - sockaddr *otherAddr; - struct hash_iterator endpointIterator; +UdpEndpointManager::FreeEndpoint(UdpDomainSupport *domain) +{ + BenaphoreLocker _(fLock); - // Iterate over all active UDP-endpoints and check if the requested bind - // is allowed (see figure 22.24 in [Stevens - TCP2, p735]): - hash_open(fActiveEndpoints, &endpointIterator); - TRACE(("UdpEndpointManager::CheckBindRequest() for %s...\n", - AddressString(sDomain, address, true).Data())); - while(1) { - otherEndpoint = (UdpEndpoint *)hash_next(fActiveEndpoints, &endpointIterator); - if (!otherEndpoint) - break; - otherAddr = (sockaddr *)&otherEndpoint->socket->address; - TRACE(("...checking endpoint %p (port=%u)...\n", otherEndpoint, - ntohs(sAddressModule->get_port(otherAddr)))); - if (sAddressModule->equal_ports(otherAddr, address)) { - // port is already bound, SO_REUSEADDR or SO_REUSEPORT is required: - if (otherEndpoint->socket->options & (SO_REUSEADDR | SO_REUSEPORT) == 0 - || socketOptions & (SO_REUSEADDR | SO_REUSEPORT) == 0) { - status = EADDRINUSE; - break; - } - // if both addresses are the same, SO_REUSEPORT is required: - if (sAddressModule->equal_addresses(otherAddr, address) - && (otherEndpoint->socket->options & SO_REUSEPORT == 0 - || socketOptions & SO_REUSEPORT == 0)) { - status = EADDRINUSE; - break; - } - } + domain->Put(); + + if (domain->IsEmpty()) { + fDomains.Remove(domain); + delete domain; } - hash_close(fActiveEndpoints, &endpointIterator, false); - TRACE(("UdpEndpointManager::CheckBindRequest done (status=%lx)\n", status)); - return status; + return B_OK; } -status_t -UdpEndpointManager::ActivateEndpoint(UdpEndpoint *endpoint) -{ // sUdpEndpointManager->Locker() must be locked! - TRACE(("UDP-endpoint(%s) is activated\n", - AddressString(sDomain, (sockaddr *)&endpoint->socket->address, true).Data())); - return hash_insert(fActiveEndpoints, endpoint); -} +// #pragma mark - -status_t -UdpEndpointManager::DeactivateEndpoint(UdpEndpoint *endpoint) -{ // sUdpEndpointManager->Locker() must be locked! - TRACE(("UDP-endpoint(%s) is deactivated\n", - AddressString(sDomain, (sockaddr *)&endpoint->socket->address, true).Data())); - return hash_remove(fActiveEndpoints, endpoint); -} +UdpDomainSupport * +UdpEndpointManager::_GetDomain(net_domain *domain, bool create) +{ + UdpDomainList::Iterator it = fDomains.GetIterator(); - -status_t -UdpEndpointManager::OpenEndpoint(UdpEndpoint *endpoint) -{ // sUdpEndpointManager->Locker() must be locked! - if (fEndpointCount++ == 0) { - sDomain = sStackModule->get_domain(AF_INET); - sAddressModule = sDomain->address_module; - TRACE(("udp: setting domain-pointer to %p.\n", sDomain)); + // TODO convert this into a Hashtable or install per-domain + // receiver handlers that forward the requests to the + // appropriate DemuxIncomingBuffer(). For instance, while + // being constructed UdpDomainSupport could call + // register_domain_receiving_protocol() with the right + // family. + while (it.HasNext()) { + UdpDomainSupport *domainSupport = it.Next(); + if (domainSupport->Domain() == domain) + return domainSupport; } - return B_OK; -} + if (!create) + return NULL; -status_t -UdpEndpointManager::CloseEndpoint(UdpEndpoint *endpoint) -{ // sUdpEndpointManager->Locker() must be locked! - return B_OK; -} - - -status_t -UdpEndpointManager::FreeEndpoint(UdpEndpoint *endpoint) -{ // sUdpEndpointManager->Locker() must be locked! - if (--fEndpointCount == 0) { - TRACE(("udp: clearing domain-pointer and address-module.\n")); - sDomain = NULL; - sAddressModule = NULL; + UdpDomainSupport *domainSupport = + new (std::nothrow) UdpDomainSupport(domain); + if (domainSupport == NULL || domainSupport->InitCheck() < B_OK) { + delete domainSupport; + return NULL; } - return B_OK; -} - [... truncated: 470 lines follow ...] From jackburton at mail.berlios.de Thu Apr 12 14:28:14 2007 From: jackburton at mail.berlios.de (jackburton at BerliOS) Date: Thu, 12 Apr 2007 14:28:14 +0200 Subject: [Haiku-commits] r20662 - haiku/trunk/src/servers/app Message-ID: <200704121228.l3CCSE40009188@sheep.berlios.de> Author: jackburton Date: 2007-04-12 14:28:13 +0200 (Thu, 12 Apr 2007) New Revision: 20662 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20662&view=rev Modified: haiku/trunk/src/servers/app/Desktop.cpp Log: Menu windows are no longer the preferred keyboard events target (for now, at least). This feature wasn't used yet anyway, and turning it off cures bug #1152. Modified: haiku/trunk/src/servers/app/Desktop.cpp =================================================================== --- haiku/trunk/src/servers/app/Desktop.cpp 2007-04-12 08:22:47 UTC (rev 20661) +++ haiku/trunk/src/servers/app/Desktop.cpp 2007-04-12 12:28:13 UTC (rev 20662) @@ -1105,10 +1105,13 @@ EventTarget* Desktop::KeyboardEventTarget() { + // TODO: Not yet useful, and prevents a crashing application + // which has opened menu windows to be debugged (ticket #1152) +#if 0 WindowLayer* window = _CurrentWindows().LastWindow(); if (window != NULL && window->Feel() == kMenuWindowFeel) return &window->EventTarget(); - +#endif if (FocusWindow() != NULL) return &FocusWindow()->EventTarget(); From jackburton at mail.berlios.de Thu Apr 12 15:15:14 2007 From: jackburton at mail.berlios.de (jackburton at BerliOS) Date: Thu, 12 Apr 2007 15:15:14 +0200 Subject: [Haiku-commits] r20663 - haiku/trunk/src/kits/opengl Message-ID: <200704121315.l3CDFECj013050@sheep.berlios.de> Author: jackburton Date: 2007-04-12 15:15:06 +0200 (Thu, 12 Apr 2007) New Revision: 20663 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20663&view=rev Modified: haiku/trunk/src/kits/opengl/GLView.cpp Log: sizeof(B_PAGE_SIZE) != B_PAGE_SIZE. Fixed bug 1151. Sorry for the silly typo. Also uses calloc() so that the direct_buffer_info struct is initialized to 0. Modified: haiku/trunk/src/kits/opengl/GLView.cpp =================================================================== --- haiku/trunk/src/kits/opengl/GLView.cpp 2007-04-12 12:28:13 UTC (rev 20662) +++ haiku/trunk/src/kits/opengl/GLView.cpp 2007-04-12 13:15:06 UTC (rev 20663) @@ -326,7 +326,7 @@ glviewDirectInfo->direct_connected = false; break; } - //direct_info_locker->Unlock(); + //direct_info_locker->Unlock(); if (fRenderer) fRenderer->DirectConnected(localInfo); @@ -502,7 +502,7 @@ glview_direct_info::glview_direct_info() { // TODO: See direct_window_data() in app_server's ServerWindow.cpp - direct_info = (direct_buffer_info *)malloc(sizeof(B_PAGE_SIZE)); + direct_info = (direct_buffer_info *)calloc(1, B_PAGE_SIZE); direct_connected = false; } From axeld at mail.berlios.de Thu Apr 12 15:20:34 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Thu, 12 Apr 2007 15:20:34 +0200 Subject: [Haiku-commits] r20664 - haiku/trunk/src/add-ons/translators/jpeg Message-ID: <200704121320.l3CDKYl3013457@sheep.berlios.de> Author: axeld Date: 2007-04-12 15:20:33 +0200 (Thu, 12 Apr 2007) New Revision: 20664 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20664&view=rev Modified: haiku/trunk/src/add-ons/translators/jpeg/JPEGTranslator.cpp haiku/trunk/src/add-ons/translators/jpeg/be_jerror.cpp Log: * EXIF data is now also parsed in case there was no ioExtension message passed in; the orientation was only honoured in case there was a message before. * Disabled error alerts; they are more annoying than helpful. * Bumped version to 1.2.0. Modified: haiku/trunk/src/add-ons/translators/jpeg/JPEGTranslator.cpp =================================================================== --- haiku/trunk/src/add-ons/translators/jpeg/JPEGTranslator.cpp 2007-04-12 13:15:06 UTC (rev 20663) +++ haiku/trunk/src/add-ons/translators/jpeg/JPEGTranslator.cpp 2007-04-12 13:20:33 UTC (rev 20664) @@ -53,7 +53,7 @@ char translatorName[] = "JPEG Images"; char translatorInfo[] = "?2002-2003, Marcin Konicki\n" - "?2005-2006, Haiku\n" + "?2005-2007, Haiku\n" "\n" "Based on IJG library ? 1991-1998, Thomas G. Lane\n" " http://www.ijg.org/files/\n" @@ -63,7 +63,7 @@ "With some colorspace conversion routines by Magnus Hellman\n" " http://www.bebits.com/app/802\n"; -int32 translatorVersion = 0x111; +int32 translatorVersion = 0x120; // Define the formats we know how to read translation_format inputFormats[] = { @@ -1379,31 +1379,29 @@ jpeg_create_decompress(&cinfo); be_jpeg_stdio_src(&cinfo, in); -#if 1 jpeg_save_markers(&cinfo, MARKER_EXIF, 131072); // make sure the EXIF tag is stored -#endif // Read info about image jpeg_read_header(&cinfo, TRUE); BMessage exif; - if (ioExtension != NULL) { - // add EXIF data to message, if any - jpeg_marker_struct* marker = cinfo.marker_list; - while (marker != NULL) { - if (marker->marker == MARKER_EXIF - && !strncmp((char*)marker->data, "Exif", 4)) { + // parse EXIF data and add it ioExtension, if any + jpeg_marker_struct* marker = cinfo.marker_list; + while (marker != NULL) { + if (marker->marker == MARKER_EXIF + && !strncmp((char*)marker->data, "Exif", 4)) { + if (ioExtension != NULL) { // Strip EXIF header from TIFF data ioExtension->AddData("exif", B_RAW_TYPE, (uint8 *)marker->data + 6, marker->data_length - 6); - - BMemoryIO io(marker->data + 6, marker->data_length - 6); - convert_exif_to_message(io, exif); } - marker = marker->next; + + BMemoryIO io(marker->data + 6, marker->data_length - 6); + convert_exif_to_message(io, exif); } + marker = marker->next; } // Default color info Modified: haiku/trunk/src/add-ons/translators/jpeg/be_jerror.cpp =================================================================== --- haiku/trunk/src/add-ons/translators/jpeg/be_jerror.cpp 2007-04-12 13:15:06 UTC (rev 20663) +++ haiku/trunk/src/add-ons/translators/jpeg/be_jerror.cpp 2007-04-12 13:20:33 UTC (rev 20664) @@ -67,8 +67,10 @@ /* Create the message */ (*cinfo->err->format_message) (cinfo, buffer); +#if 0 /* show error message */ (new BAlert("JPEG Library Error", buffer, "OK", NULL, NULL, B_WIDTH_AS_USUAL, B_STOP_ALERT))->Go(); +#endif /* Let the memory manager delete any temp files before we die */ jpeg_destroy(cinfo); @@ -88,10 +90,12 @@ /* Create the message */ (*cinfo->err->format_message) (cinfo, buffer); +#if 0 /* If it's compressing or decompressing and user turned messages on */ if (!cinfo->is_decompressor || cinfo->err->ShowReadWarnings) /* show warning message */ (new BAlert("JPEG Library Warning", buffer, "OK", NULL, NULL, B_WIDTH_AS_USUAL, B_WARNING_ALERT))->Go(); +#endif } From bonefish at cs.tu-berlin.de Thu Apr 12 16:44:39 2007 From: bonefish at cs.tu-berlin.de (Ingo Weinhold) Date: Thu, 12 Apr 2007 16:44:39 +0200 Subject: [Haiku-commits] r20545 - buildtools/trunk/jam In-Reply-To: <20070412011616.1591.4@cs.tu-berlin.de> References: <40887606593-BeMail@zon> <20070412011616.1591.4@cs.tu-berlin.de> Message-ID: <20070412164439.666.2@cs.tu-berlin.de> On 2007-04-12 at 01:16:16 [+0200], Ingo Weinhold wrote: > On 2007-04-11 at 22:26:31 [+0200], Axel D?rfler > wrote: > > Ingo Weinhold wrote: > > > > I can only report that I had this error :-) > > > > I could try to reproduce it again by reverting my local changes to > > > > HaikuImage, and eventually find out which command triggers it. > > > Don't worry. I'm not really in the mood for hunting obscure Jam bugs, > > > as > > > long as we can work around so easily. :-) > > > > Removing binaries isn't exactly a nice solution, but as it seems to > > work... :-) > > Since jam is ignorant about targets removed from the build system > (including the objects in a static library), fully building the library > every time it is updated, is the only way to at least not carry the removed > objects about forever. If that also solves your problem, good, but that's > not the reason for the change in the first place. Ah, you managed to remove enough of the original conversion and answer late enough that I mixed up what this thread was about. :-) By work-around I was not referring to removing targets from the image, but to increasing the maximal line length some more. If that stops to work, looking into the actual problem will become inevitable, though. CU, Ingo From darkwyrm at mail.berlios.de Thu Apr 12 17:57:46 2007 From: darkwyrm at mail.berlios.de (darkwyrm at BerliOS) Date: Thu, 12 Apr 2007 17:57:46 +0200 Subject: [Haiku-commits] r20665 - haiku/trunk/src/add-ons/kernel/drivers/midi/usb_midi Message-ID: <200704121557.l3CFvksQ029611@sheep.berlios.de> Author: darkwyrm Date: 2007-04-12 17:57:46 +0200 (Thu, 12 Apr 2007) New Revision: 20665 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20665&view=rev Modified: haiku/trunk/src/add-ons/kernel/drivers/midi/usb_midi/Jamfile Log: Enable build of usb_midi on R5 using same Jamfile techniques as usb_hid Modified: haiku/trunk/src/add-ons/kernel/drivers/midi/usb_midi/Jamfile =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/midi/usb_midi/Jamfile 2007-04-12 13:20:33 UTC (rev 20664) +++ haiku/trunk/src/add-ons/kernel/drivers/midi/usb_midi/Jamfile 2007-04-12 15:57:46 UTC (rev 20665) @@ -2,17 +2,22 @@ SetSubDirSupportedPlatformsBeOSCompatible ; +local buffer_impl = ; if $(TARGET_PLATFORM) != haiku { UseHeaders [ FDirName $(HAIKU_TOP) headers os drivers ] : true ; # We need the public usb headers also when not compiling for Haiku. + buffer_impl = ring_buffer.cpp ; } UsePrivateHeaders [ FDirName kernel util ] ; KernelAddon usb_midi : usb_midi.c devlist.c + $(buffer_impl) ; +SEARCH on [ FGristFiles ring_buffer.cpp ] = [ FDirName $(HAIKU_TOP) src system kernel util ] ; + ObjectHdrs [ FGristFiles usb_midi$(SUFOBJ) ] : [ FDirName $(TARGET_COMMON_DEBUG_OBJECT_DIR) preferences devices ] ; From axeld at mail.berlios.de Thu Apr 12 18:23:34 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Thu, 12 Apr 2007 18:23:34 +0200 Subject: [Haiku-commits] r20666 - haiku/trunk/src/apps/networkstatus Message-ID: <200704121623.l3CGNYe9031009@sheep.berlios.de> Author: axeld Date: 2007-04-12 18:23:34 +0200 (Thu, 12 Apr 2007) New Revision: 20666 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20666&view=rev Modified: haiku/trunk/src/apps/networkstatus/NetworkStatusView.cpp Log: Fixed two bugs: * FrameReceived() updated the bitmaps, but did not invalidate the view, causing B_FULL_UPDATE_ON_RESIZE to show an outdated icon. * fInDeskbar was not initialized in case the archive constructor was used. Modified: haiku/trunk/src/apps/networkstatus/NetworkStatusView.cpp =================================================================== --- haiku/trunk/src/apps/networkstatus/NetworkStatusView.cpp 2007-04-12 15:57:46 UTC (rev 20665) +++ haiku/trunk/src/apps/networkstatus/NetworkStatusView.cpp 2007-04-12 16:23:34 UTC (rev 20666) @@ -24,6 +24,7 @@ #include #include #include +#include #include #include @@ -68,7 +69,7 @@ NetworkStatusView::NetworkStatusView(BRect frame, int32 resizingMode, bool inDeskbar) : BView(frame, kDeskbarItemName, resizingMode, - B_WILL_DRAW | B_FRAME_EVENTS | B_FULL_UPDATE_ON_RESIZE), + B_WILL_DRAW | B_FRAME_EVENTS), fInDeskbar(inDeskbar), fStatus(kStatusUnknown) { @@ -88,8 +89,14 @@ NetworkStatusView::NetworkStatusView(BMessage* archive) - : BView(archive) + : BView(archive), + fInDeskbar(false) { + app_info info; + if (be_app->GetAppInfo(&info) == B_OK + && !strcasecmp(info.signature, "application/x-vnd.Be-TSKB")) + fInDeskbar = true; + _Init(); } @@ -243,6 +250,7 @@ NetworkStatusView::FrameResized(float width, float height) { _UpdateBitmaps(); + Invalidate(); } From korli at mail.berlios.de Thu Apr 12 20:11:11 2007 From: korli at mail.berlios.de (korli at BerliOS) Date: Thu, 12 Apr 2007 20:11:11 +0200 Subject: [Haiku-commits] r20667 - haiku/trunk/headers/private/storage Message-ID: <200704121811.l3CIBBEM022260@sheep.berlios.de> Author: korli Date: 2007-04-12 20:11:11 +0200 (Thu, 12 Apr 2007) New Revision: 20667 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20667&view=rev Modified: haiku/trunk/headers/private/storage/DiskDeviceVisitor.h Log: fixed typo Modified: haiku/trunk/headers/private/storage/DiskDeviceVisitor.h =================================================================== --- haiku/trunk/headers/private/storage/DiskDeviceVisitor.h 2007-04-12 16:23:34 UTC (rev 20666) +++ haiku/trunk/headers/private/storage/DiskDeviceVisitor.h 2007-04-12 18:11:11 UTC (rev 20667) @@ -22,4 +22,4 @@ virtual bool Visit(BPartition *partition, int32 level); }; -#endif _DISK_DEVICE_VISITOR_H +#endif // _DISK_DEVICE_VISITOR_H From korli at mail.berlios.de Thu Apr 12 20:17:32 2007 From: korli at mail.berlios.de (korli at BerliOS) Date: Thu, 12 Apr 2007 20:17:32 +0200 Subject: [Haiku-commits] r20668 - haiku/trunk/headers/private/net Message-ID: <200704121817.l3CIHWeT022744@sheep.berlios.de> Author: korli Date: 2007-04-12 20:17:31 +0200 (Thu, 12 Apr 2007) New Revision: 20668 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20668&view=rev Modified: haiku/trunk/headers/private/net/NetBufferUtilities.h Log: gcc4 is picky with in-template symbols, they must be qualified Modified: haiku/trunk/headers/private/net/NetBufferUtilities.h =================================================================== --- haiku/trunk/headers/private/net/NetBufferUtilities.h 2007-04-12 18:11:11 UTC (rev 20667) +++ haiku/trunk/headers/private/net/NetBufferUtilities.h 2007-04-12 18:17:31 UTC (rev 20668) @@ -87,7 +87,7 @@ ~NetBufferField() { - Sync(); + this->Sync(); } }; @@ -101,15 +101,15 @@ void Remove() { - Remove(sizeof(Type)); + this->Remove(sizeof(Type)); } void Remove(size_t bytes) { - if (fBuffer != NULL) { - Module::Get()->remove_header(fBuffer, bytes); - fBuffer = NULL; + if (this->fBuffer != NULL) { + Module::Get()->remove_header(this->fBuffer, bytes); + this->fBuffer = NULL; } } }; @@ -123,7 +123,7 @@ ~NetBufferHeaderRemover() { - Remove(); + this->Remove(); } }; @@ -133,17 +133,17 @@ public: NetBufferPrepend(net_buffer *buffer, size_t size = sizeof(Type)) { - fBuffer = buffer; + this->fBuffer = buffer; - fStatus = Module::Get()->prepend_size(buffer, size, - (void **)&fData); - if (fStatus == B_OK && fData == NULL) - fData = &fDataBuffer; + this->fStatus = Module::Get()->prepend_size(buffer, size, + (void **)&(this->fData)); + if (this->fStatus == B_OK && this->fData == NULL) + this->fData = &this->fDataBuffer; } ~NetBufferPrepend() { - Sync(); + this->Sync(); } }; From korli at mail.berlios.de Thu Apr 12 20:36:37 2007 From: korli at mail.berlios.de (korli at BerliOS) Date: Thu, 12 Apr 2007 20:36:37 +0200 Subject: [Haiku-commits] r20669 - haiku/trunk/headers/posix Message-ID: <200704121836.l3CIabLA023741@sheep.berlios.de> Author: korli Date: 2007-04-12 20:36:37 +0200 (Thu, 12 Apr 2007) New Revision: 20669 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20669&view=rev Modified: haiku/trunk/headers/posix/stddef.h Log: use __builtin_offsetof for gcc4 and superior, it avoids a gcc4 broken build with template use of offsetof() Modified: haiku/trunk/headers/posix/stddef.h =================================================================== --- haiku/trunk/headers/posix/stddef.h 2007-04-12 18:17:31 UTC (rev 20668) +++ haiku/trunk/headers/posix/stddef.h 2007-04-12 18:36:37 UTC (rev 20669) @@ -5,7 +5,11 @@ */ #include +#if defined(__GNUC__) && __GNUC__ > 3 +#define offsetof(type,member) __builtin_offsetof(type, member) +#else #define offsetof(type,member) ((size_t)&((type*)0)->member) +#endif typedef long ptrdiff_t; From korli at mail.berlios.de Thu Apr 12 21:20:45 2007 From: korli at mail.berlios.de (korli at BerliOS) Date: Thu, 12 Apr 2007 21:20:45 +0200 Subject: [Haiku-commits] r20670 - haiku/trunk/src/kits/game Message-ID: <200704121920.l3CJKjq0026636@sheep.berlios.de> Author: korli Date: 2007-04-12 21:20:45 +0200 (Thu, 12 Apr 2007) New Revision: 20670 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20670&view=rev Modified: haiku/trunk/src/kits/game/PushGameSound.cpp haiku/trunk/src/kits/game/SimpleGameSound.cpp Log: improve codestyle fix bad init in BPushGameSound Modified: haiku/trunk/src/kits/game/PushGameSound.cpp =================================================================== --- haiku/trunk/src/kits/game/PushGameSound.cpp 2007-04-12 18:36:37 UTC (rev 20669) +++ haiku/trunk/src/kits/game/PushGameSound.cpp 2007-04-12 19:20:45 UTC (rev 20670) @@ -32,20 +32,18 @@ #include "GSUtility.h" -BPushGameSound::BPushGameSound(size_t inBufferFrameCount, - const gs_audio_format *format, - size_t inBufferCount, - BGameSoundDevice *device) +BPushGameSound::BPushGameSound(size_t inBufferFrameCount, const gs_audio_format *format, + size_t inBufferCount, BGameSoundDevice *device) : BStreamingGameSound(inBufferFrameCount, format, inBufferCount, device) { - if (InitCheck() == B_OK) - { - status_t error = SetParameters(inBufferFrameCount, format, inBufferCount); - if (error != B_OK) - fPageLocked = new BList; - else - SetInitError(error); - } + if (InitCheck() != B_OK) + return; + + status_t error = SetParameters(inBufferFrameCount, format, inBufferCount); + if (error != B_OK) + fPageLocked = new BList; + else + SetInitError(error); } @@ -69,14 +67,16 @@ BPushGameSound::lock_status -BPushGameSound::LockNextPage(void **out_pagePtr, - size_t *out_pageSize) +BPushGameSound::LockNextPage(void **out_pagePtr, size_t *out_pageSize) { // the user can not lock every page - if (fPageLocked->CountItems() > fPageCount - 3) return lock_failed; + if (fPageLocked->CountItems() > fPageCount - 3) + return lock_failed; // the user cann't lock a page being played - if (fLockPos < fPlayPos && fLockPos + fPageSize > fPlayPos) return lock_failed; + if (fLockPos < fPlayPos + && fLockPos + fPageSize > fPlayPos) + return lock_failed; // lock the page char * lockPage = &fBuffer[fLockPos]; @@ -84,7 +84,8 @@ // move the locker to the next page fLockPos += fPageSize; - if (fLockPos > fBufferSize) fLockPos = 0; + if (fLockPos > fBufferSize) + fLockPos = 0; *out_pagePtr = lockPage; *out_pageSize = fPageSize; @@ -101,8 +102,7 @@ BPushGameSound::lock_status -BPushGameSound::LockForCyclic(void **out_basePtr, - size_t *out_size) +BPushGameSound::LockForCyclic(void **out_basePtr, size_t *out_size) { *out_basePtr = fBuffer; *out_size = fBufferSize; @@ -136,8 +136,7 @@ status_t -BPushGameSound::Perform(int32 selector, - void *data) +BPushGameSound::Perform(int32 selector, void *data) { return B_ERROR; } @@ -149,7 +148,8 @@ size_t inBufferCount) { status_t error = BStreamingGameSound::SetParameters(inBufferFrameCount, format, inBufferCount); - if (error != B_OK) return error; + if (error != B_OK) + return error; size_t frameSize = get_sample_size(format->format) * format->channel_count; @@ -172,67 +172,61 @@ void -BPushGameSound::FillBuffer(void *inBuffer, - size_t inByteCount) +BPushGameSound::FillBuffer(void *inBuffer, size_t inByteCount) { size_t bytes = inByteCount; - if (BytesReady(&bytes)) - { - if (fPlayPos + bytes > fBufferSize) - { - size_t remainder = fPlayPos + bytes - fBufferSize; - char * buffer = (char*)inBuffer; - - // fill the buffer with the samples left at the end of our buffer - memcpy(buffer, &fBuffer[fPlayPos], remainder); - fPlayPos = 0; - - // fill the remainder of the buffer by looping to the start - // of the buffer if it isn't locked - bytes -= remainder; - if (BytesReady(&bytes)) - { - memcpy(&buffer[remainder], fBuffer, bytes); - fPlayPos += bytes; - } - } - else - { - memcpy(inBuffer, &fBuffer[fPlayPos], bytes); - fPlayPos += bytes; - } + if (!BytesReady(&bytes)) + return; + + if (fPlayPos + bytes > fBufferSize) { + size_t remainder = fPlayPos + bytes - fBufferSize; + char * buffer = (char*)inBuffer; - BStreamingGameSound::FillBuffer(inBuffer, inByteCount); - } + // fill the buffer with the samples left at the end of our buffer + memcpy(buffer, &fBuffer[fPlayPos], remainder); + fPlayPos = 0; + + // fill the remainder of the buffer by looping to the start + // of the buffer if it isn't locked + bytes -= remainder; + if (BytesReady(&bytes)) { + memcpy(&buffer[remainder], fBuffer, bytes); + fPlayPos += bytes; + } + } else { + memcpy(inBuffer, &fBuffer[fPlayPos], bytes); + fPlayPos += bytes; + } + + BStreamingGameSound::FillBuffer(inBuffer, inByteCount); } bool BPushGameSound::BytesReady(size_t * bytes) { - if (fPageLocked->CountItems() > 0) - { - size_t start = fPlayPos; - size_t ready = fPlayPos; - int32 page = int32(start / fPageSize); + if (fPageLocked->CountItems() <= 0) + return true; - // return if there is nothing to do - if (fPageLocked->HasItem(&fBuffer[page * fPageSize])) return false; + size_t start = fPlayPos; + size_t ready = fPlayPos; + int32 page = int32(start / fPageSize); - while (ready < *bytes) - { - ready += fPageSize; - page = int32(ready / fPageSize); + // return if there is nothing to do + if (fPageLocked->HasItem(&fBuffer[page * fPageSize])) + return false; + + while (ready < *bytes) { + ready += fPageSize; + page = int32(ready / fPageSize); - if (fPageLocked->HasItem(&fBuffer[page * fPageSize])) - { - // we have found a locked page - *bytes = ready - start - (ready - page * fPageSize); - return true; - } - } - } + if (fPageLocked->HasItem(&fBuffer[page * fPageSize])) { + // we have found a locked page + *bytes = ready - start - (ready - page * fPageSize); + return true; + } + } // all of the bytes are ready return true; Modified: haiku/trunk/src/kits/game/SimpleGameSound.cpp =================================================================== --- haiku/trunk/src/kits/game/SimpleGameSound.cpp 2007-04-12 18:36:37 UTC (rev 20669) +++ haiku/trunk/src/kits/game/SimpleGameSound.cpp 2007-04-12 19:20:45 UTC (rev 20670) @@ -39,8 +39,7 @@ #include -BSimpleGameSound::BSimpleGameSound(const entry_ref *inFile, - BGameSoundDevice *device) +BSimpleGameSound::BSimpleGameSound(const entry_ref *inFile, BGameSoundDevice *device) : BGameSound(device) { if (InitCheck() == B_OK) @@ -48,8 +47,7 @@ } -BSimpleGameSound::BSimpleGameSound(const char *inFile, - BGameSoundDevice *device) +BSimpleGameSound::BSimpleGameSound(const char *inFile, BGameSoundDevice *device) : BGameSound(device) { if (InitCheck() == B_OK) @@ -71,7 +69,7 @@ : BGameSound(device) { if (InitCheck() == B_OK) - SetInitError(Init(inData, inFrameCount, format)); + SetInitError(Init(inData, inFrameCount, format)); } @@ -155,11 +153,13 @@ media_format mformat; int64 framesRead, framesTotal = 0; - if (file.InitCheck() != B_OK) return file.InitCheck(); + if (file.InitCheck() != B_OK) + return file.InitCheck(); BMediaTrack* audioStream = file.TrackAt(0); audioStream->EncodedFormat(&mformat); - if (!mformat.IsAudio()) return B_ERROR; + if (!mformat.IsAudio()) + return B_ERROR; int64 frames = audioStream->CountFrames(); @@ -172,15 +172,13 @@ memset(&gsformat, 0, sizeof(gs_audio_format)); media_to_gs_format(&gsformat, &mformat.u.raw_audio); - if (mformat.u.raw_audio.format == media_raw_audio_format::B_AUDIO_CHAR) - { + if (mformat.u.raw_audio.format == media_raw_audio_format::B_AUDIO_CHAR) { // The GameKit doesnt support this format so we will have to reformat // the data into something the GameKit does support. char * buffer = new char[gsformat.buffer_size]; uchar * data = new uchar[frames * gsformat.channel_count]; - while (framesTotal < frames) - { + while (framesTotal < frames) { // read the next chunck from the stream memset(buffer, 0, gsformat.buffer_size); audioStream->ReadFrames(buffer, &framesRead); @@ -200,17 +198,14 @@ // free the buffers we no longer need delete [] buffer; delete [] data; - } - else - { + } else { // We need to detriman the size, in bytes, of a single sample. // At the same time, we will store the format of the audio buffer size_t frameSize = get_sample_size(gsformat.format) * gsformat.channel_count; char * data = new char[frames * frameSize]; gsformat.buffer_size = frames * frameSize; - while(framesTotal < frames) - { + while(framesTotal < frames) { char * position = &data[framesTotal * frameSize]; audioStream->ReadFrames(position, &framesRead); @@ -228,14 +223,14 @@ status_t -BSimpleGameSound::Init(const void* inData, - int64 inFrameCount, +BSimpleGameSound::Init(const void* inData, int64 inFrameCount, const gs_audio_format* format) { gs_id sound; status_t error = Device()->CreateBuffer(&sound, format, inData, inFrameCount); - if (error != B_OK) return error; + if (error != B_OK) + return error; BGameSound::Init(sound); From korli at mail.berlios.de Thu Apr 12 22:32:20 2007 From: korli at mail.berlios.de (korli at BerliOS) Date: Thu, 12 Apr 2007 22:32:20 +0200 Subject: [Haiku-commits] r20671 - haiku/trunk/src/kits/game Message-ID: <200704122032.l3CKWK9t000521@sheep.berlios.de> Author: korli Date: 2007-04-12 22:32:19 +0200 (Thu, 12 Apr 2007) New Revision: 20671 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20671&view=rev Modified: haiku/trunk/src/kits/game/PushGameSound.cpp Log: fixed the wrong test for real Modified: haiku/trunk/src/kits/game/PushGameSound.cpp =================================================================== --- haiku/trunk/src/kits/game/PushGameSound.cpp 2007-04-12 19:20:45 UTC (rev 20670) +++ haiku/trunk/src/kits/game/PushGameSound.cpp 2007-04-12 20:32:19 UTC (rev 20671) @@ -40,7 +40,7 @@ return; status_t error = SetParameters(inBufferFrameCount, format, inBufferCount); - if (error != B_OK) + if (error == B_OK) fPageLocked = new BList; else SetInitError(error); From hugosantos at mail.berlios.de Fri Apr 13 02:55:54 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Fri, 13 Apr 2007 02:55:54 +0200 Subject: [Haiku-commits] r20672 - in haiku/trunk: headers/private/net src/add-ons/kernel/network/protocols/ipv4 src/add-ons/kernel/network/protocols/udp src/add-ons/kernel/network/stack Message-ID: <200704130055.l3D0tsUO001010@sheep.berlios.de> Author: hugosantos Date: 2007-04-13 02:55:32 +0200 (Fri, 13 Apr 2007) New Revision: 20672 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20672&view=rev Added: haiku/trunk/headers/private/net/ProtocolUtilities.h Modified: haiku/trunk/headers/private/net/NetBufferUtilities.h haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp haiku/trunk/src/add-ons/kernel/network/stack/link.cpp haiku/trunk/src/add-ons/kernel/network/stack/stack.cpp haiku/trunk/src/add-ons/kernel/network/stack/stack_private.h Log: introduced a new helper class DatagramSocket which provides a consistent base interface and functionality for the implementation of datagram-based sockets. - made the ipv4 raw, udp and link protocols use DatagramSocket. Modified: haiku/trunk/headers/private/net/NetBufferUtilities.h =================================================================== --- haiku/trunk/headers/private/net/NetBufferUtilities.h 2007-04-12 20:32:19 UTC (rev 20671) +++ haiku/trunk/headers/private/net/NetBufferUtilities.h 2007-04-13 00:55:32 UTC (rev 20672) @@ -1,5 +1,5 @@ /* - * Copyright 2006, Haiku, Inc. All Rights Reserved. + * Copyright 2006-2007, Haiku, Inc. All Rights Reserved. * Distributed under the terms of the MIT License. */ #ifndef NET_BUFFER_UTILITIES_H Added: haiku/trunk/headers/private/net/ProtocolUtilities.h =================================================================== --- haiku/trunk/headers/private/net/ProtocolUtilities.h 2007-04-12 20:32:19 UTC (rev 20671) +++ haiku/trunk/headers/private/net/ProtocolUtilities.h 2007-04-13 00:55:32 UTC (rev 20672) @@ -0,0 +1,288 @@ +/* + * Copyright 2007, Haiku, Inc. All Rights Reserved. + * Distributed under the terms of the MIT License. + * + * Authors: + * Hugo Santos, hugosantos at gmail.com + */ + +#ifndef PROTOCOL_UTILITIES_H +#define PROTOCOL_UTILITIES_H + +#include +#include +#include + +#include +#include +#include + +class BenaphoreLocking { +public: + typedef benaphore Type; + typedef BenaphoreLocker AutoLocker; + + static status_t Init(benaphore *lock, const char *name) + { return benaphore_init(lock, name); } + static void Destroy(benaphore *lock) { benaphore_destroy(lock); } + static status_t Lock(benaphore *lock) { return benaphore_lock(lock); } + static status_t Unlock(benaphore *lock) { return benaphore_unlock(lock); } +}; + + +extern net_stack_module_info *gStackModule; +extern net_buffer_module_info *gBufferModule; + +class NetModuleBundle { +public: + static net_stack_module_info *Stack() { return gStackModule; } + static net_buffer_module_info *Buffer() { return gBufferModule; } +}; + + +template +class DatagramSocket { +public: + DatagramSocket(const char *name, net_socket *socket); + ~DatagramSocket(); + + status_t InitCheck() const; + + status_t Enqueue(net_buffer *buffer); + status_t EnqueueClone(net_buffer *buffer); + net_buffer *Dequeue(bool clone); + status_t BlockingDequeue(bool clone, bigtime_t timeout, + net_buffer **_buffer); + status_t SocketDequeue(uint32 flags, net_buffer **_buffer); + void Clear(); + + size_t AvailableData() const; + + void WakeAll(); + +protected: + status_t _Enqueue(net_buffer *buffer); + status_t _EnqueueClone(net_buffer *buffer); + net_buffer *_Dequeue(bool clone); + void _Clear(); + + status_t _Wait(bigtime_t timeout); + void _NotifyOneReader(bool notifySocket); + + bool _IsEmpty() const { return fBuffers.IsEmpty(); } + bigtime_t _SocketTimeout(uint32 flags) const; + + typedef typename LockingBase::Type LockType; + typedef typename LockingBase::AutoLocker AutoLocker; + typedef DoublyLinkedListCLink NetBufferLink; + typedef DoublyLinkedList BufferList; + + status_t fStatus; + net_socket *fSocket; + sem_id fNotify; + BufferList fBuffers; + size_t fCurrentBytes; + mutable LockType fLock; +}; + + +#define DECL_DATAGRAM_SOCKET(args) \ + template args \ + DatagramSocket + + +DECL_DATAGRAM_SOCKET(inline)::DatagramSocket(const char *name, + net_socket *socket) + : fSocket(socket), fCurrentBytes(0) +{ + fStatus = LockingBase::Init(&fLock, name); + if (fStatus >= B_OK) + fNotify = create_sem(0, name); +} + + +DECL_DATAGRAM_SOCKET(inline)::~DatagramSocket() +{ + _Clear(); + + if (fStatus >= B_OK) { + delete_sem(fNotify); + LockingBase::Destroy(&fLock); + } +} + + +DECL_DATAGRAM_SOCKET(inline status_t)::InitCheck() const +{ + if (fStatus < 0) + return fStatus; + return fNotify; +} + + +DECL_DATAGRAM_SOCKET(inline status_t)::Enqueue(net_buffer *buffer) +{ + AutoLocker _(fLock); + return _Enqueue(buffer); +} + + +DECL_DATAGRAM_SOCKET(inline status_t)::_Enqueue(net_buffer *buffer) +{ + if (fSocket->receive.buffer_size > 0 + && (fCurrentBytes + buffer->size) > fSocket->receive.buffer_size) + return ENOBUFS; + + fBuffers.Add(buffer); + fCurrentBytes += buffer->size; + + _NotifyOneReader(true); + + return B_OK; +} + + +DECL_DATAGRAM_SOCKET(inline status_t)::EnqueueClone(net_buffer *_buffer) +{ + AutoLocker _(fLock); + return _EnqueueClone(_buffer); +} + + +DECL_DATAGRAM_SOCKET(inline status_t)::_EnqueueClone(net_buffer *_buffer) +{ + net_buffer *buffer = ModuleBundle::Buffer()->clone(_buffer, false); + if (buffer == NULL) + return B_NO_MEMORY; + + status_t status = _Enqueue(buffer); + if (status < B_OK) + ModuleBundle::Buffer()->free(buffer); + + return status; +} + + +DECL_DATAGRAM_SOCKET(inline net_buffer *)::Dequeue(bool clone) +{ + AutoLocker _(fLock); + return _Dequeue(clone); +} + + +DECL_DATAGRAM_SOCKET(inline net_buffer *)::_Dequeue(bool clone) +{ + if (fBuffers.IsEmpty()) + return NULL; + + if (clone) + return ModuleBundle::Buffer()->clone(fBuffers.Head(), false); + + net_buffer *buffer = fBuffers.RemoveHead(); + fCurrentBytes -= buffer->size; + + return buffer; +} + + +DECL_DATAGRAM_SOCKET(inline status_t)::BlockingDequeue(bool clone, + bigtime_t timeout, net_buffer **_buffer) +{ + AutoLocker _(fLock); + + bool waited = false; + + while (fBuffers.IsEmpty()) { + status_t status = _Wait(timeout); + if (status < B_OK) + return status; + waited = true; + } + + *_buffer = _Dequeue(clone); + if (clone && waited) { + // we were signalled there was a new buffer in the + // list; but since we are cloning, notify the next + // waiting reader. + _NotifyOneReader(false); + } + + if (*_buffer == NULL) + return B_NO_MEMORY; + + return B_OK; +} + + +DECL_DATAGRAM_SOCKET(inline status_t)::SocketDequeue(uint32 flags, + net_buffer **_buffer) +{ + return BlockingDequeue(flags & MSG_PEEK, _SocketTimeout(flags), _buffer); +} + + +DECL_DATAGRAM_SOCKET(inline void)::Clear() +{ + AutoLocker _(fLock); + _Clear(); +} + + +DECL_DATAGRAM_SOCKET(inline void)::_Clear() +{ + BufferList::Iterator it = fBuffers.GetIterator(); + while (it.HasNext()) + ModuleBundle::Buffer()->free(it.Next()); + fCurrentBytes = 0; +} + + +DECL_DATAGRAM_SOCKET(inline size_t)::AvailableData() const +{ + AutoLocker _(fLock); + return fCurrentBytes; +} + + +DECL_DATAGRAM_SOCKET(inline status_t)::_Wait(bigtime_t timeout) +{ + LockingBase::Unlock(&fLock); + status_t status = acquire_sem_etc(fNotify, 1, B_CAN_INTERRUPT + | B_ABSOLUTE_TIMEOUT, timeout); + LockingBase::Lock(&fLock); + + return status; +} + + +DECL_DATAGRAM_SOCKET(inline void)::WakeAll() +{ + release_sem_etc(fNotify, 0, B_RELEASE_ALL); +} + + +DECL_DATAGRAM_SOCKET(inline void)::_NotifyOneReader(bool notifySocket) +{ + release_sem_etc(fNotify, 1, B_RELEASE_IF_WAITING_ONLY + | B_DO_NOT_RESCHEDULE); + + if (notifySocket) + ModuleBundle::Stack()->notify_socket(fSocket, B_SELECT_READ, + fCurrentBytes); +} + + +DECL_DATAGRAM_SOCKET(inline bigtime_t)::_SocketTimeout(uint32 flags) const +{ + bigtime_t timeout = fSocket->receive.timeout; + + if (flags & MSG_DONTWAIT) + timeout = 0; + else if (timeout != 0 && timeout != B_INFINITE_TIMEOUT) + timeout += system_time(); + + return timeout; +} + +#endif Modified: haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp 2007-04-12 20:32:19 UTC (rev 20671) +++ haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp 2007-04-13 00:55:32 UTC (rev 20672) @@ -13,6 +13,7 @@ #include #include #include +#include #include #include @@ -110,22 +111,9 @@ typedef DoublyLinkedList RawSocketList; -class RawSocket : public DoublyLinkedListLinkImpl { +class RawSocket : public DoublyLinkedListLinkImpl, public DatagramSocket<> { public: RawSocket(net_socket *socket); - ~RawSocket(); - - status_t InitCheck(); - - status_t Read(size_t numBytes, uint32 flags, bigtime_t timeout, - net_buffer **_buffer); - ssize_t BytesAvailable(); - - status_t Write(net_buffer *buffer); - - private: - net_socket *fSocket; - net_fifo fFifo; }; struct ipv4_protocol : net_protocol { @@ -142,10 +130,11 @@ extern net_protocol_module_info gIPv4Module; // we need this in ipv4_std_ops() for registering the AF_INET domain +net_stack_module_info *gStackModule; +net_buffer_module_info *gBufferModule; + static struct net_domain *sDomain; static net_datalink_module_info *sDatalinkModule; -static net_stack_module_info *sStackModule; -struct net_buffer_module_info *gBufferModule; static int32 sPacketID; static RawSocketList sRawSockets; static benaphore sRawSocketsLock; @@ -156,59 +145,11 @@ RawSocket::RawSocket(net_socket *socket) - : - fSocket(socket) + : DatagramSocket<>("ipv4 raw socket", socket) { - status_t status = sStackModule->init_fifo(&fFifo, "ipv4 raw socket", 65536); - if (status < B_OK) - fFifo.notify = status; } -RawSocket::~RawSocket() -{ - if (fFifo.notify >= B_OK) - sStackModule->uninit_fifo(&fFifo); -} - - -status_t -RawSocket::InitCheck() -{ - return fFifo.notify >= B_OK ? B_OK : fFifo.notify; -} - - -status_t -RawSocket::Read(size_t numBytes, uint32 flags, bigtime_t timeout, - net_buffer **_buffer) -{ - net_buffer *buffer; - status_t status = sStackModule->fifo_dequeue_buffer(&fFifo, - flags, timeout, &buffer); - if (status < B_OK) - return status; - - *_buffer = buffer; - return B_OK; -} - - -ssize_t -RawSocket::BytesAvailable() -{ - return fFifo.current_bytes; -} - - -status_t -RawSocket::Write(net_buffer *source) -{ - return sStackModule->fifo_socket_enqueue_buffer(&fFifo, fSocket, - B_SELECT_READ, source); -} - - // #pragma mark - @@ -218,14 +159,14 @@ fReceivedLastFragment(false), fBytesLeft(IP_MAXPACKET) { - sStackModule->init_timer(&fTimer, StaleTimer, this); + gStackModule->init_timer(&fTimer, StaleTimer, this); } FragmentPacket::~FragmentPacket() { // cancel the kill timer - sStackModule->set_timer(&fTimer, -1); + gStackModule->set_timer(&fTimer, -1); // delete all fragments net_buffer *buffer; @@ -240,7 +181,7 @@ bool lastFragment) { // restart the timer - sStackModule->set_timer(&fTimer, FRAGMENT_TIMEOUT); + gStackModule->set_timer(&fTimer, FRAGMENT_TIMEOUT); if (start >= end) { // invalid fragment @@ -595,7 +536,7 @@ header->fragment_offset = htons((lastFragment ? 0 : IP_MORE_FRAGMENTS) | (fragmentOffset >> 3)); header->checksum = 0; - header->checksum = sStackModule->checksum((uint8 *)header, headerLength); + header->checksum = gStackModule->checksum((uint8 *)header, headerLength); // TODO: compute the checksum only for those parts that changed? dprintf(" send fragment of %ld bytes (%ld bytes left)\n", fragmentLength, bytesLeft); @@ -644,10 +585,8 @@ RawSocketList::Iterator iterator = sRawSockets.GetIterator(); - while (iterator.HasNext()) { - RawSocket *raw = iterator.Next(); - raw->Write(buffer); - } + while (iterator.HasNext()) + iterator.Next()->EnqueueClone(buffer); } @@ -664,7 +603,7 @@ if (module != NULL) return module; - if (sStackModule->get_domain_receiving_protocol(sDomain, protocol, &module) == B_OK) + if (gStackModule->get_domain_receiving_protocol(sDomain, protocol, &module) == B_OK) sReceivingProtocol[protocol] = module; return module; @@ -1016,7 +955,7 @@ return B_ERROR; TRACE(("read is waiting for data...\n")); - return raw->Read(numBytes, flags, protocol->socket->receive.timeout, _buffer); + return raw->SocketDequeue(flags, _buffer); } @@ -1028,7 +967,7 @@ if (raw == NULL) return B_ERROR; - return raw->BytesAvailable(); + return raw->AvailableData(); } @@ -1175,7 +1114,7 @@ status_t init_ipv4() { - status_t status = get_module(NET_STACK_MODULE_NAME, (module_info **)&sStackModule); + status_t status = get_module(NET_STACK_MODULE_NAME, (module_info **)&gStackModule); if (status < B_OK) return status; status = get_module(NET_BUFFER_MODULE_NAME, (module_info **)&gBufferModule); @@ -1209,12 +1148,12 @@ // so we have to do it here, manually // TODO: for modules, this shouldn't be required - status = sStackModule->register_domain_protocols(AF_INET, SOCK_RAW, 0, + status = gStackModule->register_domain_protocols(AF_INET, SOCK_RAW, 0, "network/protocols/ipv4/v1", NULL); if (status < B_OK) goto err7; - status = sStackModule->register_domain(AF_INET, "internet", &gIPv4Module, + status = gStackModule->register_domain(AF_INET, "internet", &gIPv4Module, &gIPv4AddressModule, &sDomain); if (status < B_OK) goto err7; @@ -1247,10 +1186,10 @@ // put all the domain receiving protocols we gathered so far for (uint32 i = 0; i < 256; i++) { if (sReceivingProtocol[i] != NULL) - sStackModule->put_domain_receiving_protocol(sDomain, i); + gStackModule->put_domain_receiving_protocol(sDomain, i); } - sStackModule->unregister_domain(sDomain); + gStackModule->unregister_domain(sDomain); benaphore_unlock(&sReceivingProtocolLock); hash_uninit(sFragmentHash); Modified: haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp 2007-04-12 20:32:19 UTC (rev 20671) +++ haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp 2007-04-13 00:55:32 UTC (rev 20672) @@ -22,6 +22,7 @@ #include #include +#include #include #include @@ -29,9 +30,6 @@ #include #include -// TODO move the locking from the FIFO to the whole Endpoint -// much like we did with the LinkProtocol. - //#define TRACE_UDP #ifdef TRACE_UDP # define TRACE_BLOCK(x) dump_block x @@ -64,13 +62,10 @@ class UdpDomainSupport; -class UdpEndpoint : public net_protocol { +class UdpEndpoint : public net_protocol, public DatagramSocket<> { public: UdpEndpoint(net_socket *socket); - ~UdpEndpoint(); - status_t InitCheck() const; - status_t Bind(sockaddr *newAddr); status_t Unbind(sockaddr *newAddr); status_t Connect(const sockaddr *newAddr); @@ -110,8 +105,6 @@ bool fActive; // an active UdpEndpoint is part of the endpoint // hash (and it is bound and optionally connected) - net_fifo fFifo; - // storage space for incoming data }; @@ -208,9 +201,9 @@ static UdpEndpointManager *sUdpEndpointManager; +net_stack_module_info *gStackModule; net_buffer_module_info *gBufferModule; static net_datalink_module_info *sDatalinkModule; -static net_stack_module_info *sStackModule; // #pragma mark - @@ -707,30 +700,13 @@ UdpEndpoint::UdpEndpoint(net_socket *socket) : + DatagramSocket<>("udp endpoint", socket), fDomain(NULL), fActive(false) { - status_t status = sStackModule->init_fifo(&fFifo, "UDP endpoint fifo", - socket->receive.buffer_size); - if (status < B_OK) - fFifo.notify = status; } -UdpEndpoint::~UdpEndpoint() -{ - if (fFifo.notify >= B_OK) - sStackModule->uninit_fifo(&fFifo); -} - - -status_t -UdpEndpoint::InitCheck() const -{ - return fFifo.notify; -} - - // #pragma mark - activation @@ -945,9 +921,9 @@ ssize_t UdpEndpoint::BytesAvailable() { - // TODO protect this call - TRACE_EP("BytesAvailable(): %lu", fFifo.current_bytes); - return fFifo.current_bytes; + size_t bytes = AvailableData(); + TRACE_EP("BytesAvailable(): %lu", bytes); + return bytes; } @@ -956,16 +932,12 @@ { TRACE_EP("FetchData(%ld, 0x%lx)", numBytes, flags); - net_buffer *buffer; - - status_t status = sStackModule->fifo_dequeue_buffer(&fFifo, flags, - socket->receive.timeout, &buffer); + status_t status = SocketDequeue(flags, _buffer); TRACE_EP(" FetchData(): returned from fifo status=0x%lx", status); if (status < B_OK) return status; - TRACE_EP(" FetchData(): returns buffer with %ld bytes", buffer->size); - *_buffer = buffer; + TRACE_EP(" FetchData(): returns buffer with %ld bytes", (*_buffer)->size); return B_OK; } @@ -975,8 +947,7 @@ { TRACE_EP("StoreData(%p [%ld bytes])", buffer, buffer->size); - return sStackModule->fifo_socket_enqueue_buffer(&fFifo, socket, - B_SELECT_READ, buffer); + return EnqueueClone(buffer); } @@ -1160,7 +1131,7 @@ status_t status; TRACE_EPM("init_udp()"); - status = get_module(NET_STACK_MODULE_NAME, (module_info **)&sStackModule); + status = get_module(NET_STACK_MODULE_NAME, (module_info **)&gStackModule); if (status < B_OK) return status; status = get_module(NET_BUFFER_MODULE_NAME, (module_info **)&gBufferModule); @@ -1179,20 +1150,20 @@ if (status != B_OK) goto err3; - status = sStackModule->register_domain_protocols(AF_INET, SOCK_DGRAM, IPPROTO_IP, + status = gStackModule->register_domain_protocols(AF_INET, SOCK_DGRAM, IPPROTO_IP, "network/protocols/udp/v1", "network/protocols/ipv4/v1", NULL); if (status < B_OK) goto err4; - status = sStackModule->register_domain_protocols(AF_INET, SOCK_DGRAM, IPPROTO_UDP, + status = gStackModule->register_domain_protocols(AF_INET, SOCK_DGRAM, IPPROTO_UDP, "network/protocols/udp/v1", "network/protocols/ipv4/v1", NULL); if (status < B_OK) goto err4; - status = sStackModule->register_domain_receiving_protocol(AF_INET, IPPROTO_UDP, + status = gStackModule->register_domain_receiving_protocol(AF_INET, IPPROTO_UDP, "network/protocols/udp/v1"); if (status < B_OK) goto err4; Modified: haiku/trunk/src/add-ons/kernel/network/stack/link.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/link.cpp 2007-04-12 20:32:19 UTC (rev 20671) +++ haiku/trunk/src/add-ons/kernel/network/stack/link.cpp 2007-04-13 00:55:32 UTC (rev 20672) @@ -20,6 +20,7 @@ #include #include +#include #include #include @@ -28,13 +29,19 @@ #include -class LinkProtocol : public net_protocol { +class LocalStackBundle { public: - LinkProtocol(); - ~LinkProtocol(); + static net_stack_module_info *Stack() { return &gNetStackModule; } + static net_buffer_module_info *Buffer() { return &gNetBufferModule; } +}; - status_t InitCheck() const; +typedef DatagramSocket LocalDatagramSocket; +class LinkProtocol : public net_protocol, public LocalDatagramSocket { +public: + LinkProtocol(net_socket *socket); + ~LinkProtocol(); + status_t StartMonitoring(const char *); status_t StopMonitoring(); @@ -42,12 +49,8 @@ ssize_t ReadAvail() const; private: - status_t _Enqueue(net_buffer *buffer); status_t _Unregister(); - mutable benaphore fLock; - Fifo fFifo; - net_device_monitor fMonitor; net_device_interface *fMonitoredDevice; @@ -59,11 +62,9 @@ struct net_domain *sDomain; -LinkProtocol::LinkProtocol() - : fFifo("packet monitor fifo", 65536) +LinkProtocol::LinkProtocol(net_socket *socket) + : LocalDatagramSocket("packet capture", socket) { - benaphore_init(&fLock, "packet monitor lock"); - fMonitor.cookie = this; fMonitor.receive = _MonitorData; fMonitor.event = _MonitorEvent; @@ -77,19 +78,10 @@ unregister_device_monitor(fMonitoredDevice->device, &fMonitor); put_device_interface(fMonitoredDevice); } - - benaphore_destroy(&fLock); } status_t -LinkProtocol::InitCheck() const -{ - return fLock.sem >= 0 && fFifo.InitCheck(); -} - - -status_t LinkProtocol::StartMonitoring(const char *deviceName) { BenaphoreLocker _(fLock); @@ -127,26 +119,24 @@ { BenaphoreLocker _(fLock); - bigtime_t timeout = socket->receive.timeout; + bool clone = flags & MSG_PEEK; + bigtime_t timeout = _SocketTimeout(flags); - if (timeout == 0) - flags |= MSG_DONTWAIT; - else if (timeout != B_INFINITE_TIMEOUT) - timeout += system_time(); - - while (fFifo.IsEmpty()) { + bool waited = false; + while (_IsEmpty()) { if (fMonitoredDevice == NULL) return ENODEV; - status_t status = B_WOULD_BLOCK; - if ((flags & MSG_DONTWAIT) == 0) - status = fFifo.Wait(&fLock, timeout); - + status_t status = _Wait(timeout); if (status < B_OK) return status; + waited = true; } - *_buffer = fFifo.Dequeue(flags & MSG_PEEK); + *_buffer = _Dequeue(clone); + if (clone && waited) + _NotifyOneReader(false); + return *_buffer ? B_OK : B_NO_MEMORY; } @@ -157,7 +147,7 @@ BenaphoreLocker _(fLock); if (fMonitoredDevice == NULL) return ENODEV; - return fFifo.current_bytes; + return fCurrentBytes; } @@ -177,17 +167,9 @@ status_t -LinkProtocol::_Enqueue(net_buffer *buffer) -{ - BenaphoreLocker _(fLock); - return fFifo.EnqueueAndNotify(buffer, socket, B_SELECT_READ); -} - - -status_t LinkProtocol::_MonitorData(net_device_monitor *monitor, net_buffer *packet) { - return ((LinkProtocol *)monitor->cookie)->_Enqueue(packet); + return ((LinkProtocol *)monitor->cookie)->EnqueueClone(packet); } @@ -200,8 +182,8 @@ BenaphoreLocker _(protocol->fLock); protocol->_Unregister(); - if (protocol->fFifo.IsEmpty()) { - protocol->fFifo.WakeAll(); + if (protocol->_IsEmpty()) { + protocol->WakeAll(); notify_socket(protocol->socket, B_SELECT_READ, ENODEV); } } @@ -214,7 +196,7 @@ net_protocol * link_init_protocol(net_socket *socket) { - LinkProtocol *protocol = new (std::nothrow) LinkProtocol(); + LinkProtocol *protocol = new (std::nothrow) LinkProtocol(socket); if (protocol && protocol->InitCheck() < B_OK) { delete protocol; return NULL; Modified: haiku/trunk/src/add-ons/kernel/network/stack/stack.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/stack.cpp 2007-04-12 20:32:19 UTC (rev 20671) +++ haiku/trunk/src/add-ons/kernel/network/stack/stack.cpp 2007-04-13 00:55:32 UTC (rev 20672) @@ -888,7 +888,7 @@ } -static net_stack_module_info sNetStackModule = { +net_stack_module_info gNetStackModule = { { NET_STACK_MODULE_NAME, 0, @@ -939,7 +939,7 @@ }; module_info *modules[] = { - (module_info *)&sNetStackModule, + (module_info *)&gNetStackModule, (module_info *)&sNetStarterModule, (module_info *)&gNetBufferModule, (module_info *)&gNetSocketModule, Modified: haiku/trunk/src/add-ons/kernel/network/stack/stack_private.h =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/stack_private.h 2007-04-12 20:32:19 UTC (rev 20671) +++ haiku/trunk/src/add-ons/kernel/network/stack/stack_private.h 2007-04-13 00:55:32 UTC (rev 20672) @@ -14,10 +14,12 @@ #include #include #include +#include #define NET_STARTER_MODULE_NAME "network/stack/starter/v1" +extern net_stack_module_info gNetStackModule; extern net_buffer_module_info gNetBufferModule; extern net_socket_module_info gNetSocketModule; extern net_datalink_module_info gNetDatalinkModule; From hugosantos at mail.berlios.de Fri Apr 13 05:06:58 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Fri, 13 Apr 2007 05:06:58 +0200 Subject: [Haiku-commits] r20673 - in haiku/trunk: headers/private/net src/add-ons/kernel/network/datalink_protocols/arp src/add-ons/kernel/network/protocols/icmp src/add-ons/kernel/network/protocols/ipv4 src/add-ons/kernel/network/protocols/tcp src/add-ons/kernel/network/protocols/udp src/add-ons/kernel/network/stack Message-ID: <200704130306.l3D36w3V008573@sheep.berlios.de> Author: hugosantos Date: 2007-04-13 05:06:36 +0200 (Fri, 13 Apr 2007) New Revision: 20673 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20673&view=rev Modified: haiku/trunk/headers/private/net/ProtocolUtilities.h haiku/trunk/headers/private/net/net_stack.h haiku/trunk/src/add-ons/kernel/network/datalink_protocols/arp/arp.cpp haiku/trunk/src/add-ons/kernel/network/protocols/icmp/icmp.cpp haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.cpp haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp haiku/trunk/src/add-ons/kernel/network/stack/stack.cpp Log: added buffer, datalink and socket module references to the stack module so we don't have to load them in each other module. Modified: haiku/trunk/headers/private/net/ProtocolUtilities.h =================================================================== --- haiku/trunk/headers/private/net/ProtocolUtilities.h 2007-04-13 00:55:32 UTC (rev 20672) +++ haiku/trunk/headers/private/net/ProtocolUtilities.h 2007-04-13 03:06:36 UTC (rev 20673) @@ -31,17 +31,16 @@ extern net_stack_module_info *gStackModule; -extern net_buffer_module_info *gBufferModule; -class NetModuleBundle { +class NetModuleBundleGetter { public: static net_stack_module_info *Stack() { return gStackModule; } - static net_buffer_module_info *Buffer() { return gBufferModule; } + static net_buffer_module_info *Buffer() { return gStackModule->buffer_module; } }; template + typename ModuleBundle = NetModuleBundleGetter> class DatagramSocket { public: DatagramSocket(const char *name, net_socket *socket); @@ -78,7 +77,6 @@ typedef DoublyLinkedListCLink NetBufferLink; typedef DoublyLinkedList BufferList; - status_t fStatus; net_socket *fSocket; sem_id fNotify; BufferList fBuffers; @@ -96,8 +94,10 @@ net_socket *socket) : fSocket(socket), fCurrentBytes(0) { - fStatus = LockingBase::Init(&fLock, name); - if (fStatus >= B_OK) + status_t status = LockingBase::Init(&fLock, name); + if (status < B_OK) + fNotify = status; + else fNotify = create_sem(0, name); } @@ -105,18 +105,13 @@ DECL_DATAGRAM_SOCKET(inline)::~DatagramSocket() { _Clear(); - - if (fStatus >= B_OK) { - delete_sem(fNotify); - LockingBase::Destroy(&fLock); - } + delete_sem(fNotify); + LockingBase::Destroy(&fLock); } DECL_DATAGRAM_SOCKET(inline status_t)::InitCheck() const { - if (fStatus < 0) - return fStatus; return fNotify; } Modified: haiku/trunk/headers/private/net/net_stack.h =================================================================== --- haiku/trunk/headers/private/net/net_stack.h 2007-04-13 00:55:32 UTC (rev 20672) +++ haiku/trunk/headers/private/net/net_stack.h 2007-04-13 03:06:36 UTC (rev 20673) @@ -55,6 +55,10 @@ struct net_stack_module_info { module_info info; + struct net_buffer_module_info *buffer_module; + struct net_datalink_module_info *datalink_module; + struct net_socket_module_info *socket_module; + status_t (*register_domain)(int family, const char *name, struct net_protocol_module_info *module, struct net_address_module_info *addressModule, Modified: haiku/trunk/src/add-ons/kernel/network/datalink_protocols/arp/arp.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/datalink_protocols/arp/arp.cpp 2007-04-13 00:55:32 UTC (rev 20672) +++ haiku/trunk/src/add-ons/kernel/network/datalink_protocols/arp/arp.cpp 2007-04-13 03:06:36 UTC (rev 20673) @@ -728,28 +728,25 @@ status_t status = get_module(NET_STACK_MODULE_NAME, (module_info **)&sStackModule); if (status < B_OK) return status; - status = get_module(NET_BUFFER_MODULE_NAME, (module_info **)&gBufferModule); - if (status < B_OK) - goto err1; + gBufferModule = sStackModule->buffer_module; + status = benaphore_init(&sCacheLock, "arp cache"); if (status < B_OK) - goto err2; + goto err1; sCache = hash_init(64, offsetof(struct arp_entry, next), &arp_entry::Compare, &arp_entry::Hash); if (sCache == NULL) { status = B_NO_MEMORY; - goto err3; + goto err2; } register_generic_syscall(ARP_SYSCALLS, arp_control, 1, 0); return B_OK; -err3: - benaphore_destroy(&sCacheLock); err2: - put_module(NET_BUFFER_MODULE_NAME); + benaphore_destroy(&sCacheLock); err1: put_module(NET_STACK_MODULE_NAME); return status; @@ -761,7 +758,6 @@ { unregister_generic_syscall(ARP_SYSCALLS, 1); - put_module(NET_BUFFER_MODULE_NAME); put_module(NET_STACK_MODULE_NAME); return B_OK; } Modified: haiku/trunk/src/add-ons/kernel/network/protocols/icmp/icmp.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/icmp/icmp.cpp 2007-04-13 00:55:32 UTC (rev 20672) +++ haiku/trunk/src/add-ons/kernel/network/protocols/icmp/icmp.cpp 2007-04-13 03:06:36 UTC (rev 20673) @@ -300,12 +300,9 @@ status_t status = get_module(NET_STACK_MODULE_NAME, (module_info **)&sStackModule); if (status < B_OK) return status; - status = get_module(NET_BUFFER_MODULE_NAME, (module_info **)&gBufferModule); - if (status < B_OK) { - put_module(NET_STACK_MODULE_NAME); - return status; - } + gBufferModule = sStackModule->buffer_module; + sStackModule->register_domain_protocols(AF_INET, SOCK_DGRAM, IPPROTO_ICMP, "network/protocols/icmp/v1", "network/protocols/ipv4/v1", @@ -317,7 +314,6 @@ } case B_MODULE_UNINIT: - put_module(NET_BUFFER_MODULE_NAME); put_module(NET_STACK_MODULE_NAME); return B_OK; Modified: haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp 2007-04-13 00:55:32 UTC (rev 20672) +++ haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp 2007-04-13 03:06:36 UTC (rev 20673) @@ -1117,31 +1117,28 @@ status_t status = get_module(NET_STACK_MODULE_NAME, (module_info **)&gStackModule); if (status < B_OK) return status; - status = get_module(NET_BUFFER_MODULE_NAME, (module_info **)&gBufferModule); - if (status < B_OK) - goto err1; - status = get_module(NET_DATALINK_MODULE_NAME, (module_info **)&sDatalinkModule); - if (status < B_OK) - goto err2; + gBufferModule = gStackModule->buffer_module; + sDatalinkModule = gStackModule->datalink_module; + sPacketID = (int32)system_time(); status = benaphore_init(&sRawSocketsLock, "raw sockets"); if (status < B_OK) - goto err3; + goto err1; status = benaphore_init(&sFragmentLock, "IPv4 Fragments"); if (status < B_OK) - goto err4; + goto err2; status = benaphore_init(&sReceivingProtocolLock, "IPv4 receiving protocols"); if (status < B_OK) - goto err5; + goto err3; sFragmentHash = hash_init(MAX_HASH_FRAGMENTS, FragmentPacket::NextOffset(), &FragmentPacket::Compare, &FragmentPacket::Hash); if (sFragmentHash == NULL) - goto err6; + goto err4; new (&sRawSockets) RawSocketList; // static initializers do not work in the kernel, @@ -1151,27 +1148,23 @@ status = gStackModule->register_domain_protocols(AF_INET, SOCK_RAW, 0, "network/protocols/ipv4/v1", NULL); if (status < B_OK) - goto err7; + goto err5; status = gStackModule->register_domain(AF_INET, "internet", &gIPv4Module, &gIPv4AddressModule, &sDomain); if (status < B_OK) - goto err7; + goto err5; return B_OK; -err7: - hash_uninit(sFragmentHash); -err6: - benaphore_destroy(&sReceivingProtocolLock); err5: - benaphore_destroy(&sFragmentLock); + hash_uninit(sFragmentHash); err4: - benaphore_destroy(&sRawSocketsLock); + benaphore_destroy(&sReceivingProtocolLock); err3: - put_module(NET_DATALINK_MODULE_NAME); + benaphore_destroy(&sFragmentLock); err2: - put_module(NET_BUFFER_MODULE_NAME); + benaphore_destroy(&sRawSocketsLock); err1: put_module(NET_STACK_MODULE_NAME); return status; @@ -1198,8 +1191,6 @@ benaphore_destroy(&sRawSocketsLock); benaphore_destroy(&sReceivingProtocolLock); - put_module(NET_DATALINK_MODULE_NAME); - put_module(NET_BUFFER_MODULE_NAME); put_module(NET_STACK_MODULE_NAME); return B_OK; } Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.cpp 2007-04-13 00:55:32 UTC (rev 20672) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.cpp 2007-04-13 03:06:36 UTC (rev 20673) @@ -634,54 +634,43 @@ status = get_module(NET_STACK_MODULE_NAME, (module_info **)&gStackModule); if (status < B_OK) return status; - status = get_module(NET_BUFFER_MODULE_NAME, (module_info **)&gBufferModule); - if (status < B_OK) - goto err1; - status = get_module(NET_SOCKET_MODULE_NAME, (module_info **)&gSocketModule); - if (status < B_OK) - goto err2; - status = get_module(NET_DATALINK_MODULE_NAME, (module_info **)&gDatalinkModule); - if (status < B_OK) - goto err3; + gBufferModule = gStackModule->buffer_module; + gSocketModule = gStackModule->socket_module; + gDatalinkModule = gStackModule->datalink_module; + gEndpointManager = new (std::nothrow) EndpointManager(); if (gEndpointManager == NULL) { status = B_NO_MEMORY; - goto err4; + goto err1; } status = gEndpointManager->InitCheck(); if (status < B_OK) - goto err5; + goto err2; status = gStackModule->register_domain_protocols(AF_INET, SOCK_STREAM, 0, "network/protocols/tcp/v1", "network/protocols/ipv4/v1", NULL); if (status < B_OK) - goto err5; + goto err2; status = gStackModule->register_domain_protocols(AF_INET, SOCK_STREAM, IPPROTO_TCP, "network/protocols/tcp/v1", "network/protocols/ipv4/v1", NULL); if (status < B_OK) - goto err5; + goto err2; status = gStackModule->register_domain_receiving_protocol(AF_INET, IPPROTO_TCP, "network/protocols/tcp/v1"); if (status < B_OK) - goto err5; + goto err2; return B_OK; -err5: - delete gEndpointManager; -err4: - put_module(NET_DATALINK_MODULE_NAME); -err3: - put_module(NET_SOCKET_MODULE_NAME); err2: - put_module(NET_BUFFER_MODULE_NAME); + delete gEndpointManager; err1: put_module(NET_STACK_MODULE_NAME); @@ -694,12 +683,7 @@ tcp_uninit() { delete gEndpointManager; - - put_module(NET_DATALINK_MODULE_NAME); - put_module(NET_SOCKET_MODULE_NAME); - put_module(NET_BUFFER_MODULE_NAME); put_module(NET_STACK_MODULE_NAME); - return B_OK; } Modified: haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp 2007-04-13 00:55:32 UTC (rev 20672) +++ haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp 2007-04-13 03:06:36 UTC (rev 20673) @@ -178,8 +178,6 @@ UdpEndpointManager(); ~UdpEndpointManager(); - status_t DemuxIncomingBuffer(net_domain *domain, - net_buffer *buffer); status_t ReceiveData(net_buffer *buffer); UdpDomainSupport *OpenEndpoint(UdpEndpoint *endpoint); @@ -203,7 +201,6 @@ net_stack_module_info *gStackModule; net_buffer_module_info *gBufferModule; -static net_datalink_module_info *sDatalinkModule; // #pragma mark - @@ -544,21 +541,6 @@ status_t -UdpEndpointManager::DemuxIncomingBuffer(net_domain *domain, net_buffer *buffer) -{ - UdpDomainSupport *domainSupport = _GetDomain(domain, false); - if (domainSupport == NULL) { - // we don't instantiate domain supports in the - // RX path as we are only interested in delivering - // data to existing sockets. - return B_BAD_VALUE; - } - - return domainSupport->DemuxIncomingBuffer(buffer); -} - - -status_t UdpEndpointManager::ReceiveData(net_buffer *buffer) { TRACE_EPM("ReceiveData(%p [%ld bytes])", buffer, buffer->size); @@ -621,7 +603,15 @@ bufferHeader.Remove(); // remove UDP-header from buffer before passing it on - status_t status = DemuxIncomingBuffer(domain, buffer); + UdpDomainSupport *domainSupport = _GetDomain(domain, false); + if (domainSupport == NULL) { + // we don't instantiate domain supports in the + // RX path as we are only interested in delivering + // data to existing sockets. + return B_ERROR; + } + + status_t status = domainSupport->DemuxIncomingBuffer(buffer); if (status < B_OK) { TRACE_EPM(" ReceiveData(): no endpoint."); // TODO: send ICMP-error @@ -904,11 +894,11 @@ TRACE_EP("SendData(%p [%lu bytes])", buffer, buffer->size); net_route *route = NULL; - status_t status = sDatalinkModule->get_buffer_route(Domain(), buffer, - &route); + status_t status = gStackModule->datalink_module->get_buffer_route(Domain(), + buffer, &route); if (status >= B_OK) { status = SendRoutedData(buffer, route); - sDatalinkModule->put_route(Domain(), route); + gStackModule->datalink_module->put_route(Domain(), route); } return status; @@ -1134,48 +1124,39 @@ status = get_module(NET_STACK_MODULE_NAME, (module_info **)&gStackModule); if (status < B_OK) return status; - status = get_module(NET_BUFFER_MODULE_NAME, (module_info **)&gBufferModule); - if (status < B_OK) - goto err1; - status = get_module(NET_DATALINK_MODULE_NAME, (module_info **)&sDatalinkModule); - if (status < B_OK) - goto err2; + gBufferModule = gStackModule->buffer_module; sUdpEndpointManager = new (std::nothrow) UdpEndpointManager; if (sUdpEndpointManager == NULL) { status = ENOBUFS; - goto err3; + goto err1; } status = sUdpEndpointManager->InitCheck(); if (status != B_OK) - goto err3; + goto err1; status = gStackModule->register_domain_protocols(AF_INET, SOCK_DGRAM, IPPROTO_IP, "network/protocols/udp/v1", "network/protocols/ipv4/v1", NULL); if (status < B_OK) - goto err4; + goto err2; status = gStackModule->register_domain_protocols(AF_INET, SOCK_DGRAM, IPPROTO_UDP, "network/protocols/udp/v1", "network/protocols/ipv4/v1", NULL); if (status < B_OK) - goto err4; + goto err2; status = gStackModule->register_domain_receiving_protocol(AF_INET, IPPROTO_UDP, "network/protocols/udp/v1"); if (status < B_OK) - goto err4; + goto err2; return B_OK; -err4: - delete sUdpEndpointManager; -err3: - put_module(NET_DATALINK_MODULE_NAME); err2: - put_module(NET_BUFFER_MODULE_NAME); + delete sUdpEndpointManager; err1: put_module(NET_STACK_MODULE_NAME); @@ -1189,8 +1170,6 @@ { TRACE_EPM("uninit_udp()"); delete sUdpEndpointManager; - put_module(NET_DATALINK_MODULE_NAME); - put_module(NET_BUFFER_MODULE_NAME); put_module(NET_STACK_MODULE_NAME); return B_OK; } Modified: haiku/trunk/src/add-ons/kernel/network/stack/stack.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/stack.cpp 2007-04-13 00:55:32 UTC (rev 20672) +++ haiku/trunk/src/add-ons/kernel/network/stack/stack.cpp 2007-04-13 03:06:36 UTC (rev 20673) @@ -894,6 +894,11 @@ 0, stack_std_ops }, + + &gNetBufferModule, + &gNetDatalinkModule, + &gNetSocketModule, + register_domain, unregister_domain, get_domain, From hugosantos at mail.berlios.de Fri Apr 13 05:45:36 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Fri, 13 Apr 2007 05:45:36 +0200 Subject: [Haiku-commits] r20674 - haiku/trunk/src/add-ons/kernel/network/protocols/tcp Message-ID: <200704130345.l3D3jalx010043@sheep.berlios.de> Author: hugosantos Date: 2007-04-13 05:45:28 +0200 (Fri, 13 Apr 2007) New Revision: 20674 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20674&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp Log: don't do MSS segmentation in TCP's SendData(), _SendQueue() already does the appropriate work. Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-13 03:06:36 UTC (rev 20673) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-13 03:45:28 UTC (rev 20674) @@ -480,58 +480,21 @@ return EPIPE; } - size_t bytesLeft = buffer->size; + if (buffer->size > 0) { + bigtime_t timeout = absolute_timeout(socket->send.timeout); - bigtime_t timeout = absolute_timeout(socket->send.timeout); - - do { - // TODO we should not segment here, but on TX. - - net_buffer *chunk; - if (bytesLeft > socket->send.buffer_size) { - // divide the buffer in multiple of the maximum segment size - size_t chunkSize = ((socket->send.buffer_size >> 1) / fSendMaxSegmentSize) - * fSendMaxSegmentSize; - - chunk = gBufferModule->split(buffer, chunkSize); - TRACE(" Send() split buffer at %lu (buffer size %lu, mss %lu) -> %p", - chunkSize, socket->send.buffer_size, fSendMaxSegmentSize, chunk); - if (chunk == NULL) - return B_NO_MEMORY; - } else - chunk = buffer; - - while (fSendQueue.Free() < chunk->size) { + while (fSendQueue.Free() < buffer->size) { status_t status = fSendList.Wait(lock, timeout); if (status < B_OK) return posix_error(status); } - // TODO: check state! + fSendQueue.Add(buffer); + } - if (chunk->size == 0) { - gBufferModule->free(chunk); - return B_OK; - } + if (fState == ESTABLISHED || fState == FINISH_RECEIVED) + _SendQueued(); - size_t chunkSize = chunk->size; - fSendQueue.Add(chunk); - - status_t status = B_OK; - - if (fState == ESTABLISHED || fState == FINISH_RECEIVED) - status = _SendQueued(); - - if (buffer != chunk) { - // as long as we didn't eat the buffer, we can still return an error code - // (we don't own the buffer if we return an error code) - if (status < B_OK) - return status; - } - - bytesLeft -= chunkSize; - } while (bytesLeft > 0); - return B_OK; } From hugosantos at mail.berlios.de Fri Apr 13 06:20:49 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Fri, 13 Apr 2007 06:20:49 +0200 Subject: [Haiku-commits] r20675 - in haiku/trunk: headers/private/net src/add-ons/kernel/network/protocols/ipv4 Message-ID: <200704130420.l3D4KnOX011145@sheep.berlios.de> Author: hugosantos Date: 2007-04-13 06:20:39 +0200 (Fri, 13 Apr 2007) New Revision: 20675 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20675&view=rev Modified: haiku/trunk/headers/private/net/ProtocolUtilities.h haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp Log: only deliver frames to IPv4 raw sockets of the specified protocol. Modified: haiku/trunk/headers/private/net/ProtocolUtilities.h =================================================================== --- haiku/trunk/headers/private/net/ProtocolUtilities.h 2007-04-13 03:45:28 UTC (rev 20674) +++ haiku/trunk/headers/private/net/ProtocolUtilities.h 2007-04-13 04:20:39 UTC (rev 20675) @@ -60,6 +60,8 @@ void WakeAll(); + net_socket *Socket() const { return fSocket; } + protected: status_t _Enqueue(net_buffer *buffer); status_t _EnqueueClone(net_buffer *buffer); Modified: haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp 2007-04-13 03:45:28 UTC (rev 20674) +++ haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp 2007-04-13 04:20:39 UTC (rev 20675) @@ -585,8 +585,12 @@ RawSocketList::Iterator iterator = sRawSockets.GetIterator(); - while (iterator.HasNext()) - iterator.Next()->EnqueueClone(buffer); + while (iterator.HasNext()) { + RawSocket *raw = iterator.Next(); + + if (raw->Socket()->protocol == buffer->protocol) + raw->EnqueueClone(buffer); + } } @@ -909,7 +913,7 @@ gBufferModule->checksum(buffer, 0, buffer->size, true))); TRACE(("destination-IP: buffer=%p addr=%p %08lx\n", buffer, &buffer->destination, - ntohl(destination->sin_addr.s_addr))); + ntohl(destination.sin_addr.s_addr))); uint32 mtu = route->mtu ? route->mtu : interface->mtu; if (buffer->size > mtu) { @@ -1074,10 +1078,7 @@ // we must no longer access bufferHeader or header anymore after // this point - if (protocol != IPPROTO_TCP && protocol != IPPROTO_UDP) { - // SOCK_RAW doesn't get all packets - raw_receive_data(buffer); - } + raw_receive_data(buffer); gBufferModule->remove_header(buffer, headerLength); // the header is of variable size and may include IP options From axeld at pinc-software.de Fri Apr 13 09:53:40 2007 From: axeld at pinc-software.de (Axel =?iso-8859-15?q?D=F6rfler?=) Date: Fri, 13 Apr 2007 09:53:40 +0200 CEST Subject: [Haiku-commits] =?iso-8859-15?q?r20673_-_in_haiku/trunk=3A_header?= =?iso-8859-15?q?s/private/net_src/add-ons/kernel/network/datalink=5Fproto?= =?iso-8859-15?q?cols/arp_src/add-ons/kernel/network/protocols/icmp_src/ad?= =?iso-8859-15?q?d-ons/kernel/network/protocols/ipv4_src/add-ons/kernel/ne?= =?iso-8859-15?q?twork/protocols/tcp_src/add-ons/kernel/network/protocols/?= =?iso-8859-15?q?udp_src/add-ons/kernel/network/stack?= In-Reply-To: <200704130306.l3D36w3V008573@sheep.berlios.de> Message-ID: <544622386-BeMail@zon> hugosantos at mail.berlios.de wrote: > Log: > added buffer, datalink and socket module references to the stack > module so we > don't have to load them in each other module. I don't like that change at all; you're bypassing the usual module mechanism, and also prevent the per-module initializations to be called - net_socket relies on this, for example. If you don't like to load all those modules, there is also the module_dependency extension that would work like this (not available under BeOS): module_dependency module_dependencies[] = { { NET_STACK_MODULE_NAME, (module_info **)&sStackModule }, { NET_BUFFER_MODULE_NAME, (module_info **)&sBufferModule }, {} }; Please either revert that change or change it to use the above mechanism. Bye, Axel. From hugosantos at mail.berlios.de Fri Apr 13 16:38:16 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Fri, 13 Apr 2007 16:38:16 +0200 Subject: [Haiku-commits] r20676 - in haiku/trunk: headers/private/net src/add-ons/kernel/network/datalink_protocols/arp src/add-ons/kernel/network/protocols/icmp src/add-ons/kernel/network/protocols/ipv4 src/add-ons/kernel/network/protocols/tcp src/add-ons/kernel/network/protocols/udp src/add-ons/kernel/network/stack Message-ID: <200704131438.l3DEcG9A013474@sheep.berlios.de> Author: hugosantos Date: 2007-04-13 16:37:48 +0200 (Fri, 13 Apr 2007) New Revision: 20676 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20676&view=rev Modified: haiku/trunk/headers/private/net/ProtocolUtilities.h haiku/trunk/headers/private/net/net_stack.h haiku/trunk/src/add-ons/kernel/network/datalink_protocols/arp/arp.cpp haiku/trunk/src/add-ons/kernel/network/protocols/icmp/icmp.cpp haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.cpp haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp haiku/trunk/src/add-ons/kernel/network/stack/stack.cpp Log: use module_dependencies to load the required modules by udp, tcp, ipv4, icmp and arp. Modified: haiku/trunk/headers/private/net/ProtocolUtilities.h =================================================================== --- haiku/trunk/headers/private/net/ProtocolUtilities.h 2007-04-13 04:20:39 UTC (rev 20675) +++ haiku/trunk/headers/private/net/ProtocolUtilities.h 2007-04-13 14:37:48 UTC (rev 20676) @@ -30,12 +30,13 @@ }; +extern net_buffer_module_info *gBufferModule; extern net_stack_module_info *gStackModule; class NetModuleBundleGetter { public: static net_stack_module_info *Stack() { return gStackModule; } - static net_buffer_module_info *Buffer() { return gStackModule->buffer_module; } + static net_buffer_module_info *Buffer() { return gBufferModule; } }; Modified: haiku/trunk/headers/private/net/net_stack.h =================================================================== --- haiku/trunk/headers/private/net/net_stack.h 2007-04-13 04:20:39 UTC (rev 20675) +++ haiku/trunk/headers/private/net/net_stack.h 2007-04-13 14:37:48 UTC (rev 20676) @@ -55,10 +55,6 @@ struct net_stack_module_info { module_info info; - struct net_buffer_module_info *buffer_module; - struct net_datalink_module_info *datalink_module; - struct net_socket_module_info *socket_module; - status_t (*register_domain)(int family, const char *name, struct net_protocol_module_info *module, struct net_address_module_info *addressModule, Modified: haiku/trunk/src/add-ons/kernel/network/datalink_protocols/arp/arp.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/datalink_protocols/arp/arp.cpp 2007-04-13 04:20:39 UTC (rev 20675) +++ haiku/trunk/src/add-ons/kernel/network/datalink_protocols/arp/arp.cpp 2007-04-13 14:37:48 UTC (rev 20676) @@ -98,7 +98,7 @@ static void arp_timer(struct net_timer *timer, void *data); -struct net_buffer_module_info *gBufferModule; +net_buffer_module_info *gBufferModule; static net_stack_module_info *sStackModule; static hash_table *sCache; static benaphore sCacheLock; @@ -725,31 +725,19 @@ static status_t arp_init() { - status_t status = get_module(NET_STACK_MODULE_NAME, (module_info **)&sStackModule); + status_t status = benaphore_init(&sCacheLock, "arp cache"); if (status < B_OK) return status; - gBufferModule = sStackModule->buffer_module; - - status = benaphore_init(&sCacheLock, "arp cache"); - if (status < B_OK) - goto err1; - sCache = hash_init(64, offsetof(struct arp_entry, next), &arp_entry::Compare, &arp_entry::Hash); if (sCache == NULL) { - status = B_NO_MEMORY; - goto err2; + benaphore_destroy(&sCacheLock); + return B_NO_MEMORY; } register_generic_syscall(ARP_SYSCALLS, arp_control, 1, 0); return B_OK; - -err2: - benaphore_destroy(&sCacheLock); -err1: - put_module(NET_STACK_MODULE_NAME); - return status; } @@ -757,8 +745,6 @@ arp_uninit() { unregister_generic_syscall(ARP_SYSCALLS, 1); - - put_module(NET_STACK_MODULE_NAME); return B_OK; } @@ -966,6 +952,13 @@ arp_control, }; + +module_dependency module_dependencies[] = { + {NET_STACK_MODULE_NAME, (module_info **)&sStackModule}, + {NET_BUFFER_MODULE_NAME, (module_info **)&gBufferModule}, + {} +}; + module_info *modules[] = { (module_info *)&sARPModule, NULL Modified: haiku/trunk/src/add-ons/kernel/network/protocols/icmp/icmp.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/icmp/icmp.cpp 2007-04-13 04:20:39 UTC (rev 20675) +++ haiku/trunk/src/add-ons/kernel/network/protocols/icmp/icmp.cpp 2007-04-13 14:37:48 UTC (rev 20676) @@ -62,8 +62,8 @@ }; +net_buffer_module_info *gBufferModule; static net_stack_module_info *sStackModule; -struct net_buffer_module_info *gBufferModule; net_protocol * @@ -297,12 +297,6 @@ switch (op) { case B_MODULE_INIT: { - status_t status = get_module(NET_STACK_MODULE_NAME, (module_info **)&sStackModule); - if (status < B_OK) - return status; - - gBufferModule = sStackModule->buffer_module; - sStackModule->register_domain_protocols(AF_INET, SOCK_DGRAM, IPPROTO_ICMP, "network/protocols/icmp/v1", "network/protocols/ipv4/v1", @@ -314,7 +308,6 @@ } case B_MODULE_UNINIT: - put_module(NET_STACK_MODULE_NAME); return B_OK; default: @@ -353,6 +346,12 @@ icmp_error_reply, }; +module_dependency module_dependencies[] = { + {NET_STACK_MODULE_NAME, (module_info **)&sStackModule}, + {NET_BUFFER_MODULE_NAME, (module_info **)&gBufferModule}, + {} +}; + module_info *modules[] = { (module_info *)&sICMPModule, NULL Modified: haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp 2007-04-13 04:20:39 UTC (rev 20675) +++ haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp 2007-04-13 14:37:48 UTC (rev 20676) @@ -1115,31 +1115,24 @@ status_t init_ipv4() { - status_t status = get_module(NET_STACK_MODULE_NAME, (module_info **)&gStackModule); - if (status < B_OK) - return status; - - gBufferModule = gStackModule->buffer_module; - sDatalinkModule = gStackModule->datalink_module; - sPacketID = (int32)system_time(); - status = benaphore_init(&sRawSocketsLock, "raw sockets"); + status_t status = benaphore_init(&sRawSocketsLock, "raw sockets"); if (status < B_OK) - goto err1; + return status; status = benaphore_init(&sFragmentLock, "IPv4 Fragments"); if (status < B_OK) - goto err2; + goto err1; status = benaphore_init(&sReceivingProtocolLock, "IPv4 receiving protocols"); if (status < B_OK) - goto err3; + goto err2; sFragmentHash = hash_init(MAX_HASH_FRAGMENTS, FragmentPacket::NextOffset(), &FragmentPacket::Compare, &FragmentPacket::Hash); if (sFragmentHash == NULL) - goto err4; + goto err3; new (&sRawSockets) RawSocketList; // static initializers do not work in the kernel, @@ -1149,25 +1142,23 @@ status = gStackModule->register_domain_protocols(AF_INET, SOCK_RAW, 0, "network/protocols/ipv4/v1", NULL); if (status < B_OK) - goto err5; + goto err4; status = gStackModule->register_domain(AF_INET, "internet", &gIPv4Module, &gIPv4AddressModule, &sDomain); if (status < B_OK) - goto err5; + goto err4; return B_OK; -err5: - hash_uninit(sFragmentHash); err4: - benaphore_destroy(&sReceivingProtocolLock); + hash_uninit(sFragmentHash); err3: - benaphore_destroy(&sFragmentLock); + benaphore_destroy(&sReceivingProtocolLock); err2: - benaphore_destroy(&sRawSocketsLock); + benaphore_destroy(&sFragmentLock); err1: - put_module(NET_STACK_MODULE_NAME); + benaphore_destroy(&sRawSocketsLock); return status; } @@ -1242,6 +1233,13 @@ ipv4_error_reply, }; +module_dependency module_dependencies[] = { + {NET_STACK_MODULE_NAME, (module_info **)&gStackModule}, + {NET_BUFFER_MODULE_NAME, (module_info **)&gBufferModule}, + {NET_DATALINK_MODULE_NAME, (module_info **)&sDatalinkModule}, + {} +}; + module_info *modules[] = { (module_info *)&gIPv4Module, NULL Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.cpp 2007-04-13 04:20:39 UTC (rev 20675) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.cpp 2007-04-13 14:37:48 UTC (rev 20676) @@ -631,48 +631,37 @@ gDomain = NULL; gAddressModule = NULL; - status = get_module(NET_STACK_MODULE_NAME, (module_info **)&gStackModule); - if (status < B_OK) - return status; - - gBufferModule = gStackModule->buffer_module; - gSocketModule = gStackModule->socket_module; - gDatalinkModule = gStackModule->datalink_module; - gEndpointManager = new (std::nothrow) EndpointManager(); - if (gEndpointManager == NULL) { - status = B_NO_MEMORY; - goto err1; - } + if (gEndpointManager == NULL) + return B_NO_MEMORY; + status = gEndpointManager->InitCheck(); if (status < B_OK) - goto err2; + goto err1; status = gStackModule->register_domain_protocols(AF_INET, SOCK_STREAM, 0, "network/protocols/tcp/v1", "network/protocols/ipv4/v1", NULL); if (status < B_OK) - goto err2; + goto err1; status = gStackModule->register_domain_protocols(AF_INET, SOCK_STREAM, IPPROTO_TCP, "network/protocols/tcp/v1", "network/protocols/ipv4/v1", NULL); if (status < B_OK) - goto err2; + goto err1; status = gStackModule->register_domain_receiving_protocol(AF_INET, IPPROTO_TCP, "network/protocols/tcp/v1"); if (status < B_OK) - goto err2; + goto err1; return B_OK; -err2: - delete gEndpointManager; err1: - put_module(NET_STACK_MODULE_NAME); + delete gEndpointManager; TRACE(("init_tcp() fails with %lx (%s)\n", status, strerror(status))); return status; @@ -683,7 +672,6 @@ tcp_uninit() { delete gEndpointManager; - put_module(NET_STACK_MODULE_NAME); return B_OK; } @@ -734,6 +722,14 @@ tcp_error_reply, }; +module_dependency module_dependencies[] = { + {NET_STACK_MODULE_NAME, (module_info **)&gStackModule}, + {NET_BUFFER_MODULE_NAME, (module_info **)&gBufferModule}, + {NET_DATALINK_MODULE_NAME, (module_info **)&gDatalinkModule}, + {NET_SOCKET_MODULE_NAME, (module_info **)&gSocketModule}, + {} +}; + module_info *modules[] = { (module_info *)&sTCPModule, NULL Modified: haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp 2007-04-13 04:20:39 UTC (rev 20675) +++ haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp 2007-04-13 14:37:48 UTC (rev 20676) @@ -199,8 +199,9 @@ static UdpEndpointManager *sUdpEndpointManager; -net_stack_module_info *gStackModule; net_buffer_module_info *gBufferModule; +net_datalink_module_info *gDatalinkModule; +net_stack_module_info *gStackModule; // #pragma mark - @@ -894,11 +895,11 @@ TRACE_EP("SendData(%p [%lu bytes])", buffer, buffer->size); net_route *route = NULL; - status_t status = gStackModule->datalink_module->get_buffer_route(Domain(), + status_t status = gDatalinkModule->get_buffer_route(Domain(), buffer, &route); if (status >= B_OK) { status = SendRoutedData(buffer, route); - gStackModule->datalink_module->put_route(Domain(), route); + gDatalinkModule->put_route(Domain(), route); } return status; @@ -1121,16 +1122,10 @@ status_t status; TRACE_EPM("init_udp()"); - status = get_module(NET_STACK_MODULE_NAME, (module_info **)&gStackModule); - if (status < B_OK) - return status; - gBufferModule = gStackModule->buffer_module; - sUdpEndpointManager = new (std::nothrow) UdpEndpointManager; - if (sUdpEndpointManager == NULL) { - status = ENOBUFS; - goto err1; - } + if (sUdpEndpointManager == NULL) + return B_NO_MEMORY; + status = sUdpEndpointManager->InitCheck(); if (status != B_OK) goto err1; @@ -1140,25 +1135,23 @@ "network/protocols/ipv4/v1", NULL); if (status < B_OK) - goto err2; + goto err1; status = gStackModule->register_domain_protocols(AF_INET, SOCK_DGRAM, IPPROTO_UDP, "network/protocols/udp/v1", "network/protocols/ipv4/v1", NULL); if (status < B_OK) - goto err2; + goto err1; status = gStackModule->register_domain_receiving_protocol(AF_INET, IPPROTO_UDP, "network/protocols/udp/v1"); if (status < B_OK) - goto err2; + goto err1; return B_OK; -err2: - delete sUdpEndpointManager; err1: - put_module(NET_STACK_MODULE_NAME); + delete sUdpEndpointManager; TRACE_EPM("init_udp() fails with %lx (%s)", status, strerror(status)); return status; @@ -1170,7 +1163,6 @@ { TRACE_EPM("uninit_udp()"); delete sUdpEndpointManager; - put_module(NET_STACK_MODULE_NAME); return B_OK; } @@ -1221,6 +1213,13 @@ udp_error_reply, }; +module_dependency module_dependencies[] = { + {NET_STACK_MODULE_NAME, (module_info **)&gStackModule}, + {NET_BUFFER_MODULE_NAME, (module_info **)&gBufferModule}, + {NET_DATALINK_MODULE_NAME, (module_info **)&gDatalinkModule}, + {} +}; + module_info *modules[] = { (module_info *)&sUDPModule, NULL Modified: haiku/trunk/src/add-ons/kernel/network/stack/stack.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/stack.cpp 2007-04-13 04:20:39 UTC (rev 20675) +++ haiku/trunk/src/add-ons/kernel/network/stack/stack.cpp 2007-04-13 14:37:48 UTC (rev 20676) @@ -895,10 +895,6 @@ stack_std_ops }, - &gNetBufferModule, - &gNetDatalinkModule, - &gNetSocketModule, - register_domain, unregister_domain, get_domain, From hugosantos at gmail.com Fri Apr 13 16:44:44 2007 From: hugosantos at gmail.com (Hugo Santos) Date: Fri, 13 Apr 2007 15:44:44 +0100 Subject: [Haiku-commits] r20673 - in haiku/trunk: headers/private/net src/add-ons/kernel/network/datalink_protocols/arp src/add-ons/kernel/network/protocols/icmp src/add-ons/kernel/network/protocols/ipv4 src/add-ons/kernel/network/protocols/tcp src/add-on Message-ID: <9c46321e0704130744r1684ad0cw56ec3c393834020f@mail.gmail.com> Hey Axel, I switched to using module_dependencies to load the modules. My initial idea was to introduce some kind of "Bundle" class that loaded the modules required. In essence i wanted an easier way to reference modules from common infrastructure like NetBufferUtilities or ProtocolUtilities. The motivation for this change was that the buffer module is a pseudo-dependency of the stack module anyway, so we could rely on it loading it for us (which then got expanded to the socket and datalink modules as well). It directly referenced it because they are all linked together, but it could very well load it. Anyway, this is fixed now. Hugo On 4/13/07, Axel D?rfler wrote: > hugosantos at mail.berlios.de wrote: > > Log: > > added buffer, datalink and socket module references to the stack > > module so we > don't have to load them in each other module. > > I don't like that change at all; you're bypassing the usual module > mechanism, and also prevent the per-module initializations to be called > - net_socket relies on this, for example. > If you don't like to load all those modules, there is also the > module_dependency extension that would work like this (not available > under BeOS): > > module_dependency module_dependencies[] = { > { NET_STACK_MODULE_NAME, (module_info **)&sStackModule }, > { NET_BUFFER_MODULE_NAME, (module_info **)&sBufferModule }, > {} > }; > > Please either revert that change or change it to use the above > mechanism. > > Bye, > Axel. > > _______________________________________________ > Haiku-commits mailing list > Haiku-commits at lists.berlios.de > https://lists.berlios.de/mailman/listinfo/haiku-commits > From marcusoverhagen at mail.berlios.de Fri Apr 13 17:52:58 2007 From: marcusoverhagen at mail.berlios.de (marcusoverhagen at BerliOS) Date: Fri, 13 Apr 2007 17:52:58 +0200 Subject: [Haiku-commits] r20677 - haiku/trunk/headers/private/drivers Message-ID: <200704131552.l3DFqwEq017863@sheep.berlios.de> Author: marcusoverhagen Date: 2007-04-13 17:52:58 +0200 (Fri, 13 Apr 2007) New Revision: 20677 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20677&view=rev Added: haiku/trunk/headers/private/drivers/dvb.h Log: Interface definition of DVB drivers. Currently private API. Added: haiku/trunk/headers/private/drivers/dvb.h =================================================================== --- haiku/trunk/headers/private/drivers/dvb.h 2007-04-13 14:37:48 UTC (rev 20676) +++ haiku/trunk/headers/private/drivers/dvb.h 2007-04-13 15:52:58 UTC (rev 20677) @@ -0,0 +1,269 @@ +/* + * Copyright (c) 2005 Marcus Overhagen + * + * Permission is hereby granted, free of charge, to any person + * obtaining a copy of this software and associated documentation + * files (the "Software"), to deal in the Software without restriction, + * including without limitation the rights to use, copy, modify, + * merge, publish, distribute, sublicense, and/or sell copies of + * the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be + * included in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES + * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT + * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, + * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + */ + +/* This is the driver ioctl interface used for DVB on BeOS + * it is not final, and will be changed before a public release + * is made of the DVB framework (media add-on and example player). + * + * The driver should publish in /dev/dvb/cardname/n (with n=1..). + * It must implement the ioctl codes from dvb_ioctl_t. + * The driver must have buffers readable by userspace, it + * should directly use DMA buffers for that. + * The DVB add-on expects DVB_CAPTURE to block until data is + * available, or a timeout has expired. If the timeout expired, + * it must return B_TIMED_OUT. This ensures that the driver + * doesn't block when reception conditions are going bad, and + * allows user space programs to recognize this. + * If the ioctl succeeds, the driver must record the capture end time + * and report the data pointer and size. The data must stay valid + * for a few ms, to give the user space thread, running at realtime + * priority, a chance to read it. The driver must do at least + * double buffering to achieve this. + * For DVB-T, two buffers of 61 kByte give about 16 ms validity period + * for each buffer, thats enough. A 100 ms timout is used, to ensure + * that DVB_CAPTURE doesn't block when no data is available. + * + * A normal ioctl sequence is: + * - DVB_GET_INTERFACE_INFO + * - DVB_SET_TUNING_PARAMETERS + * - DVB_GET_STATUS + * - DVB_START_CAPTURE + * - DVB_CAPTURE (repeated) + * - DVB_STOP_CAPTURE + * + * The following ioctls can be called at any time, + * including when capture is active: + * - DVB_GET_INTERFACE_INFO + * - DVB_GET_FREQUENCY_INFO + * - DVB_GET_TUNING_PARAMETERS + * - DVB_GET_STATUS + * - DVB_GET_SS + * - DVB_GET_BER + * - DVB_GET_SNR + * - DVB_GET_UPC + * + * In future releases, other ioctls that are not yet defined may + * be called. It's important that the driver does not crash, but + * instead returnes an error code. + * + * Parameter reference for ioctl() functions: + * + * opcode | parameter | description + * --------------------------+-------------------------+----------------------------------------- + * DVB_GET_INTERFACE_INFO | dvb_interface_info_t | get interface capabilites (memset to 0 first) + * DVB_GET_FREQUENCY_INFO | dvb_frequency_info_t | get interface capabilites (memset to 0 first) + * DVB_SET_TUNING_PARAMETERS | dvb_tuning_parameters_t | perform tuning information + * DVB_GET_TUNING_PARAMETERS | dvb_tuning_parameters_t | get active parameters (after autotuning) (memset to 0 first) + * DVB_START_CAPTURE | (none) | start the capture + * DVB_STOP_CAPTURE | (none) | stop the capture + * DVB_GET_STATUS | dvb_status_t | get current status + * DVB_GET_SS | uint32 | signal strength, range 0 to 1000 + * DVB_GET_BER | uint32 | block error rate, range 0 to 1000 + * DVB_GET_SNR | uint32 | signal noise ratio, range 0 to 1000 + * DVB_GET_UPC | uint32 | XXX ???, range 0 to 1000 + * DVB_CAPTURE | dvb_capture_t | get information about captured data + * + */ + + +#ifndef __DVB_H +#define __DVB_H + +#include + +typedef enum { + DVB_TYPE_UNKNOWN = -1, + DVB_TYPE_DVB_C = 0x10, + DVB_TYPE_DVB_H = 0x20, + DVB_TYPE_DVB_S = 0x30, + DVB_TYPE_DVB_T = 0x40, +} dvb_type_t; + + +// channel bandwith +typedef enum { + DVB_BANDWIDTH_AUTO = 0, + DVB_BANDWIDTH_5_MHZ = 5000, + DVB_BANDWIDTH_6_MHZ = 6000, + DVB_BANDWIDTH_7_MHZ = 7000, + DVB_BANDWIDTH_8_MHZ = 8000, +} dvb_bandwidth_t; + + +// channel polarity +typedef enum { + DVB_POLARITY_UNKNOWN = -1, + DVB_POLARITY_VERTICAL = 1, + DVB_POLARITY_HORIZONTAL = 2, +} dvb_polarity_t; + + +// "modulation" or "constellation" +typedef enum { + DVB_MODULATION_AUTO, + DVB_MODULATION_QPSK, + DVB_MODULATION_16_QAM, + DVB_MODULATION_32_QAM, + DVB_MODULATION_64_QAM, + DVB_MODULATION_128_QAM, + DVB_MODULATION_256_QAM, +} dvb_modulation_t; + + +// dvb_cofdm_mode, dvb_transmission_mode +typedef enum { + DVB_TRANSMISSION_MODE_AUTO, + DVB_TRANSMISSION_MODE_2K, + DVB_TRANSMISSION_MODE_4K, + DVB_TRANSMISSION_MODE_8K, +} dvb_transmission_mode_t; + + +// code rate, specified by inner FEC (forward error correction) scheme +typedef enum { + DVB_FEC_AUTO, + DVB_FEC_NONE, + DVB_FEC_1_2, + DVB_FEC_2_3, + DVB_FEC_3_4, + DVB_FEC_4_5, + DVB_FEC_5_6, + DVB_FEC_6_7, + DVB_FEC_7_8, + DVB_FEC_8_9, +} dvb_code_rate_t; + + +// guard interval +typedef enum { + DVB_GUARD_INTERVAL_AUTO, + DVB_GUARD_INTERVAL_1_4, + DVB_GUARD_INTERVAL_1_8, + DVB_GUARD_INTERVAL_1_16, + DVB_GUARD_INTERVAL_1_32, +} dvb_guard_interval_t; + + +// alpha value for hierarchical transmission +typedef enum { + DVB_HIERARCHY_AUTO, + DVB_HIERARCHY_NONE, + DVB_HIERARCHY_1, + DVB_HIERARCHY_2, + DVB_HIERARCHY_4, +} dvb_hierarchy_t; + + +// spectral inversion +typedef enum { + DVB_INVERSION_AUTO, + DVB_INVERSION_ON, + DVB_INVERSION_OFF, +} dvb_inversion_t; + + +typedef enum { + DVB_STATUS_SIGNAL = 0x0001, + DVB_STATUS_CARRIER = 0x0002, + DVB_STATUS_LOCK = 0x0004, + DVB_STATUS_VITERBI = 0x0008, + DVB_STATUS_SYNC = 0x0010, +} dvb_status_t; + + +typedef enum { + DVB_GET_INTERFACE_INFO = (B_DEVICE_OP_CODES_END + 0x100), + DVB_GET_FREQUENCY_INFO = (B_DEVICE_OP_CODES_END + 0x120), + DVB_SET_TUNING_PARAMETERS, + DVB_GET_TUNING_PARAMETERS, + DVB_START_CAPTURE, + DVB_STOP_CAPTURE, + DVB_GET_STATUS, + DVB_GET_SS, + DVB_GET_BER, + DVB_GET_SNR, + DVB_GET_UPC, + DVB_CAPTURE, +} dvb_ioctl_t; + + +typedef struct { + uint32 version; // set this to 1 + uint32 flags; // set this to 0 + dvb_type_t type; + uint32 _res1[16]; + char name[100]; + char info[500]; + uint32 _res2[16]; +} dvb_interface_info_t; + + +typedef struct { + uint32 _res1[16]; + uint64 frequency_min; + uint64 frequency_max; + uint64 frequency_step; + uint32 _res2[64]; +} dvb_frequency_info_t; + + +typedef struct { + uint64 frequency; + dvb_inversion_t inversion; + dvb_bandwidth_t bandwidth; + dvb_modulation_t modulation; + dvb_hierarchy_t hierarchy; + dvb_code_rate_t code_rate_hp; + dvb_code_rate_t code_rate_lp; + dvb_transmission_mode_t transmission_mode; + dvb_guard_interval_t guard_interval; +} dvb_t_tuning_parameters_t; + + +typedef struct { + uint64 frequency; + dvb_inversion_t inversion; + dvb_modulation_t modulation; + uint32 symbolrate; + dvb_polarity_t polarity; +} dvb_s_tuning_parameters_t; + + +typedef struct { + union { + dvb_t_tuning_parameters_t dvb_t; + dvb_s_tuning_parameters_t dvb_s; + uint32 _pad[32]; + } u; +} dvb_tuning_parameters_t; + + +typedef struct { + void * data; + size_t size; + bigtime_t end_time; + uint32 _res[2]; +} dvb_capture_t; + +#endif From marcusoverhagen at mail.berlios.de Fri Apr 13 18:21:20 2007 From: marcusoverhagen at mail.berlios.de (marcusoverhagen at BerliOS) Date: Fri, 13 Apr 2007 18:21:20 +0200 Subject: [Haiku-commits] r20678 - in haiku/trunk/src/add-ons/kernel/drivers: . dvb dvb/cx23882 Message-ID: <200704131621.l3DGLKWY019556@sheep.berlios.de> Author: marcusoverhagen Date: 2007-04-13 18:21:17 +0200 (Fri, 13 Apr 2007) New Revision: 20678 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20678&view=rev Added: haiku/trunk/src/add-ons/kernel/drivers/dvb/ haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/ haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/config.h haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/cx22702.c haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/cx22702.h haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/cx23882.c haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/cx23882.h haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/cx23882_i2c.c haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/cx23882_i2c.h haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/cx23882_regs.h haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/driver.c haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/driver.h haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/dtt7592.c haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/dtt7592.h haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/dvb_interface.c haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/dvb_interface.h haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/i2c_core.c haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/i2c_core.h haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/util.c haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/util.h Log: Driver for DVB-T cards with cx23882 chipset, like WinTV NOVA-T PCI Added: haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/config.h =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/config.h 2007-04-13 15:52:58 UTC (rev 20677) +++ haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/config.h 2007-04-13 16:21:17 UTC (rev 20678) @@ -0,0 +1,41 @@ +/* + * Copyright (c) 2004-2007 Marcus Overhagen + * + * Permission is hereby granted, free of charge, to any person + * obtaining a copy of this software and associated documentation + * files (the "Software"), to deal in the Software without restriction, + * including without limitation the rights to use, copy, modify, + * merge, publish, distribute, sublicense, and/or sell copies of + * the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be + * included in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES + * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT + * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, + * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + */ + +#ifndef __CONFIG_H +#define __CONFIG_H + +#define VERSION "1.0" +#define BUILD __DATE__ " "__TIME__ +#define INFO1 "cx23882: DVB-T Driver. Version " VERSION ", Revision " REVISION ", Build " BUILD +#define INFO2 "cx23882: Copyright (c) 2004-2006 Marcus Overhagen. All rights reserved.\n" + +#define MAX_CARDS 8 + +#define PCI_LATENCY 0x20 + +#define I2C_ADDR_DEMOD 0x43 +#define I2C_ADDR_EEPROM 0x50 +#define I2C_ADDR_PLL 0x61 + +#endif Added: haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/cx22702.c =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/cx22702.c 2007-04-13 15:52:58 UTC (rev 20677) +++ haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/cx22702.c 2007-04-13 16:21:17 UTC (rev 20678) @@ -0,0 +1,306 @@ +/* + * Copyright (c) 2004-2007 Marcus Overhagen + * + * Permission is hereby granted, free of charge, to any person + * obtaining a copy of this software and associated documentation + * files (the "Software"), to deal in the Software without restriction, + * including without limitation the rights to use, copy, modify, + * merge, publish, distribute, sublicense, and/or sell copies of + * the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be + * included in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES + * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT + * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, + * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + */ + +#include +#include "cx22702.h" +#include "dtt7592.h" +#include "config.h" +#include "dvb.h" + +#define TRACE_CX22702 +#ifdef TRACE_CX22702 + #define TRACE dprintf +#else + #define TRACE(a...) +#endif + + +static void +cx22702_reg_dump(i2c_bus *bus) +{ + int i; + for (i = 0; i < 256; i++) { + uint8 data; + if (cx22702_reg_read(bus, i, &data) != B_OK) + dprintf("cx22702_reg 0x%02x error\n", i); + else + dprintf("cx22702_reg 0x%02x value 0x%02x\n", i, data); + } +} + + +status_t +cx22702_reg_write(i2c_bus *bus, uint8 reg, uint8 data) +{ + status_t res; + uint8 buf[2] = {reg, data}; + res = i2c_write(bus, I2C_ADDR_DEMOD, buf, 2); + if (res != B_OK) + TRACE("cx22702_reg_write error, reg 0x%02x, value 0x%02x\n", reg, data); + return res; +} + + +status_t +cx22702_reg_read(i2c_bus *bus, uint8 reg, uint8 *data) +{ + status_t res; + res = i2c_xfer(bus, I2C_ADDR_DEMOD, ®, 1, data, 1); + if (res != B_OK) + TRACE("cx22702_reg_read error, reg 0x%02x\n", reg); + return res; +} + + +status_t +cx22702_init(i2c_bus *bus) +{ + if (cx22702_reg_write(bus, 0x00, 0x02) != B_OK) return B_ERROR; + if (cx22702_reg_write(bus, 0x00, 0x00) != B_OK) return B_ERROR; + snooze(10000); + if (cx22702_reg_write(bus, 0x00, 0x00) != B_OK) return B_ERROR; + if (cx22702_reg_write(bus, 0x09, 0x01) != B_OK) return B_ERROR; + if (cx22702_reg_write(bus, 0x0B, 0x04) != B_OK) return B_ERROR; + if (cx22702_reg_write(bus, 0x0C, 0x00) != B_OK) return B_ERROR; + if (cx22702_reg_write(bus, 0x0D, 0x80) != B_OK) return B_ERROR; + if (cx22702_reg_write(bus, 0x26, 0x80) != B_OK) return B_ERROR; + if (cx22702_reg_write(bus, 0x2D, 0xff) != B_OK) return B_ERROR; + if (cx22702_reg_write(bus, 0xDC, 0x00) != B_OK) return B_ERROR; + if (cx22702_reg_write(bus, 0xE4, 0x00) != B_OK) return B_ERROR; + if (cx22702_reg_write(bus, 0xF8, 0x02) != B_OK) return B_ERROR; + if (cx22702_reg_write(bus, 0x00, 0x01) != B_OK) return B_ERROR; + return B_OK; +} + + +status_t +cx22702_get_frequency_info(i2c_bus *bus, dvb_frequency_info_t *info) +{ + memset(info, 0, sizeof(*info)); + info->frequency_min = 149000000; + info->frequency_max = 860000000; + info->frequency_step = 166667; + return B_OK; +} + + +status_t +cx22702_set_tuning_parameters(i2c_bus *bus, const dvb_t_tuning_parameters_t *params) +{ + uint8 data; + status_t res; + + if (cx22702_reg_write(bus, 0x00, 0x00) != B_OK) + return B_ERROR; + + res = dtt7592_set_frequency(bus, params->frequency, params->bandwidth); + if (res != B_OK) + return res; + + if (cx22702_reg_read(bus, 0x0c, &data) != B_OK) + return B_ERROR; + switch (params->inversion) { + case DVB_INVERSION_ON: data |= 0x01; break; + case DVB_INVERSION_OFF: data &= ~0x01; break; + default: return B_ERROR; + } + switch (params->bandwidth) { + case DVB_BANDWIDTH_6_MHZ: data = (data & ~0x10) | 0x20; break; + case DVB_BANDWIDTH_7_MHZ: data = (data & ~0x20) | 0x10; break; + case DVB_BANDWIDTH_8_MHZ: data &= ~0x30; break; + default: return B_ERROR; + } + if (cx22702_reg_write(bus, 0x0c, data) != B_OK) + return B_ERROR; + + switch (params->modulation) { + case DVB_MODULATION_QPSK: data = 0x00; break; + case DVB_MODULATION_16_QAM: data = 0x08; break; + case DVB_MODULATION_64_QAM: data = 0x10; break; + default: return B_ERROR; + } + switch (params->hierarchy) { + case DVB_HIERARCHY_NONE: break; + case DVB_HIERARCHY_1: data |= 0x01; break; + case DVB_HIERARCHY_2: data |= 0x02; break; + case DVB_HIERARCHY_4: data |= 0x03; break; + default: return B_ERROR; + } + if (cx22702_reg_write(bus, 0x06, data) != B_OK) + return B_ERROR; + + switch (params->code_rate_hp) { + case DVB_FEC_NONE: data = 0x00; break; + case DVB_FEC_1_2: data = 0x00; break; + case DVB_FEC_2_3: data = 0x08; break; + case DVB_FEC_3_4: data = 0x10; break; + case DVB_FEC_5_6: data = 0x18; break; + case DVB_FEC_6_7: data = 0x20; break; + default: return B_ERROR; + } + switch (params->code_rate_lp) { + case DVB_FEC_NONE: break; + case DVB_FEC_1_2: break; + case DVB_FEC_2_3: data |= 0x01; break; + case DVB_FEC_3_4: data |= 0x02; break; + case DVB_FEC_5_6: data |= 0x03; break; + case DVB_FEC_6_7: data |= 0x04; break; + default: return B_ERROR; + } + if (cx22702_reg_write(bus, 0x07, data) != B_OK) + return B_ERROR; + + switch (params->transmission_mode) { + case DVB_TRANSMISSION_MODE_2K: data = 0x00; break; + case DVB_TRANSMISSION_MODE_8K: data = 0x01; break; + default: return B_ERROR; + } + switch (params->guard_interval) { + case DVB_GUARD_INTERVAL_1_4: data |= 0x0c; break; + case DVB_GUARD_INTERVAL_1_8: data |= 0x08; break; + case DVB_GUARD_INTERVAL_1_16: data |= 0x04; break; + case DVB_GUARD_INTERVAL_1_32: break; + default: return B_ERROR; + } + if (cx22702_reg_write(bus, 0x08, data) != B_OK) + return B_ERROR; + + if (cx22702_reg_read(bus, 0x0b, &data) != B_OK) + return B_ERROR; + if (cx22702_reg_write(bus, 0x0b, data | 0x02) != B_OK) + return B_ERROR; + + if (cx22702_reg_write(bus, 0x00, 0x01) != B_OK) + return B_ERROR; + +// cx22702_reg_dump(bus); + + return B_OK; +} + + +status_t +cx22702_get_tuning_parameters(i2c_bus *bus, dvb_t_tuning_parameters_t *params) +{ + uint8 reg01, reg02, reg03, reg0A, reg0C; + + if (cx22702_reg_read(bus, 0x01, ®01) != B_OK) + return B_ERROR; + if (cx22702_reg_read(bus, 0x02, ®02) != B_OK) + return B_ERROR; + if (cx22702_reg_read(bus, 0x03, ®03) != B_OK) + return B_ERROR; + if (cx22702_reg_read(bus, 0x0a, ®0A) != B_OK) + return B_ERROR; + if (cx22702_reg_read(bus, 0x0c, ®0C) != B_OK) + return B_ERROR; + + memset(params, 0, sizeof(*params)); + params->inversion = (reg0C & 0x01) ? DVB_INVERSION_ON : DVB_INVERSION_OFF; + + // XXX TODO... + + return B_OK; +} + + +status_t +cx22702_get_status(i2c_bus *bus, dvb_status_t *status) +{ + uint8 reg0A, reg23; + + if (cx22702_reg_read(bus, 0x0a, ®0A) != B_OK) + return B_ERROR; + if (cx22702_reg_read(bus, 0x23, ®23) != B_OK) + return B_ERROR; + + *status = 0; + if (reg0A & 0x10) + *status |= DVB_STATUS_LOCK | DVB_STATUS_VITERBI | DVB_STATUS_SYNC; + if (reg0A & 0x20) + *status |= DVB_STATUS_CARRIER; + if (reg23 < 0xf0) + *status |= DVB_STATUS_SIGNAL; + + return B_OK; +} + + +status_t +cx22702_get_ss(i2c_bus *bus, uint32 *ss) +{ + uint8 reg23; + if (cx22702_reg_read(bus, 0x23, ®23) != B_OK) + return B_ERROR; + *ss = reg23; + return B_OK; +} + + +status_t +cx22702_get_ber(i2c_bus *bus, uint32 *ber) +{ + uint8 regDE_1, regDE_2, regDF; + int trys; + + trys = 50; + do { + if (cx22702_reg_read(bus, 0xDE, ®DE_1) != B_OK) + return B_ERROR; + if (cx22702_reg_read(bus, 0xDF, ®DF) != B_OK) + return B_ERROR; + if (cx22702_reg_read(bus, 0xDE, ®DE_2) != B_OK) + return B_ERROR; + } while (regDE_1 != regDE_2 && --trys > 0); + if (trys == 0) + return B_ERROR; + + *ber = (regDE_1 & 0x7f) << 7 | (regDF & 0x7f); + + return B_OK; +} + + +status_t +cx22702_get_snr(i2c_bus *bus, uint32 *snr) +{ + uint32 ber; + status_t stat = cx22702_get_ber(bus, &ber); + *snr = 16384 - ber; + return stat; +} + + +status_t +cx22702_get_upc(i2c_bus *bus, uint32 *upc) +{ + uint8 regE3; + + if (cx22702_reg_read(bus, 0xE3, ®E3) != B_OK) + return B_ERROR; + if (cx22702_reg_write(bus, 0xE3, 0) != B_OK) + return B_ERROR; + *upc = regE3; + return B_OK; +} Added: haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/cx22702.h =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/cx22702.h 2007-04-13 15:52:58 UTC (rev 20677) +++ haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/cx22702.h 2007-04-13 16:21:17 UTC (rev 20678) @@ -0,0 +1,47 @@ +/* + * Copyright (c) 2004-2007 Marcus Overhagen + * + * Permission is hereby granted, free of charge, to any person + * obtaining a copy of this software and associated documentation + * files (the "Software"), to deal in the Software without restriction, + * including without limitation the rights to use, copy, modify, + * merge, publish, distribute, sublicense, and/or sell copies of + * the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be + * included in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES + * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT + * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, + * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + */ + +#ifndef __CX22702_H +#define __CX22702_H + +#include "i2c-core.h" +#include "dvb.h" + +status_t cx22702_reg_write(i2c_bus *bus, uint8 reg, uint8 data); +status_t cx22702_reg_read(i2c_bus *bus, uint8 reg, uint8 *data); + +status_t cx22702_init(i2c_bus *bus); + +status_t cx22702_get_frequency_info(i2c_bus *bus, dvb_frequency_info_t *info); + +status_t cx22702_set_tuning_parameters(i2c_bus *bus, const dvb_t_tuning_parameters_t *params); +status_t cx22702_get_tuning_parameters(i2c_bus *bus, dvb_t_tuning_parameters_t *params); + +status_t cx22702_get_status(i2c_bus *bus, dvb_status_t *status); +status_t cx22702_get_ss(i2c_bus *bus, uint32 *ss); +status_t cx22702_get_ber(i2c_bus *bus, uint32 *ber); +status_t cx22702_get_snr(i2c_bus *bus, uint32 *snr); +status_t cx22702_get_upc(i2c_bus *bus, uint32 *upc); + +#endif Added: haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/cx23882.c =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/cx23882.c 2007-04-13 15:52:58 UTC (rev 20677) +++ haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/cx23882.c 2007-04-13 16:21:17 UTC (rev 20678) @@ -0,0 +1,377 @@ +/* + * Copyright (c) 2004-2007 Marcus Overhagen + * + * Permission is hereby granted, free of charge, to any person + * obtaining a copy of this software and associated documentation + * files (the "Software"), to deal in the Software without restriction, + * including without limitation the rights to use, copy, modify, + * merge, publish, distribute, sublicense, and/or sell copies of + * the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be + * included in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES + * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT + * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, + * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + */ + +#include "cx23882.h" +#include "util.h" +#include +#include +#include + + +#define TRACE_CX23882 +#ifdef TRACE_CX23882 + #define TRACE dprintf +#else + #define TRACE(a...) +#endif + +// settings for hardware stream sync +#define MPEG2_SYNC_BYTE 0x47 +#define MPEG2_PACKET_SIZE 188 +#define SYNC_PACKET_COUNT 7 // 0 and 5 don't seem to work + +// Line size is also used as FIFO size! +// BYTES_PER_LINE must be a multiple of 8 and <= 4096 bytes +#define PACKETS_PER_LINE 20 +#define BYTES_PER_LINE (PACKETS_PER_LINE * MPEG2_PACKET_SIZE) + +#define SRAM_START_ADDRESS 0x180000 +#define SRAM_BASE_CMDS_TS 0x200 +#define SRAM_BASE_RISC_PROG 0x400 +#define SRAM_BASE_RISC_QUEUE 0x800 +#define SRAM_BASE_CDT 0x900 +#define SRAM_BASE_FIFO_0 0x1000 +#define SRAM_BASE_FIFO_1 0x2000 + +// About 64 kByte DMA buffer size +#define LINES_PER_BUFFER 16 +#define DMA_BUFFER_SIZE (LINES_PER_BUFFER * BYTES_PER_LINE) + + +static status_t cx23882_buffers_alloc(cx23882_device *device); +static void cx23882_buffers_free(cx23882_device *device); +static void cx23882_risc_ram_setup(cx23882_device *device); +static void cx23882_sram_setup(cx23882_device *device); +static void cx23882_via_sis_fixup(cx23882_device *device); + + +void +cx23882_reset(cx23882_device *device) +{ + // software reset (XXX Test) + reg_write32(0x38c06c, 1); + snooze(200000); + + // disable RISC controller + reg_write32(REG_DEV_CNTRL2, 0); + + // disable TS interface DMA + reg_write32(REG_TS_DMA_CNTRL, 0x0); + + // disable VIP interface up- & downstram DMA + reg_write32(REG_VIP_STREAM_EN, 0x0); + + // disable host interface up- & downstram DMA + reg_write32(REG_HST_STREAM_EN, 0x0); + + // stop all interrupts + reg_write32(REG_PCI_INT_MSK, 0x0); + reg_write32(REG_VID_INT_MSK, 0x0); + reg_write32(REG_AUD_INT_MSK, 0x0); + reg_write32(REG_TS_INT_MSK, 0x0); + reg_write32(REG_VIP_INT_MSK, 0x0); + reg_write32(REG_HST_INT_MSK, 0x0); + reg_write32(REG_DMA_RISC_INT_MSK, 0x0); + + // clear all pending interrupts + reg_write32(REG_PCI_INT_STAT, 0xffffffff); + reg_write32(REG_VID_INT_STAT, 0xffffffff); + reg_write32(REG_AUD_INT_STAT, 0xffffffff); + reg_write32(REG_TS_INT_STAT, 0xffffffff); + reg_write32(REG_VIP_INT_STAT, 0xffffffff); + reg_write32(REG_HST_INT_STAT, 0xffffffff); + reg_write32(REG_DMA_RISC_INT_MSK, 0xffffffff); +} + + +status_t +cx23882_init(cx23882_device *device) +{ + // assumes that cx23882_reset() has already been called + + status_t err; + + if ((err = cx23882_buffers_alloc(device)) < B_OK) { + dprintf("cx23882: Error, buffer alloc failed\n"); + return err; + } + + device->capture_size = DMA_BUFFER_SIZE; + + cx23882_via_sis_fixup(device); + + // Set FIFO thresholds, should be 0 < x <= 7 + reg_write32(REG_PDMA_STHRSH, PDMA_ISBTHRSH_6 | PDMA_PCITHRSH_6); + reg_write32(REG_PDMA_DTHRSH, PDMA_ISBTHRSH_6 | PDMA_PCITHRSH_6); + + // init risc programm + cx23882_risc_ram_setup(device); + + // init sram + cx23882_sram_setup(device); + + // Reset counter to 0 + reg_write32(REG_TS_GP_CNT_CNTRL, 0x3); + + // Line length for RISC DMA + reg_write32(REG_TS_LNGTH, BYTES_PER_LINE); + + // Set serial interface mode + reg_write32(REG_TS_GEN_CONTROL, reg_read32(REG_TS_GEN_CONTROL) | TS_GEN_CONTROL_IPB_SMODE); + + // Setup hardware MPEG2 fec interface + reg_write32(REG_HW_SOP_CONTROL, (MPEG2_SYNC_BYTE << 16) | (MPEG2_PACKET_SIZE << 4) | SYNC_PACKET_COUNT); + + // Setup TSSTOP status, active low, rising and falling edge, single bit width + reg_write32(REG_TS_SOP_STATUS, reg_read32(REG_TS_SOP_STATUS) | 0x18000); + reg_write32(REG_TS_SOP_STATUS, reg_read32(REG_TS_SOP_STATUS) & ~0x06000); + + // Enable interrupts for MPEG TS and all errors + reg_write32(REG_PCI_INT_MSK, reg_read32(REG_PCI_INT_MSK) | PCI_INT_STAT_TS_INT | 0x00fc00); + reg_write32(REG_TS_INT_MSK, reg_read32(REG_TS_INT_MSK) | TS_INT_STAT_TS_RISC1 | TS_INT_STAT_TS_RISC2 | 0x1f1100); + + TRACE("cx23882_init done\n"); + return B_OK; +} + + +status_t +cx23882_terminate(cx23882_device *device) +{ + cx23882_reset(device); + + cx23882_buffers_free(device); + return B_OK; +} + + +status_t +cx23882_start_capture(cx23882_device *device) +{ + TRACE("cx23882_start_capture\n"); + + // start RISC processor and DMA + reg_write32(REG_DEV_CNTRL2, reg_read32(REG_DEV_CNTRL2) | DEV_CNTRL2_RUN_RISC); + reg_write32(REG_TS_DMA_CNTRL, reg_read32(REG_TS_DMA_CNTRL) | TS_DMA_CNTRL_TS_FIFO_EN | TS_DMA_CNTRL_TS_RISC_EN); + return B_OK; +} + + +status_t +cx23882_stop_capture(cx23882_device *device) +{ + TRACE("cx23882_stop_capture\n"); + + // stop RISC processor and DMA + reg_write32(REG_TS_DMA_CNTRL, reg_read32(REG_TS_DMA_CNTRL) & ~(TS_DMA_CNTRL_TS_FIFO_EN | TS_DMA_CNTRL_TS_RISC_EN)); + reg_write32(REG_DEV_CNTRL2, reg_read32(REG_DEV_CNTRL2) & ~DEV_CNTRL2_RUN_RISC); + return B_OK; +} + + +static inline void +cx23882_mpegts_int(cx23882_device *device) +{ + uint32 mstat = reg_read32(REG_TS_INT_MSTAT); + reg_write32(REG_TS_INT_STAT, mstat); + +// dprintf("cx23882_mpegts_int got 0x%08lx\n", mstat); + + if (mstat & TS_INT_STAT_OPC_ERR) { + dprintf("cx23882_mpegts_int RISC opcode error\n"); + reg_write32(REG_PCI_INT_MSK, 0); + return; + } + + if ((mstat & (TS_INT_STAT_TS_RISC1 | TS_INT_STAT_TS_RISC2)) == (TS_INT_STAT_TS_RISC1 | TS_INT_STAT_TS_RISC2)) { + dprintf("cx23882_mpegts_int both buffers ready\n"); + mstat = TS_INT_STAT_TS_RISC1; + } + + if (mstat & TS_INT_STAT_TS_RISC1) { + int32 count; +// dprintf("cx23882_mpegts_int buffer 1 at %Ld\n", system_time()); + device->capture_data = device->dma_buf1_virt; + device->capture_end_time = system_time(); + get_sem_count(device->capture_sem, &count); + if (count <= 0) + release_sem_etc(device->capture_sem, 1, B_DO_NOT_RESCHEDULE); + } + + if (mstat & TS_INT_STAT_TS_RISC2) { + int32 count; +// dprintf("cx23882_mpegts_int buffer 2 at %Ld\n", system_time()); + device->capture_data = device->dma_buf2_virt; + device->capture_end_time = system_time(); + get_sem_count(device->capture_sem, &count); + if (count <= 0) + release_sem_etc(device->capture_sem, 1, B_DO_NOT_RESCHEDULE); + } +} + + +int32 +cx23882_int(void *data) +{ + cx23882_device *device = data; + uint32 mstat; + uint32 wmstat; + + mstat = reg_read32(REG_PCI_INT_MSTAT); + if (!mstat) + return B_UNHANDLED_INTERRUPT; + + if (mstat & (PCI_INT_STAT_HST_INT | PCI_INT_STAT_VIP_INT | PCI_INT_STAT_AUD_INT | PCI_INT_STAT_VID_INT)) { + // serious error, these bits should not be set + dprintf("cx23882_int error: msk 0x%08lx, stat 0x%08lx, mstat 0x%08lx\n", reg_read32(REG_PCI_INT_MSK), reg_read32(REG_PCI_INT_STAT), mstat); + reg_write32(REG_PCI_INT_MSK, 0); + return B_HANDLED_INTERRUPT; + } + + wmstat = mstat & ~(PCI_INT_STAT_HST_INT | PCI_INT_STAT_VIP_INT | PCI_INT_STAT_TS_INT | PCI_INT_STAT_AUD_INT | PCI_INT_STAT_VID_INT); + if (wmstat) + reg_write32(REG_PCI_INT_STAT, wmstat); + + if (wmstat) + dprintf("cx23882_int got 0x%08lx\n", wmstat); + + if (mstat & PCI_INT_STAT_TS_INT) { + cx23882_mpegts_int(device); + return B_INVOKE_SCHEDULER; + } else { + return B_HANDLED_INTERRUPT; + } +} + + +static status_t +cx23882_buffers_alloc(cx23882_device *device) +{ + device->dma_buf1_area = alloc_mem(&device->dma_buf1_virt, &device->dma_buf1_phys, DMA_BUFFER_SIZE, B_READ_AREA, "cx23882 dma buf 1"); + device->dma_buf2_area = alloc_mem(&device->dma_buf2_virt, &device->dma_buf2_phys, DMA_BUFFER_SIZE, B_READ_AREA, "cx23882 dma buf 2"); + if (device->dma_buf1_area < B_OK || device->dma_buf2_area < B_OK) { + cx23882_buffers_free(device); + return B_NO_MEMORY; + } + return B_OK; +} + + +static void +cx23882_buffers_free(cx23882_device *device) +{ + if (device->dma_buf1_area >= 0) + delete_area(device->dma_buf1_area); + if (device->dma_buf2_area >= 0) + delete_area(device->dma_buf2_area); + device->dma_buf1_area = -1; + device->dma_buf2_area = -1; +} + + +static void +cx23882_sram_setup(cx23882_device *device) +{ + dprintf("cx23882_sram_setup enter\n"); + + // setup CDT entries for both FIFOs + reg_write32(SRAM_START_ADDRESS + SRAM_BASE_CDT, SRAM_START_ADDRESS + SRAM_BASE_FIFO_0); + reg_write32(SRAM_START_ADDRESS + SRAM_BASE_CDT + 16, SRAM_START_ADDRESS + SRAM_BASE_FIFO_1); + + // setup CDMS + reg_write32(SRAM_START_ADDRESS + SRAM_BASE_CMDS_TS + 0x00, SRAM_START_ADDRESS + SRAM_BASE_RISC_PROG); + reg_write32(SRAM_START_ADDRESS + SRAM_BASE_CMDS_TS + 0x04, SRAM_START_ADDRESS + SRAM_BASE_CDT); + reg_write32(SRAM_START_ADDRESS + SRAM_BASE_CMDS_TS + 0x08, (2 * 16) / 8); // FIFO count = 2 + reg_write32(SRAM_START_ADDRESS + SRAM_BASE_CMDS_TS + 0x0c, SRAM_START_ADDRESS + SRAM_BASE_RISC_QUEUE); + reg_write32(SRAM_START_ADDRESS + SRAM_BASE_CMDS_TS + 0x10, 0x80000000 | (0x100 / 4)); + + // setup DMA registers + reg_write32(REG_DMA28_PTR1, SRAM_START_ADDRESS + SRAM_BASE_FIFO_0); + reg_write32(REG_DMA28_PTR2, SRAM_START_ADDRESS + SRAM_BASE_CDT); + reg_write32(REG_DMA28_CNT1, BYTES_PER_LINE / 8); + reg_write32(REG_DMA28_CNT2, (2 * 16) / 8); // FIFO count = 2 + + dprintf("cx23882_sram_setup leave\n"); +} + + +static void +cx23882_risc_ram_setup(cx23882_device *device) +{ + char *start = (char *)(device->regs) + SRAM_START_ADDRESS + SRAM_BASE_RISC_PROG; + volatile uint32 *rp = (volatile uint32 *)start; + int i; + + #define set_opcode(a) (*rp++) = B_HOST_TO_LENDIAN_INT32((a)) + + dprintf("cx23882_risc_ram_setup enter\n"); + + // sync + set_opcode(RISC_RESYNC | 0); + + // copy buffer 1 + for (i = 0; i < LINES_PER_BUFFER; i++) { + set_opcode(RISC_WRITE | RISC_SOL | RISC_EOL | BYTES_PER_LINE); + set_opcode((unsigned long)device->dma_buf1_phys + i * BYTES_PER_LINE); + } + + // execute IRQ 1 + set_opcode(RISC_SKIP | RISC_IRQ1 | RISC_SOL | 0); + + // copy buffer 2 + for (i = 0; i < LINES_PER_BUFFER; i++) { + set_opcode(RISC_WRITE | RISC_SOL | RISC_EOL | BYTES_PER_LINE); + set_opcode((unsigned long)device->dma_buf2_phys + i * BYTES_PER_LINE); + } + + // execute IRQ 2 + set_opcode(RISC_SKIP | RISC_IRQ2 | RISC_SOL | 0); + + // jmp to start, but skip sync instruction + set_opcode(RISC_JUMP | RISC_SRP); + set_opcode(SRAM_START_ADDRESS + SRAM_BASE_RISC_PROG + 4); + + #undef set_opcode + + dprintf("cx23882_risc_ram_setup leave\n"); +} + + +static void +cx23882_via_sis_fixup(cx23882_device *device) +{ + uint16 host_vendor; + uint32 dev_cntrl1; + + host_vendor = gPci->read_pci_config(0, 0, 0, PCI_vendor_id, 2); + dev_cntrl1 = reg_read32(REG_F2_DEV_CNTRL1); + + if (host_vendor == PCI_VENDOR_VIA || host_vendor == PCI_VENDOR_SIS) { + dprintf("cx23882: enabling VIA/SIS compatibility mode\n"); + reg_write32(REG_F2_DEV_CNTRL1, dev_cntrl1 | F2_DEV_CNTRL1_EN_VSFX); + } else { + dprintf("cx23882: disabling VIA/SIS compatibility mode\n"); + reg_write32(REG_F2_DEV_CNTRL1, dev_cntrl1 & ~F2_DEV_CNTRL1_EN_VSFX); + } +} Added: haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/cx23882.h =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/cx23882.h 2007-04-13 15:52:58 UTC (rev 20677) +++ haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/cx23882.h 2007-04-13 16:21:17 UTC (rev 20678) @@ -0,0 +1,72 @@ +/* + * Copyright (c) 2004-2007 Marcus Overhagen + * + * Permission is hereby granted, free of charge, to any person + * obtaining a copy of this software and associated documentation + * files (the "Software"), to deal in the Software without restriction, + * including without limitation the rights to use, copy, modify, + * merge, publish, distribute, sublicense, and/or sell copies of + * the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be + * included in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES + * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT + * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, + * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + */ + +#ifndef __CX23882_H +#define __CX23882_H + +#include +#include "driver.h" +#include "cx23882_regs.h" +#include "i2c-core.h" + +typedef struct { + const pci_info * pci_info; + int irq; + void * regs; + area_id regs_area; + uint32 i2c_reg; + i2c_bus * i2c_bus; + + area_id dma_buf1_area; + void * dma_buf1_virt; + void * dma_buf1_phys; + area_id dma_buf2_area; + void * dma_buf2_virt; + void * dma_buf2_phys; + + sem_id capture_sem; + void * capture_data; + size_t capture_size; + bigtime_t capture_end_time; +} cx23882_device; + + +#define reg_read8(offset) (*(volatile uint8 *) ((char *)(device->regs) + (offset))) +#define reg_read16(offset) (*(volatile uint16 *)((char *)(device->regs) + (offset))) +#define reg_read32(offset) (*(volatile uint32 *)((char *)(device->regs) + (offset))) +#define reg_write8(offset, value) (*(volatile uint8 *) ((char *)(device->regs) + (offset)) = value) +#define reg_write16(offset, value) (*(volatile uint16 *)((char *)(device->regs) + (offset)) = value) +#define reg_write32(offset, value) (*(volatile uint32 *)((char *)(device->regs) + (offset)) = value) + + +void cx23882_reset(cx23882_device *device); +status_t cx23882_init(cx23882_device *device); +status_t cx23882_terminate(cx23882_device *device); + +status_t cx23882_start_capture(cx23882_device *device); +status_t cx23882_stop_capture(cx23882_device *device); + +int32 cx23882_int(void *data); + +#endif Added: haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/cx23882_i2c.c =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/cx23882_i2c.c 2007-04-13 15:52:58 UTC (rev 20677) +++ haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/cx23882_i2c.c 2007-04-13 16:21:17 UTC (rev 20678) @@ -0,0 +1,90 @@ +/* + * Copyright (c) 2004-2007 Marcus Overhagen + * + * Permission is hereby granted, free of charge, to any person + * obtaining a copy of this software and associated documentation + * files (the "Software"), to deal in the Software without restriction, + * including without limitation the rights to use, copy, modify, + * merge, publish, distribute, sublicense, and/or sell copies of + * the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be + * included in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES + * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT + * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, + * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + */ + +#include "i2c.h" +#include "i2c-core.h" + + +static void +set_scl(void *cookie, int state) +{ + cx23882_device * device = cookie; + if (state) + device->i2c_reg |= I2C_SCL; + else + device->i2c_reg &= ~I2C_SCL; + reg_write32(REG_I2C_CONTROL, device->i2c_reg); + reg_read32(REG_I2C_CONTROL); // PCI bridge flush +} + + +static void +set_sda(void *cookie, int state) +{ + cx23882_device * device = cookie; + if (state) + device->i2c_reg |= I2C_SDA; + else + device->i2c_reg &= ~I2C_SDA; + reg_write32(REG_I2C_CONTROL, device->i2c_reg); + reg_read32(REG_I2C_CONTROL); // PCI bridge flush +} + + +static int +get_scl(void *cookie) +{ + cx23882_device * device = cookie; + return (reg_read32(REG_I2C_CONTROL) & I2C_SCL) >> 1; // I2C_SCL is 0x02 +} + + +static int +get_sda(void *cookie) +{ + cx23882_device * device = cookie; + return reg_read32(REG_I2C_CONTROL) & I2C_SDA; // I2C_SDA is 0x01 +} + + +status_t +i2c_init(cx23882_device *device) +{ + device->i2c_bus = i2c_create_bus(device, 80000, 2000000, set_scl, set_sda, get_scl, get_sda); + device->i2c_reg = reg_read32(REG_I2C_CONTROL); + device->i2c_reg &= ~I2C_HW_MODE; + device->i2c_reg |= I2C_SCL | I2C_SDA; + reg_write32(REG_I2C_CONTROL, device->i2c_reg); + reg_read32(REG_I2C_CONTROL); // PCI bridge flush + return device->i2c_bus ? B_OK : B_ERROR; +} + + +void +i2c_terminate(cx23882_device *device) +{ + i2c_delete_bus(device->i2c_bus); +} + + Added: haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/cx23882_i2c.h =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/cx23882_i2c.h 2007-04-13 15:52:58 UTC (rev 20677) +++ haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/cx23882_i2c.h 2007-04-13 16:21:17 UTC (rev 20678) @@ -0,0 +1,33 @@ +/* + * Copyright (c) 2004-2007 Marcus Overhagen + * + * Permission is hereby granted, free of charge, to any person + * obtaining a copy of this software and associated documentation + * files (the "Software"), to deal in the Software without restriction, + * including without limitation the rights to use, copy, modify, + * merge, publish, distribute, sublicense, and/or sell copies of + * the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be + * included in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES + * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT + * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, + * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + */ + +#ifndef __I2C_H +#define __I2C_H [... truncated: 1692 lines follow ...] From jackburton at mail.berlios.de Fri Apr 13 18:35:56 2007 From: jackburton at mail.berlios.de (jackburton at BerliOS) Date: Fri, 13 Apr 2007 18:35:56 +0200 Subject: [Haiku-commits] r20679 - haiku/trunk/src/apps/terminal Message-ID: <200704131635.l3DGZuA0032018@sheep.berlios.de> Author: jackburton Date: 2007-04-13 18:35:50 +0200 (Fri, 13 Apr 2007) New Revision: 20679 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20679&view=rev Added: haiku/trunk/src/apps/terminal/FindWindow.cpp haiku/trunk/src/apps/terminal/FindWindow.h haiku/trunk/src/apps/terminal/PrefWindow.cpp haiku/trunk/src/apps/terminal/PrefWindow.h Removed: haiku/trunk/src/apps/terminal/FindDlg.cpp haiku/trunk/src/apps/terminal/FindDlg.h haiku/trunk/src/apps/terminal/PrefDlg.cpp haiku/trunk/src/apps/terminal/PrefDlg.h Modified: haiku/trunk/src/apps/terminal/Jamfile haiku/trunk/src/apps/terminal/TermWindow.cpp Log: Renamed *Dlg to *Window, since the term "Dialog" is alien to the beos api. Thanks to Vasilis Kaoutsis for the suggestion. I'll rename the classes with the next commit. Deleted: haiku/trunk/src/apps/terminal/FindDlg.cpp Deleted: haiku/trunk/src/apps/terminal/FindDlg.h Copied: haiku/trunk/src/apps/terminal/FindWindow.cpp (from rev 20662, haiku/trunk/src/apps/terminal/FindDlg.cpp) =================================================================== --- haiku/trunk/src/apps/terminal/FindDlg.cpp 2007-04-12 12:28:13 UTC (rev 20662) +++ haiku/trunk/src/apps/terminal/FindWindow.cpp 2007-04-13 16:35:50 UTC (rev 20679) @@ -0,0 +1,167 @@ +/* + * Copyright 2007, Haiku, Inc. + * Copyright 2003-2004 Kian Duffy, myob at users.sourceforge.net + * Parts Copyright 1998-1999 Kazuho Okui and Takashi Murai. + * All rights reserved. Distributed under the terms of the MIT license. + */ + + +#include "FindWindow.h" + +#include +#include +#include +#include +#include +#include + + +const uint32 MSG_FIND_HIDE = 'Fhid'; + + +FindDlg::FindDlg (BRect frame, BMessenger messenger , BString &str, + bool findSelection, bool matchWord, bool matchCase, bool forwardSearch) + : BWindow(frame, "Find", B_FLOATING_WINDOW, B_NOT_RESIZABLE|B_NOT_ZOOMABLE), + fFindDlgMessenger(messenger) +{ + AddShortcut((ulong)'W', (ulong)B_COMMAND_KEY, new BMessage(MSG_FIND_HIDE)); + + //Build up view + fFindView = new BView(Bounds(), "FindView", B_FOLLOW_ALL, B_WILL_DRAW); + fFindView->SetViewColor(ui_color(B_PANEL_BACKGROUND_COLOR)); + AddChild(fFindView); + + font_height height; + fFindView->GetFontHeight(&height); + float lineHeight = height.ascent + height.descent + height.leading; + + //These labels are from the bottom up + float buttonsTop = frame.Height() - 19 - lineHeight; + float matchWordBottom = buttonsTop - 4; + float matchWordTop = matchWordBottom - lineHeight - 8; + float matchCaseBottom = matchWordTop - 4; + float matchCaseTop = matchCaseBottom - lineHeight - 8; + float forwardSearchBottom = matchCaseTop - 4; + float forwardSearchTop = forwardSearchBottom - lineHeight - 8; + + //These things are calculated from the top + float textRadioTop = 12; + float textRadioBottom = textRadioTop + 2 + lineHeight + 2 + 1; + float textRadioRight = fFindView->StringWidth("Use Text: ") + 30; + float selectionRadioTop = textRadioBottom + 4; + float selectionRadioBottom = selectionRadioTop + lineHeight + 8; + + //Divider + float dividerHeight = (selectionRadioBottom + forwardSearchTop) / 2; + + //Button Coordinates + float searchButtonLeft = (frame.Width() - fFindView->StringWidth("Find") - 60) / 2; + float searchButtonRight = searchButtonLeft + fFindView->StringWidth("Find") + 60; + + //Build the Views + fTextRadio = new BRadioButton(BRect(14, textRadioTop, textRadioRight, textRadioBottom), + "fTextRadio", "Use Text: ", NULL); + fFindView->AddChild(fTextRadio); + + fFindLabel = new BTextControl(BRect(textRadioRight + 4, textRadioTop, frame.Width() - 14, textRadioBottom), + "fFindLabel", "", "", NULL); + fFindLabel->SetDivider(0); + fFindView->AddChild(fFindLabel); + if (!findSelection) + fFindLabel->SetText(str.String()); + fFindLabel->MakeFocus(true); + + fSelectionRadio = new BRadioButton(BRect(14, selectionRadioTop, frame.Width() - 14, selectionRadioBottom), + "fSelectionRadio", "Use Selection", NULL); + fFindView->AddChild(fSelectionRadio); + + if (findSelection) + fSelectionRadio->SetValue(B_CONTROL_ON); + else + fTextRadio->SetValue(B_CONTROL_ON); + + fSeparator = new BBox(BRect(6, dividerHeight, frame.Width() - 6, dividerHeight + 1)); + fFindView->AddChild(fSeparator); + + fForwardSearchBox = new BCheckBox(BRect(14, forwardSearchTop, frame.Width() - 14, forwardSearchBottom), + "fForwardSearchBox", "Search Forward", NULL); + fFindView->AddChild(fForwardSearchBox); + if (forwardSearch) + fForwardSearchBox->SetValue(B_CONTROL_ON); + + fMatchCaseBox = new BCheckBox(BRect(14, matchCaseTop, frame.Width() - 14, matchCaseBottom), + "fMatchCaseBox", "Match Case", NULL); + fFindView->AddChild(fMatchCaseBox); + if (matchCase) + fMatchCaseBox->SetValue(B_CONTROL_ON); + + fMatchWordBox = new BCheckBox(BRect(14, matchWordTop, frame.Width() - 14, matchWordBottom), + "fMatchWordBox", "Match Word", NULL); + fFindView->AddChild(fMatchWordBox); + if (matchWord) + fMatchWordBox->SetValue(B_CONTROL_ON); + + fFindButton = new BButton(BRect(searchButtonLeft, buttonsTop, searchButtonRight, frame.Height() - 14), + "fFindButton", "Find", new BMessage(MSG_FIND)); + fFindButton->MakeDefault(true); + fFindView->AddChild(fFindButton); + + Show(); +} + + +FindDlg::~FindDlg() +{ +} + + +void +FindDlg::MessageReceived(BMessage *msg) +{ + switch (msg->what) { + case B_QUIT_REQUESTED: + Quit(); + break; + + case MSG_FIND: + _SendFindMessage(); + break; + + case MSG_FIND_HIDE: + Quit(); + break; + + default: + BWindow::MessageReceived(msg); + break; + } +} + + +void +FindDlg::Quit() +{ + fFindDlgMessenger.SendMessage(MSG_FIND_CLOSED); + BWindow::Quit(); +} + + +void +FindDlg::_SendFindMessage() +{ + BMessage message(MSG_FIND); + + if (fTextRadio->Value() == B_CONTROL_ON) { + message.AddString("findstring", fFindLabel->Text()); + message.AddBool("findselection", false); + } else + message.AddBool("findselection", true); + + //Add the other parameters + message.AddBool("usetext", fTextRadio->Value() == B_CONTROL_ON); + message.AddBool("forwardsearch", fForwardSearchBox->Value() == B_CONTROL_ON); + message.AddBool("matchcase", fMatchCaseBox->Value() == B_CONTROL_ON); + message.AddBool("matchword", fMatchWordBox->Value() == B_CONTROL_ON); + + fFindDlgMessenger.SendMessage(&message); +} Copied: haiku/trunk/src/apps/terminal/FindWindow.h (from rev 20662, haiku/trunk/src/apps/terminal/FindDlg.h) Modified: haiku/trunk/src/apps/terminal/Jamfile =================================================================== --- haiku/trunk/src/apps/terminal/Jamfile 2007-04-13 16:21:17 UTC (rev 20678) +++ haiku/trunk/src/apps/terminal/Jamfile 2007-04-13 16:35:50 UTC (rev 20679) @@ -9,12 +9,12 @@ AppearPrefView.cpp CodeConv.cpp CurPos.cpp - FindDlg.cpp + FindWindow.cpp MenuUtil.cpp Terminal.cpp - PrefDlg.cpp PrefHandler.cpp PrefView.cpp + PrefWindow.cpp spawn.cpp TermApp.cpp TermBaseView.cpp Deleted: haiku/trunk/src/apps/terminal/PrefDlg.cpp Deleted: haiku/trunk/src/apps/terminal/PrefDlg.h Copied: haiku/trunk/src/apps/terminal/PrefWindow.cpp (from rev 20662, haiku/trunk/src/apps/terminal/PrefDlg.cpp) =================================================================== --- haiku/trunk/src/apps/terminal/PrefDlg.cpp 2007-04-12 12:28:13 UTC (rev 20662) +++ haiku/trunk/src/apps/terminal/PrefWindow.cpp 2007-04-13 16:35:50 UTC (rev 20679) @@ -0,0 +1,221 @@ +/* + * Copyright 2007, Haiku, Inc. + * Copyright 2003-2004 Kian Duffy, myob at users.sourceforge.net + * Parts Copyright 1998-1999 Kazuho Okui and Takashi Murai. + * All rights reserved. Distributed under the terms of the MIT license. + */ + + +#include "AppearPrefView.h" +#include "MenuUtil.h" +#include "PrefHandler.h" +#include "PrefWindow.h" +#include "PrefView.h" +#include "spawn.h" +#include "TermConst.h" + +#include +#include +#include +#include +#include +#include + +#include + + +extern PrefHandler *gTermPref; + // Global Preference Handler + +PrefDlg::PrefDlg(BMessenger messenger) + : BWindow(_CenteredRect(BRect(0, 0, 350, 215)), "Terminal Settings", + B_TITLED_WINDOW_LOOK, B_NORMAL_WINDOW_FEEL, + B_NOT_RESIZABLE|B_NOT_ZOOMABLE), + fPrefTemp(new PrefHandler(gTermPref)), + fSavePanel(NULL), + fDirty(false), + fPrefDlgMessenger(messenger) +{ + BRect rect; + + BView *top = new BView(Bounds(), "topview", B_FOLLOW_NONE, B_WILL_DRAW); + top->SetViewColor(ui_color(B_PANEL_BACKGROUND_COLOR)); + AddChild(top); + + rect = top->Bounds(); + rect.bottom *= .75; + AppearancePrefView *prefView= new AppearancePrefView(rect, "Appearance", + fPrefDlgMessenger); + top->AddChild(prefView); + + fSaveAsFileButton = new BButton(BRect(0, 0, 1, 1), "savebutton", "Save to File", + new BMessage(MSG_SAVEAS_PRESSED), B_FOLLOW_TOP, B_WILL_DRAW); + fSaveAsFileButton->ResizeToPreferred(); + fSaveAsFileButton->MoveTo(5, top->Bounds().Height() - 5 - + fSaveAsFileButton->Bounds().Height()); + top->AddChild(fSaveAsFileButton); + + fSaveButton = new BButton(BRect(0, 0, 1, 1), "okbutton", "OK", + new BMessage(MSG_SAVE_PRESSED), B_FOLLOW_TOP, B_WILL_DRAW); + fSaveButton->ResizeToPreferred(); + fSaveButton->MoveTo(top->Bounds().Width() - 5 - fSaveButton->Bounds().Width(), + top->Bounds().Height() - 5 - fSaveButton->Bounds().Height()); + fSaveButton->MakeDefault(true); + top->AddChild(fSaveButton); + + fRevertButton = new BButton(BRect(0, 0, 1, 1), "revertbutton", + "Cancel", new BMessage(MSG_REVERT_PRESSED), B_FOLLOW_TOP, B_WILL_DRAW); + fRevertButton->ResizeToPreferred(); + fRevertButton->MoveTo(fSaveButton->Frame().left - 10 - + fRevertButton->Bounds().Width(), top->Bounds().Height() - 5 - + fRevertButton->Bounds().Height()); + top->AddChild(fRevertButton); + + AddShortcut((ulong)'Q', (ulong)B_COMMAND_KEY, new BMessage(B_QUIT_REQUESTED)); + AddShortcut((ulong)'W', (ulong)B_COMMAND_KEY, new BMessage(B_QUIT_REQUESTED)); + + Show(); +} + + +PrefDlg::~PrefDlg() +{ +} + + +void +PrefDlg::Quit() +{ + fPrefDlgMessenger.SendMessage(MSG_PREF_CLOSED); + delete fPrefTemp; + delete fSavePanel; + BWindow::Quit(); +} + + +bool +PrefDlg::QuitRequested() +{ + if (!fDirty) + return true; + + BAlert *alert = new BAlert("", "Save changes to this preference panel?", + "Cancel", "Don't Save", "Save", + B_WIDTH_AS_USUAL, B_OFFSET_SPACING, + B_WARNING_ALERT); + alert->SetShortcut(0, B_ESCAPE); + alert->SetShortcut(1, 'd'); + alert->SetShortcut(2, 's'); + + int32 index = alert->Go(); + if (index == 0) + return false; + + if (index == 2) + _Save(); + + return true; +} + + +void +PrefDlg::_SaveAs() +{ + if (!fSavePanel) + fSavePanel = new BFilePanel(B_SAVE_PANEL, new BMessenger(this)); + + fSavePanel->Show(); +} + + +void +PrefDlg::_SaveRequested(BMessage *msg) +{ + entry_ref dirref; + const char *filename; + + msg->FindRef("directory", &dirref); + msg->FindString("name", &filename); + + BDirectory dir(&dirref); + BPath path(&dir, filename); + + gTermPref->SaveAsText(path.Path(), PREFFILE_MIMETYPE, TERM_SIGNATURE); +} + + +void +PrefDlg::_Save() +{ + delete fPrefTemp; + fPrefTemp = new PrefHandler(gTermPref); + + BPath path; + if (PrefHandler::GetDefaultPath(path) == B_OK) { + gTermPref->SaveAsText(path.Path(), PREFFILE_MIMETYPE); + fDirty = false; + } +} + + +void +PrefDlg::_Revert() +{ + delete gTermPref; + gTermPref = new PrefHandler(fPrefTemp); + + fPrefDlgMessenger.SendMessage(MSG_HALF_FONT_CHANGED); + fPrefDlgMessenger.SendMessage(MSG_COLOR_CHANGED); + fPrefDlgMessenger.SendMessage(MSG_INPUT_METHOD_CHANGED); + + fDirty = false; +} + + +void +PrefDlg::MessageReceived(BMessage *msg) +{ + switch (msg->what) { + case MSG_SAVE_PRESSED: + _Save(); + PostMessage(B_QUIT_REQUESTED); + break; + + case MSG_SAVEAS_PRESSED: + _SaveAs(); + break; + + case MSG_REVERT_PRESSED: + _Revert(); + PostMessage(B_QUIT_REQUESTED); + break; + + case MSG_PREF_MODIFIED: + fDirty = true; + break; + + case B_SAVE_REQUESTED: + _SaveRequested(msg); + break; + + default: + BWindow::MessageReceived(msg); + break; + } +} + + +BRect +PrefDlg::_CenteredRect(BRect rect) +{ + BRect screenRect = BScreen().Frame(); + + screenRect.InsetBy(10,10); + + float x = screenRect.left + (screenRect.Width() - rect.Width()) / 2; + float y = screenRect.top + (screenRect.Height() - rect.Height()) / 3; + + rect.OffsetTo(x, y); + + return rect; +} Copied: haiku/trunk/src/apps/terminal/PrefWindow.h (from rev 20662, haiku/trunk/src/apps/terminal/PrefDlg.h) Modified: haiku/trunk/src/apps/terminal/TermWindow.cpp =================================================================== --- haiku/trunk/src/apps/terminal/TermWindow.cpp 2007-04-13 16:21:17 UTC (rev 20678) +++ haiku/trunk/src/apps/terminal/TermWindow.cpp 2007-04-13 16:35:50 UTC (rev 20679) @@ -29,8 +29,8 @@ #include "CodeConv.h" #include "ColorWindow.h" #include "MenuUtil.h" -#include "FindDlg.h" -#include "PrefDlg.h" +#include "FindWindow.h" +#include "PrefWindow.h" #include "PrefView.h" #include "PrefHandler.h" #include "TermApp.h" From jackburton at mail.berlios.de Fri Apr 13 18:41:45 2007 From: jackburton at mail.berlios.de (jackburton at BerliOS) Date: Fri, 13 Apr 2007 18:41:45 +0200 Subject: [Haiku-commits] r20680 - haiku/trunk/src/apps/terminal Message-ID: <200704131641.l3DGfjXf009899@sheep.berlios.de> Author: jackburton Date: 2007-04-13 18:41:44 +0200 (Fri, 13 Apr 2007) New Revision: 20680 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20680&view=rev Modified: haiku/trunk/src/apps/terminal/FindWindow.cpp haiku/trunk/src/apps/terminal/FindWindow.h haiku/trunk/src/apps/terminal/PrefWindow.cpp haiku/trunk/src/apps/terminal/PrefWindow.h haiku/trunk/src/apps/terminal/TermWindow.cpp haiku/trunk/src/apps/terminal/TermWindow.h Log: Renamed *Dlg classes to *Window, completing my previous commit Modified: haiku/trunk/src/apps/terminal/FindWindow.cpp =================================================================== --- haiku/trunk/src/apps/terminal/FindWindow.cpp 2007-04-13 16:35:50 UTC (rev 20679) +++ haiku/trunk/src/apps/terminal/FindWindow.cpp 2007-04-13 16:41:44 UTC (rev 20680) @@ -19,7 +19,7 @@ const uint32 MSG_FIND_HIDE = 'Fhid'; -FindDlg::FindDlg (BRect frame, BMessenger messenger , BString &str, +FindWindow::FindWindow (BRect frame, BMessenger messenger , BString &str, bool findSelection, bool matchWord, bool matchCase, bool forwardSearch) : BWindow(frame, "Find", B_FLOATING_WINDOW, B_NOT_RESIZABLE|B_NOT_ZOOMABLE), fFindDlgMessenger(messenger) @@ -110,13 +110,13 @@ } -FindDlg::~FindDlg() +FindWindow::~FindWindow() { } void -FindDlg::MessageReceived(BMessage *msg) +FindWindow::MessageReceived(BMessage *msg) { switch (msg->what) { case B_QUIT_REQUESTED: @@ -139,7 +139,7 @@ void -FindDlg::Quit() +FindWindow::Quit() { fFindDlgMessenger.SendMessage(MSG_FIND_CLOSED); BWindow::Quit(); @@ -147,7 +147,7 @@ void -FindDlg::_SendFindMessage() +FindWindow::_SendFindMessage() { BMessage message(MSG_FIND); Modified: haiku/trunk/src/apps/terminal/FindWindow.h =================================================================== --- haiku/trunk/src/apps/terminal/FindWindow.h 2007-04-13 16:35:50 UTC (rev 20679) +++ haiku/trunk/src/apps/terminal/FindWindow.h 2007-04-13 16:41:44 UTC (rev 20680) @@ -17,11 +17,11 @@ const ulong MSG_FIND_CLOSED = 'mfcl'; -class FindDlg : public BWindow { +class FindWindow : public BWindow { public: - FindDlg (BRect frame, BMessenger messenger, BString &str, + FindWindow (BRect frame, BMessenger messenger, BString &str, bool findSelection, bool matchWord, bool matchCase, bool forwardSearch); - virtual ~FindDlg(); + virtual ~FindWindow(); virtual void Quit(); virtual void MessageReceived(BMessage *msg); Modified: haiku/trunk/src/apps/terminal/PrefWindow.cpp =================================================================== --- haiku/trunk/src/apps/terminal/PrefWindow.cpp 2007-04-13 16:35:50 UTC (rev 20679) +++ haiku/trunk/src/apps/terminal/PrefWindow.cpp 2007-04-13 16:41:44 UTC (rev 20680) @@ -27,7 +27,7 @@ extern PrefHandler *gTermPref; // Global Preference Handler -PrefDlg::PrefDlg(BMessenger messenger) +PrefWindow::PrefWindow(BMessenger messenger) : BWindow(_CenteredRect(BRect(0, 0, 350, 215)), "Terminal Settings", B_TITLED_WINDOW_LOOK, B_NORMAL_WINDOW_FEEL, B_NOT_RESIZABLE|B_NOT_ZOOMABLE), @@ -78,13 +78,13 @@ } -PrefDlg::~PrefDlg() +PrefWindow::~PrefWindow() { } void -PrefDlg::Quit() +PrefWindow::Quit() { fPrefDlgMessenger.SendMessage(MSG_PREF_CLOSED); delete fPrefTemp; @@ -94,7 +94,7 @@ bool -PrefDlg::QuitRequested() +PrefWindow::QuitRequested() { if (!fDirty) return true; @@ -119,7 +119,7 @@ void -PrefDlg::_SaveAs() +PrefWindow::_SaveAs() { if (!fSavePanel) fSavePanel = new BFilePanel(B_SAVE_PANEL, new BMessenger(this)); @@ -129,7 +129,7 @@ void -PrefDlg::_SaveRequested(BMessage *msg) +PrefWindow::_SaveRequested(BMessage *msg) { entry_ref dirref; const char *filename; @@ -145,7 +145,7 @@ void -PrefDlg::_Save() +PrefWindow::_Save() { delete fPrefTemp; fPrefTemp = new PrefHandler(gTermPref); @@ -159,7 +159,7 @@ void -PrefDlg::_Revert() +PrefWindow::_Revert() { delete gTermPref; gTermPref = new PrefHandler(fPrefTemp); @@ -173,7 +173,7 @@ void -PrefDlg::MessageReceived(BMessage *msg) +PrefWindow::MessageReceived(BMessage *msg) { switch (msg->what) { case MSG_SAVE_PRESSED: @@ -206,7 +206,7 @@ BRect -PrefDlg::_CenteredRect(BRect rect) +PrefWindow::_CenteredRect(BRect rect) { BRect screenRect = BScreen().Frame(); Modified: haiku/trunk/src/apps/terminal/PrefWindow.h =================================================================== --- haiku/trunk/src/apps/terminal/PrefWindow.h 2007-04-13 16:35:50 UTC (rev 20679) +++ haiku/trunk/src/apps/terminal/PrefWindow.h 2007-04-13 16:41:44 UTC (rev 20680) @@ -28,11 +28,11 @@ class PrefHandler; -class PrefDlg : public BWindow +class PrefWindow : public BWindow { public: - PrefDlg(BMessenger messenger); - virtual ~PrefDlg(); + PrefWindow(BMessenger messenger); + virtual ~PrefWindow(); virtual void Quit(); virtual bool QuitRequested(); Modified: haiku/trunk/src/apps/terminal/TermWindow.cpp =================================================================== --- haiku/trunk/src/apps/terminal/TermWindow.cpp 2007-04-13 16:35:50 UTC (rev 20679) +++ haiku/trunk/src/apps/terminal/TermWindow.cpp 2007-04-13 16:41:44 UTC (rev 20680) @@ -317,7 +317,7 @@ } case MENU_PREF_OPEN: { if (!fPrefWindow) - fPrefWindow = new PrefDlg(this); + fPrefWindow = new PrefWindow(this); else fPrefWindow->Activate(); break; @@ -333,7 +333,7 @@ r.top += 20; r.right = r.left + 260; r.bottom = r.top + 190; - fFindPanel = new FindDlg(r, this, fFindString, fFindSelection, fMatchWord, fMatchCase, fForwardSearch); + fFindPanel = new FindWindow(r, this, fFindString, fFindSelection, fMatchWord, fMatchCase, fForwardSearch); } else fFindPanel->Activate(); Modified: haiku/trunk/src/apps/terminal/TermWindow.h =================================================================== --- haiku/trunk/src/apps/terminal/TermWindow.h 2007-04-13 16:35:50 UTC (rev 20679) +++ haiku/trunk/src/apps/terminal/TermWindow.h 2007-04-13 16:41:44 UTC (rev 20680) @@ -40,9 +40,8 @@ class TermView; class TermParse; class CodeConv; -class PrefDlg; -class PrefDlg2; -class FindDlg; +class PrefWindow; +class FindWindow; class TermWindow : public BWindow { @@ -82,8 +81,8 @@ BView *fBaseView; CodeConv *fCodeConv; BMessage *fPrintSettings; - PrefDlg *fPrefWindow; - FindDlg *fFindPanel; + PrefWindow *fPrefWindow; + FindWindow *fFindPanel; BMessageRunner *fWindowUpdate; BMenuItem *item; BRect fSavedFrame; From hugosantos at mail.berlios.de Fri Apr 13 23:33:31 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Fri, 13 Apr 2007 23:33:31 +0200 Subject: [Haiku-commits] r20681 - in haiku/trunk: headers/private/net src/add-ons/kernel/network/protocols/ipv4 src/add-ons/kernel/network/protocols/udp src/add-ons/kernel/network/stack Message-ID: <200704132133.l3DLXVl1010673@sheep.berlios.de> Author: hugosantos Date: 2007-04-13 23:33:13 +0200 (Fri, 13 Apr 2007) New Revision: 20681 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20681&view=rev Modified: haiku/trunk/headers/private/net/ProtocolUtilities.h haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp haiku/trunk/src/add-ons/kernel/network/stack/link.cpp Log: respect SO_BROADCAST for received and sent datagrams. - check if the destination address is specified in IPv4's SendData() - minor cleanups to IPv4's TRACE()s. Modified: haiku/trunk/headers/private/net/ProtocolUtilities.h =================================================================== --- haiku/trunk/headers/private/net/ProtocolUtilities.h 2007-04-13 16:41:44 UTC (rev 20680) +++ haiku/trunk/headers/private/net/ProtocolUtilities.h 2007-04-13 21:33:13 UTC (rev 20681) @@ -50,13 +50,14 @@ status_t InitCheck() const; status_t Enqueue(net_buffer *buffer); - status_t EnqueueClone(net_buffer *buffer); net_buffer *Dequeue(bool clone); status_t BlockingDequeue(bool clone, bigtime_t timeout, net_buffer **_buffer); - status_t SocketDequeue(uint32 flags, net_buffer **_buffer); void Clear(); + status_t SocketEnqueue(net_buffer *buffer); + status_t SocketDequeue(uint32 flags, net_buffer **_buffer); + size_t AvailableData() const; void WakeAll(); @@ -65,7 +66,7 @@ protected: status_t _Enqueue(net_buffer *buffer); - status_t _EnqueueClone(net_buffer *buffer); + status_t _SocketEnqueue(net_buffer *buffer); net_buffer *_Dequeue(bool clone); void _Clear(); @@ -141,15 +142,22 @@ } -DECL_DATAGRAM_SOCKET(inline status_t)::EnqueueClone(net_buffer *_buffer) +DECL_DATAGRAM_SOCKET(inline status_t)::SocketEnqueue(net_buffer *_buffer) { AutoLocker _(fLock); - return _EnqueueClone(_buffer); + return _SocketEnqueue(_buffer); } -DECL_DATAGRAM_SOCKET(inline status_t)::_EnqueueClone(net_buffer *_buffer) +DECL_DATAGRAM_SOCKET(inline status_t)::_SocketEnqueue(net_buffer *_buffer) { + if (_buffer->flags & MSG_BCAST) { + // only deliver datagrams sent to a broadcast address + // to sockets with SO_BROADCAST on. + if (!(fSocket->options & SO_BROADCAST)) + return B_OK; + } + net_buffer *buffer = ModuleBundle::Buffer()->clone(_buffer, false); if (buffer == NULL) return B_NO_MEMORY; Modified: haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp 2007-04-13 16:41:44 UTC (rev 20680) +++ haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp 2007-04-13 21:33:13 UTC (rev 20681) @@ -31,9 +31,14 @@ //#define TRACE_IPV4 #ifdef TRACE_IPV4 -# define TRACE(x) dprintf x +# define TRACE(format, args...) \ + dprintf("IPv4 [%llu] " format "\n", system_time() , ##args) +# define TRACE_SK(protocol, format, args...) \ + dprintf("IPv4 [%llu] %p " format "\n", system_time(), \ + protocol , ##args) #else -# define TRACE(x) ; +# define TRACE(args...) do { } while (0) +# define TRACE_SK(args...) do { } while (0) #endif struct ipv4_header { @@ -211,17 +216,17 @@ return B_OK; } - TRACE((" previous: %p, next: %p\n", previous, next)); + TRACE(" previous: %p, next: %p", previous, next); // If we have parts of the data already, truncate as needed if (previous != NULL && previous->fragment.end > start) { - TRACE((" remove header %d bytes\n", previous->fragment.end - start)); + TRACE(" remove header %d bytes", previous->fragment.end - start); gBufferModule->remove_header(buffer, previous->fragment.end - start); start = previous->fragment.end; } if (next != NULL && next->fragment.start < end) { - TRACE((" remove trailer %d bytes\n", next->fragment.start - end)); + TRACE(" remove trailer %d bytes", next->fragment.start - end); gBufferModule->remove_trailer(buffer, next->fragment.start - end); end = next->fragment.start; } @@ -238,7 +243,7 @@ buffer->fragment.end = end; status_t status = gBufferModule->merge(buffer, previous, false); - TRACE((" merge previous: %s\n", strerror(status))); + TRACE(" merge previous: %s", strerror(status)); if (status < B_OK) { fFragments.Insert(next, previous); return status; @@ -254,7 +259,7 @@ fBytesLeft -= IP_MAXPACKET - end; } - TRACE((" hole length: %d\n", (int)fBytesLeft)); + TRACE(" hole length: %d", (int)fBytesLeft); return B_OK; } else if (next != NULL && next->fragment.start == end) { @@ -264,7 +269,7 @@ buffer->fragment.end = next->fragment.end; status_t status = gBufferModule->merge(buffer, next, true); - TRACE((" merge next: %s\n", strerror(status))); + TRACE(" merge next: %s", strerror(status)); if (status < B_OK) { fFragments.Insert((net_buffer *)previous->link.next, next); return status; @@ -280,14 +285,14 @@ fBytesLeft -= IP_MAXPACKET - end; } - TRACE((" hole length: %d\n", (int)fBytesLeft)); + TRACE(" hole length: %d", (int)fBytesLeft); return B_OK; } // We couldn't merge the fragments, so we need to add it as is - TRACE((" new fragment: %p, bytes %d-%d\n", buffer, start, end)); + TRACE(" new fragment: %p, bytes %d-%d", buffer, start, end); buffer->fragment.start = start; buffer->fragment.end = end; @@ -301,7 +306,7 @@ fBytesLeft -= IP_MAXPACKET - end; } - TRACE((" hole length: %d\n", (int)fBytesLeft)); + TRACE(" hole length: %d", (int)fBytesLeft); return B_OK; } @@ -373,7 +378,7 @@ FragmentPacket::StaleTimer(struct net_timer *timer, void *data) { FragmentPacket *packet = (FragmentPacket *)data; - TRACE(("Assembling FragmentPacket %p timed out!\n", packet)); + TRACE("Assembling FragmentPacket %p timed out!", packet); BenaphoreLocker locker(&sFragmentLock); @@ -464,8 +469,8 @@ uint16 end = start + header.TotalLength() - header.HeaderLength(); bool lastFragment = (fragmentOffset & IP_MORE_FRAGMENTS) == 0; - TRACE((" Received IPv4 %sfragment of size %d, offset %d.\n", - lastFragment ? "last ": "", end - start, start)); + TRACE(" Received IPv4 %sfragment of size %d, offset %d.", + lastFragment ? "last ": "", end - start, start); // Remove header unless this is the first fragment if (start != 0) @@ -500,8 +505,7 @@ send_fragments(ipv4_protocol *protocol, struct net_route *route, net_buffer *buffer, uint32 mtu) { - TRACE(("ipv4 needs to fragment (size %lu, MTU %lu)...\n", - buffer->size, mtu)); + TRACE_SK(protocol, "SendFragments(%lu bytes, mtu %lu)", buffer->size, mtu); NetBufferHeaderReader originalHeader(buffer); if (originalHeader.Status() < B_OK) @@ -581,7 +585,7 @@ { BenaphoreLocker locker(sRawSocketsLock); - TRACE(("ipv4:raw_receive_data(): protocol %i\n", buffer->protocol)); + TRACE("RawReceiveData(%i)", buffer->protocol); RawSocketList::Iterator iterator = sRawSockets.GetIterator(); @@ -589,7 +593,7 @@ RawSocket *raw = iterator.Next(); if (raw->Socket()->protocol == buffer->protocol) - raw->EnqueueClone(buffer); + raw->SocketEnqueue(buffer); } } @@ -662,6 +666,8 @@ return status; } + TRACE_SK(protocol, "Open()"); + protocol->raw = raw; BenaphoreLocker locker(sRawSocketsLock); @@ -678,6 +684,8 @@ if (raw == NULL) return B_ERROR; + TRACE_SK(protocol, "Close()"); + BenaphoreLocker locker(sRawSocketsLock); sRawSockets.Remove(raw); delete raw; @@ -859,7 +867,8 @@ ipv4_protocol *protocol = (ipv4_protocol *)_protocol; net_interface *interface = route->interface; - TRACE(("someone tries to send some actual routed data!\n")); + TRACE_SK(protocol, "SendRoutedData(%p, %p [%ld bytes])", route, buffer, + buffer->size); sockaddr_in &source = *(sockaddr_in *)&buffer->source; sockaddr_in &destination = *(sockaddr_in *)&buffer->destination; @@ -908,12 +917,12 @@ *IPChecksumField(buffer) = gBufferModule->checksum(buffer, 0, sizeof(ipv4_header), true); - TRACE(("header chksum: %ld, buffer checksum: %ld\n", + TRACE_SK(protocol, " SendRoutedData(): header chksum: %ld, buffer checksum: %ld", gBufferModule->checksum(buffer, 0, sizeof(ipv4_header), true), - gBufferModule->checksum(buffer, 0, buffer->size, true))); + gBufferModule->checksum(buffer, 0, buffer->size, true)); - TRACE(("destination-IP: buffer=%p addr=%p %08lx\n", buffer, &buffer->destination, - ntohl(destination.sin_addr.s_addr))); + TRACE_SK(protocol, " SendRoutedData(): destination: %08lx", + ntohl(destination.sin_addr.s_addr)); uint32 mtu = route->mtu ? route->mtu : interface->mtu; if (buffer->size > mtu) { @@ -928,8 +937,18 @@ status_t ipv4_send_data(net_protocol *protocol, net_buffer *buffer) { - TRACE(("someone tries to send some actual data!\n")); + TRACE_SK(protocol, "SendData(%p [%ld bytes])", buffer, buffer->size); + sockaddr_in &destination = *(sockaddr_in *)&buffer->destination; + + if (destination.sin_len == 0 || destination.sin_addr.s_addr == INADDR_ANY) + return EDESTADDRREQ; + else if (destination.sin_addr.s_addr == INADDR_BROADCAST) { + // TODO check for local broadcast addresses as well? + if (protocol && !(protocol->socket->options & SO_BROADCAST)) + return B_BAD_VALUE; + } + net_route *route = NULL; status_t status = sDatalinkModule->get_buffer_route(sDomain, buffer, &route); @@ -958,7 +977,8 @@ if (raw == NULL) return B_ERROR; - TRACE(("read is waiting for data...\n")); + TRACE_SK(protocol, "ReadData(%lu, 0x%lx)", numBytes, flags); + return raw->SocketDequeue(flags, _buffer); } @@ -1003,7 +1023,7 @@ status_t ipv4_receive_data(net_buffer *buffer) { - TRACE(("IPv4 received a packet (%p) of %ld size!\n", buffer, buffer->size)); + TRACE("ReceiveData(%p [%ld bytes])", buffer, buffer->size); NetBufferHeaderReader bufferHeader(buffer); if (bufferHeader.Status() < B_OK) @@ -1038,10 +1058,10 @@ // test if the packet is really for us uint32 matchedAddressType; - if (!sDatalinkModule->is_local_address(sDomain, (sockaddr*)&destination, + if (!sDatalinkModule->is_local_address(sDomain, (sockaddr*)&destination, &buffer->interface, &matchedAddressType)) { - TRACE(("this packet was not for us %lx -> %lx\n", - ntohl(header.source), ntohl(header.destination))); + TRACE(" ReceiveData(): packet was not for us %lx -> %lx", + ntohl(header.source), ntohl(header.destination)); return B_ERROR; } if (matchedAddressType != 0) { @@ -1061,15 +1081,15 @@ if ((fragmentOffset & IP_MORE_FRAGMENTS) != 0 || (fragmentOffset & IP_FRAGMENT_OFFSET_MASK) != 0) { // this is a fragment - TRACE((" Found a Fragment!\n")); + TRACE(" ReceiveData(): Found a Fragment!"); status = reassemble_fragments(header, &buffer); - TRACE((" -> %s!\n", strerror(status))); + TRACE(" ReceiveData(): -> %s", strerror(status)); if (status != B_OK) return status; if (buffer == NULL) { // buffer was put into fragment packet - TRACE((" Not yet assembled...\n")); + TRACE(" ReceiveData(): Not yet assembled."); return B_OK; } } Modified: haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp 2007-04-13 16:41:44 UTC (rev 20680) +++ haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp 2007-04-13 21:33:13 UTC (rev 20681) @@ -938,7 +938,7 @@ { TRACE_EP("StoreData(%p [%ld bytes])", buffer, buffer->size); - return EnqueueClone(buffer); + return SocketEnqueue(buffer); } Modified: haiku/trunk/src/add-ons/kernel/network/stack/link.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/link.cpp 2007-04-13 16:41:44 UTC (rev 20680) +++ haiku/trunk/src/add-ons/kernel/network/stack/link.cpp 2007-04-13 21:33:13 UTC (rev 20681) @@ -169,7 +169,7 @@ status_t LinkProtocol::_MonitorData(net_device_monitor *monitor, net_buffer *packet) { - return ((LinkProtocol *)monitor->cookie)->EnqueueClone(packet); + return ((LinkProtocol *)monitor->cookie)->SocketEnqueue(packet); } From korli at mail.berlios.de Sat Apr 14 15:35:39 2007 From: korli at mail.berlios.de (korli at BerliOS) Date: Sat, 14 Apr 2007 15:35:39 +0200 Subject: [Haiku-commits] r20682 - haiku/trunk/src/kits/game Message-ID: <200704141335.l3EDZd4x011176@sheep.berlios.de> Author: korli Date: 2007-04-14 15:35:39 +0200 (Sat, 14 Apr 2007) New Revision: 20682 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20682&view=rev Modified: haiku/trunk/src/kits/game/FileGameSound.cpp haiku/trunk/src/kits/game/GSUtility.cpp haiku/trunk/src/kits/game/GameSound.cpp haiku/trunk/src/kits/game/PushGameSound.cpp haiku/trunk/src/kits/game/SimpleGameSound.cpp haiku/trunk/src/kits/game/StreamingGameSound.cpp Log: update license headers, code style In BPushGameSound, SetParameter and SetStreamHook return B_UNSUPPORTED while Perform calls the parent class. Moved code to the constructor. Modified: haiku/trunk/src/kits/game/FileGameSound.cpp =================================================================== --- haiku/trunk/src/kits/game/FileGameSound.cpp 2007-04-13 21:33:13 UTC (rev 20681) +++ haiku/trunk/src/kits/game/FileGameSound.cpp 2007-04-14 13:35:39 UTC (rev 20682) @@ -1,28 +1,11 @@ -//------------------------------------------------------------------------------ -// Copyright (c) 2001-2002, OpenBeOS -// -// Permission is hereby granted, free of charge, to any person obtaining a -// copy of this software and associated documentation files (the "Software"), -// to deal in the Software without restriction, including without limitation -// the rights to use, copy, modify, merge, publish, distribute, sublicense, -// and/or sell copies of the Software, and to permit persons to whom the -// Software is furnished to do so, subject to the following conditions: -// -// The above copyright notice and this permission notice shall be included in -// all copies or substantial portions of the Software. -// -// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR -// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, -// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE -// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER -// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING -// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER -// DEALINGS IN THE SOFTWARE. -// -// File Name: FileGameSound.cpp -// Author: Christopher ML Zumwalt May (zummy at users.sf.net) -// Description: BFileGameSound is a class that streams data out of a file. -//------------------------------------------------------------------------------ +/* + * Copyright 2001-2007, Haiku Inc. + * Authors: + * Christopher ML Zumwalt May (zummy at users.sf.net) + * J?r?me Duval + * + * Distributed under the terms of the MIT License. + */ #include #include Modified: haiku/trunk/src/kits/game/GSUtility.cpp =================================================================== --- haiku/trunk/src/kits/game/GSUtility.cpp 2007-04-13 21:33:13 UTC (rev 20681) +++ haiku/trunk/src/kits/game/GSUtility.cpp 2007-04-14 13:35:39 UTC (rev 20682) @@ -1,44 +1,19 @@ -//------------------------------------------------------------------------------ -// Copyright (c) 2001-2002, OpenBeOS -// -// Permission is hereby granted, free of charge, to any person obtaining a -// copy of this software and associated documentation files (the "Software"), -// to deal in the Software without restriction, including without limitation -// the rights to use, copy, modify, merge, publish, distribute, sublicense, -// and/or sell copies of the Software, and to permit persons to whom the -// Software is furnished to do so, subject to the following conditions: -// -// The above copyright notice and this permission notice shall be included in -// all copies or substantial portions of the Software. -// -// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR -// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, -// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE -// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER -// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING -// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER -// DEALINGS IN THE SOFTWARE. -// -// File Name: GameSoundDevice.h -// Author: Christopher ML Zumwalt May (zummy at users.sf.net) -// Description: Utility functions used by sound system -//------------------------------------------------------------------------------ +/* + * Copyright 2001-2002, Haiku Inc. + * Authors: + * Christopher ML Zumwalt May (zummy at users.sf.net) + * + * Distributed under the terms of the MIT License. + */ -// Standard Includes ----------------------------------------------------------- - -// System Includes ------------------------------------------------------------- +#include #include -// Project Includes ------------------------------------------------------------ -#include - -// Local Includes -------------------------------------------------------------- #include "GSUtility.h" -// Local Defines --------------------------------------------------------------- -// Utility functions ----------------------------------------------------------- -_gs_ramp* InitRamp(float* value, float set, float frames, bigtime_t duration) +_gs_ramp* +InitRamp(float* value, float set, float frames, bigtime_t duration) { float diff = (set > *value) ? set - *value : *value - set; bigtime_t sec = bigtime_t(duration / 1000000.0); @@ -60,27 +35,31 @@ return ramp; } -bool ChangeRamp(_gs_ramp* ramp) + +bool +ChangeRamp(_gs_ramp* ramp) { - if (ramp->frame_count > ramp->frame_total) return true; + if (ramp->frame_count > ramp->frame_total) + return true; - if (ramp->frame_inc_count >= ramp->frame_inc) - { + if (ramp->frame_inc_count >= ramp->frame_inc) { ramp->frame_inc_count = 0; *ramp->value += ramp->inc; } - else ramp->frame_inc_count++; + else + ramp->frame_inc_count++; ramp->frame_count++; return false; } -size_t get_sample_size(int32 format) + +size_t +get_sample_size(int32 format) { size_t sample; - switch(format) - { + switch(format) { case media_raw_audio_format::B_AUDIO_CHAR: sample = sizeof(char); break; @@ -107,7 +86,9 @@ return sample; } -void media_to_gs_format(gs_audio_format* dest, media_raw_audio_format* source) + +void +media_to_gs_format(gs_audio_format* dest, media_raw_audio_format* source) { dest->format = source->format; dest->frame_rate = source->frame_rate; Modified: haiku/trunk/src/kits/game/GameSound.cpp =================================================================== --- haiku/trunk/src/kits/game/GameSound.cpp 2007-04-13 21:33:13 UTC (rev 20681) +++ haiku/trunk/src/kits/game/GameSound.cpp 2007-04-14 13:35:39 UTC (rev 20682) @@ -1,29 +1,10 @@ -//------------------------------------------------------------------------------ -// Copyright (c) 2001-2002, OpenBeOS -// -// Permission is hereby granted, free of charge, to any person obtaining a -// copy of this software and associated documentation files (the "Software"), -// to deal in the Software without restriction, including without limitation -// the rights to use, copy, modify, merge, publish, distribute, sublicense, -// and/or sell copies of the Software, and to permit persons to whom the -// Software is furnished to do so, subject to the following conditions: -// -// The above copyright notice and this permission notice shall be included in -// all copies or substantial portions of the Software. -// -// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR -// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, -// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE -// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER -// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING -// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER -// DEALINGS IN THE SOFTWARE. -// -// File Name: GameSound.cpp -// Author: Christopher ML Zumwalt May (zummy at users.sf.net) -// Description: Provides much of interfaces with BGameSoundDevice on behalf -// of the rest of it's childern. -//------------------------------------------------------------------------------ +/* + * Copyright 2001-2002, Haiku Inc. + * Authors: + * Christopher ML Zumwalt May (zummy at users.sf.net) + * + * Distributed under the terms of the MIT License. + */ #include #include Modified: haiku/trunk/src/kits/game/PushGameSound.cpp =================================================================== --- haiku/trunk/src/kits/game/PushGameSound.cpp 2007-04-13 21:33:13 UTC (rev 20681) +++ haiku/trunk/src/kits/game/PushGameSound.cpp 2007-04-14 13:35:39 UTC (rev 20682) @@ -1,28 +1,11 @@ -//------------------------------------------------------------------------------ -// Copyright (c) 2001-2002, OpenBeOS -// -// Permission is hereby granted, free of charge, to any person obtaining a -// copy of this software and associated documentation files (the "Software"), -// to deal in the Software without restriction, including without limitation -// the rights to use, copy, modify, merge, publish, distribute, sublicense, -// and/or sell copies of the Software, and to permit persons to whom the -// Software is furnished to do so, subject to the following conditions: -// -// The above copyright notice and this permission notice shall be included in -// all copies or substantial portions of the Software. -// -// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR -// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, -// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE -// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER -// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING -// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER -// DEALINGS IN THE SOFTWARE. -// -// File Name: GameSound.cpp -// Author: Christopher ML Zumwalt May (zummy at users.sf.net) -// Description: BPushGameSound class -//------------------------------------------------------------------------------ +/* + * Copyright 2001-2007, Haiku Inc. + * Authors: + * Christopher ML Zumwalt May (zummy at users.sf.net) + * J?r?me Duval + * + * Distributed under the terms of the MIT License. + */ #include @@ -36,14 +19,15 @@ size_t inBufferCount, BGameSoundDevice *device) : BStreamingGameSound(inBufferFrameCount, format, inBufferCount, device) { - if (InitCheck() != B_OK) - return; + fPageLocked = new BList; + + size_t frameSize = get_sample_size(format->format) * format->channel_count; - status_t error = SetParameters(inBufferFrameCount, format, inBufferCount); - if (error == B_OK) - fPageLocked = new BList; - else - SetInitError(error); + fPageCount = inBufferCount; + fPageSize = frameSize * inBufferFrameCount; + fBufferSize = fPageSize * fPageCount; + + fBuffer = new char[fBufferSize]; } @@ -58,7 +42,8 @@ { fPageLocked = new BList; } - + + BPushGameSound::~BPushGameSound() { delete [] fBuffer; @@ -70,12 +55,12 @@ BPushGameSound::LockNextPage(void **out_pagePtr, size_t *out_pageSize) { // the user can not lock every page - if (fPageLocked->CountItems() > fPageCount - 3) + if (fPageLocked->CountItems() > fPageCount - 3) return lock_failed; // the user cann't lock a page being played if (fLockPos < fPlayPos - && fLockPos + fPageSize > fPlayPos) + && fLockPos + fPageSize > fPlayPos) return lock_failed; // lock the page @@ -84,7 +69,7 @@ // move the locker to the next page fLockPos += fPageSize; - if (fLockPos > fBufferSize) + if (fLockPos > fBufferSize) fLockPos = 0; *out_pagePtr = lockPage; @@ -138,7 +123,7 @@ status_t BPushGameSound::Perform(int32 selector, void *data) { - return B_ERROR; + return BStreamingGameSound::Perform(selector, data); } @@ -147,19 +132,7 @@ const gs_audio_format *format, size_t inBufferCount) { - status_t error = BStreamingGameSound::SetParameters(inBufferFrameCount, format, inBufferCount); - if (error != B_OK) - return error; - - size_t frameSize = get_sample_size(format->format) * format->channel_count; - - fPageCount = inBufferCount; - fPageSize = frameSize * inBufferFrameCount; - fBufferSize = fPageSize * fPageCount; - - fBuffer = new char[fBufferSize]; - - return B_OK; + return B_UNSUPPORTED; } @@ -167,7 +140,7 @@ BPushGameSound::SetStreamHook(void (*hook)(void * inCookie, void * inBuffer, size_t inByteCount, BStreamingGameSound * me), void * cookie) { - return B_ERROR; + return B_UNSUPPORTED; } Modified: haiku/trunk/src/kits/game/SimpleGameSound.cpp =================================================================== --- haiku/trunk/src/kits/game/SimpleGameSound.cpp 2007-04-13 21:33:13 UTC (rev 20681) +++ haiku/trunk/src/kits/game/SimpleGameSound.cpp 2007-04-14 13:35:39 UTC (rev 20682) @@ -1,29 +1,10 @@ -//------------------------------------------------------------------------------ -// Copyright (c) 2001-2005, Haiku -// -// Permission is hereby granted, free of charge, to any person obtaining a -// copy of this software and associated documentation files (the "Software"), -// to deal in the Software without restriction, including without limitation -// the rights to use, copy, modify, merge, publish, distribute, sublicense, -// and/or sell copies of the Software, and to permit persons to whom the -// Software is furnished to do so, subject to the following conditions: -// -// The above copyright notice and this permission notice shall be included in -// all copies or substantial portions of the Software. -// -// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR -// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, -// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE -// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER -// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING -// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER -// DEALINGS IN THE SOFTWARE. -// -// File Name: SimpleGameSound.h -// Author: Christopher ML Zumwalt May (zummy at users.sf.net) -// Description: BSimpleGameSound is a class for sound effects that are -// short, and consists of non-changing samples in memory. -//------------------------------------------------------------------------------ +/* + * Copyright 2001-2005, Haiku Inc. + * Authors: + * Christopher ML Zumwalt May (zummy at users.sf.net) + * + * Distributed under the terms of the MIT License. + */ #include #include Modified: haiku/trunk/src/kits/game/StreamingGameSound.cpp =================================================================== --- haiku/trunk/src/kits/game/StreamingGameSound.cpp 2007-04-13 21:33:13 UTC (rev 20681) +++ haiku/trunk/src/kits/game/StreamingGameSound.cpp 2007-04-14 13:35:39 UTC (rev 20682) @@ -25,17 +25,10 @@ // (data not known beforehand) game sounds. //------------------------------------------------------------------------------ -// Standard Includes ----------------------------------------------------------- - -// System Includes ------------------------------------------------------------- - -// Project Includes ------------------------------------------------------------ #include "GameSoundDevice.h" - -// Local Includes -------------------------------------------------------------- #include "StreamingGameSound.h" -// Local Defines --------------------------------------------------------------- + BStreamingGameSound::BStreamingGameSound(size_t inBufferFrameCount, const gs_audio_format *format, size_t inBufferCount, @@ -44,8 +37,7 @@ fStreamHook(NULL), fStreamCookie(NULL) { - if (InitCheck() == B_OK) - { + if (InitCheck() == B_OK) { status_t error = SetParameters(inBufferFrameCount, format, inBufferCount); SetInitError(error); } From axeld at mail.berlios.de Sat Apr 14 20:11:42 2007 From: axeld at mail.berlios.de (axeld at BerliOS) Date: Sat, 14 Apr 2007 20:11:42 +0200 Subject: [Haiku-commits] r20683 - in haiku/trunk: headers/os/app src/kits/interface Message-ID: <200704141811.l3EIBgUA009840@sheep.berlios.de> Author: axeld Date: 2007-04-14 20:11:42 +0200 (Sat, 14 Apr 2007) New Revision: 20683 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20683&view=rev Modified: haiku/trunk/headers/os/app/AppDefs.h haiku/trunk/src/kits/interface/Window.cpp Log: * Added and implemented B_INVALIDATE as available on Dano; to invalidate only a certain part of the view, you can add a BRect "be:area" to that message - very handy. * Cleaned up AppDefs.h a bit. Modified: haiku/trunk/headers/os/app/AppDefs.h =================================================================== --- haiku/trunk/headers/os/app/AppDefs.h 2007-04-14 13:35:39 UTC (rev 20682) +++ haiku/trunk/headers/os/app/AppDefs.h 2007-04-14 18:11:42 UTC (rev 20683) @@ -1,30 +1,17 @@ /* - * Copyright 2001-2002, Haiku Inc. All Rights Reserved. + * Copyright 2001-2007, Haiku Inc. All Rights Reserved. * Distributed under the terms of the MIT License. * * Authors: * Erik Jaesler (erik at cgsoftware.com) */ - #ifndef _APP_DEFS_H #define _APP_DEFS_H -// Standard Includes ----------------------------------------------------------- -// System Includes ------------------------------------------------------------- #include -// Project Includes ------------------------------------------------------------ -// Local Includes -------------------------------------------------------------- - -// Local Defines --------------------------------------------------------------- - -// Globals --------------------------------------------------------------------- - - -// Global Cursors -------------------------------------------------------------- - // Old-style cursors extern const unsigned char B_HAND_CURSOR[]; extern const unsigned char B_I_BEAM_CURSOR[]; @@ -36,8 +23,8 @@ extern const BCursor *B_CURSOR_I_BEAM; #endif -// System Message Codes -------------------------------------------------------- +// System Message Codes enum { B_ABOUT_REQUESTED = '_ABR', B_WINDOW_ACTIVATED = '_ACT', @@ -46,6 +33,7 @@ B_QUIT_REQUESTED = '_QRQ', B_CLOSE_REQUESTED = '_QRQ', // Obsolete; use B_QUIT_REQUESTED B_CANCEL = '_CNC', + B_INVALIDATE = '_IVL', B_KEY_DOWN = '_KYD', B_KEY_UP = '_KYU', B_UNMAPPED_KEY_DOWN = '_UKD', @@ -76,8 +64,10 @@ B_WORKSPACES_CHANGED = '_WCG', B_WORKSPACE_ACTIVATED = '_WAC', B_ZOOM = '_WZM', - _COLORS_UPDATED = '_CLU', // Currently internal-use only. Later, public as B_COLORS_UPDATED - _FONTS_UPDATED = '_FNU', // Currently internal-use only. Later, public as B_FONTS_UPDATED + _COLORS_UPDATED = '_CLU', + // Currently internal-use only. Later, public as B_COLORS_UPDATED + _FONTS_UPDATED = '_FNU', + // Currently internal-use only. Later, public as B_FONTS_UPDATED _APP_MENU_ = '_AMN', _BROWSER_MENUS_ = '_BRM', _MENU_EVENT_ = '_MEV', @@ -99,8 +89,7 @@ }; -// Other Commands -------------------------------------------------------------- - +// Other Commands enum { B_SET_PROPERTY = 'PSET', B_GET_PROPERTY = 'PGET', @@ -142,7 +131,5 @@ // Media Kit reserves all reserved codes starting in 'TRI' }; -//------------------------------------------------------------------------------ #endif // _APP_DEFS_H - Modified: haiku/trunk/src/kits/interface/Window.cpp =================================================================== --- haiku/trunk/src/kits/interface/Window.cpp 2007-04-14 13:35:39 UTC (rev 20682) +++ haiku/trunk/src/kits/interface/Window.cpp 2007-04-14 18:11:42 UTC (rev 20683) @@ -962,6 +962,19 @@ target->MessageReceived(msg); break; + case B_INVALIDATE: + { + if (BView* view = dynamic_cast(target)) { + BRect rect; + if (msg->FindRect("be:area", &rect) == B_OK) + view->Invalidate(rect); + else + view->Invalidate(); + } else + target->MessageReceived(msg); + break; + } + case B_KEY_DOWN: { if (!_HandleKeyDown(msg)) { From stippi at mail.berlios.de Sun Apr 15 00:37:04 2007 From: stippi at mail.berlios.de (stippi at BerliOS) Date: Sun, 15 Apr 2007 00:37:04 +0200 Subject: [Haiku-commits] r20684 - haiku/trunk/src/preferences/filetypes Message-ID: <200704142237.l3EMb440004288@sheep.berlios.de> Author: stippi Date: 2007-04-15 00:36:56 +0200 (Sun, 15 Apr 2007) New Revision: 20684 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20684&view=rev Modified: haiku/trunk/src/preferences/filetypes/FileTypes.icons.rdef haiku/trunk/src/preferences/filetypes/FileTypes.rdef haiku/trunk/src/preferences/filetypes/IconView.cpp Log: * added vector icons for application and supported types * added "icon heap" icon * implemented loading vector icon for "icon heap" Modified: haiku/trunk/src/preferences/filetypes/FileTypes.icons.rdef =================================================================== --- haiku/trunk/src/preferences/filetypes/FileTypes.icons.rdef 2007-04-14 18:11:42 UTC (rev 20683) +++ haiku/trunk/src/preferences/filetypes/FileTypes.icons.rdef 2007-04-14 22:36:56 UTC (rev 20684) @@ -2,6 +2,35 @@ * FileTypes.icons.rdef */ +#ifdef HAIKU_TARGET_PLATFORM_HAIKU + +resource(0, "BEOS:application/x-be-resource") #'VICN' array { + $"6E63696607050102000603399E0F3D9C0ABF82B23B84A94B88504870C900A5B1" + $"FFBCEAF1FFFFB3B8FF020106023E49240000000000003CAAAA4940004A3000FF" + $"C0D5FF7C896EFF040192020006023A4BAE3411A9B629883C6629495368484715" + $"00FFF9BAFFFFC104020006023A6A0E3670BCB6D8C13AD0F64A21BC4A0DF300BA" + $"DCFFFF2A20F10200060239AAD5343BA5B6E7993C629D4ABB354803A500E99797" + $"FFCE3232070606AE0BB40BBF4D33C3AFB75DC173BDEFC607C13EC804CA28BD82" + $"C118B920C51BBB40BF07B8083AB6BC0605AE02B57D3EB9B9C3EFB7BB44BBB751" + $"BD75C936CA8EC1B1402F0A093B593D5BBFCDC93E455BC516C5F160465B435D45" + $"44510A045A425E3F5A3D57400A063236323D3A41403E403739330A063A433A4A" + $"404D464A464341400A064237423E48424E3F4E394835090A03020203000A0001" + $"011001178400040A020101000A0001001001178400040A010100000A00030405" + $"061001178400040A040104000A050105000A06010600" +}; + +resource(1, "BEOS:application/octet-stream") #'VICN' array { + $"6E6369660402000603399E0F3D9C0ABF82B23B84A94B88504870C900A5B1FFBC" + $"EAF1FFFFB3B8FF0501020106023E49240000000000003CAAAA4940004A3000FF" + $"C0D5FF7C896EFF040192040606AE0BB40BBF4D33C3AFB75DC173BDEFC607C13E" + $"C804CA28BD82C118B920C51BBB40BF07B8083AB6BC0605AE02B57D3EB9B9C3EF" + $"B7BB44BBB751BD75C936CA8EC1B1402F0A093B593D5BBFCDC93E455BC516C5F1" + $"60465B435D4544510A045A425E3F5A3D5740050A03020203000A010101100117" + $"8400040A020101000A0101001001178400040A00010000" +}; + +#else // HAIKU_TARGET_PLATFORM_HAIKU + resource(0, "BEOS:L:application/x-be-resource") #'ICON' array { $"FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF02020008FFFFFFFFFFFFFFFFFFFF" $"FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF041B17110802FFFFFFFFFFFFFFFFFF" @@ -109,3 +138,5 @@ $"FFFFFFFFAE00000000AEAEFFFFFFFFFF" $"FFFFFFFFFFAE00AEFFAEFFFFFFFFFFFF" }; + +#endif // HAIKU_TARGET_PLATFORM_HAIKU Modified: haiku/trunk/src/preferences/filetypes/FileTypes.rdef =================================================================== --- haiku/trunk/src/preferences/filetypes/FileTypes.rdef 2007-04-14 18:11:42 UTC (rev 20683) +++ haiku/trunk/src/preferences/filetypes/FileTypes.rdef 2007-04-14 22:36:56 UTC (rev 20684) @@ -27,25 +27,46 @@ }; -resource mini_icon array { - $"FFFFFFFFFFFFFFFF020200FFFFFFFFFF" - $"FFFFFFFFFFFFFF04151E1500FFFFFFFF" - $"FFFFFFFFFFFFFF021D1E1C00FFFFFFFF" - $"FFFFFFFF00FFFF00151B1600FFFFFFFF" - $"FFFFFF003F0000FA0000000000FFFFFF" - $"FFFF003FFD0000F9F9FAFAFAFA00FFFF" - $"FF003FFEFDFD00F9F9F9F97D7D00FFFF" - $"003F62FE89007B00F9F900007D00FFFF" - $"FF003FB0FD002F00F90060600000FFFF" - $"FF003FFE002F000000606060606000FF" - $"FF000000002F00003F3F606060D500FF" - $"002B00002F00FA00ACAC3F3FD5D500FF" - $"002B7B2CEB000000ACACACACD5D5000E" - $"FF002B2F00000E00ACACACACD5D5000E" - $"FF002B2F000E0E0F0000ACACD5000E0E" - $"FFFF00000E0F0F0F0F0F0000000E0EFF" +#ifdef HAIKU_TARGET_PLATFORM_HAIKU + +resource vector_icon { + $"6E6369660C0500040169020006023CADF43D104EBF02CA3EA2224BF02046648D" + $"00FFDB97FFFCAF29020006023A6496BA3F153EBCDD3EEA91492CB5C09D5100FF" + $"F7EAFEFDD17B020006023AB3673751B2BC59783FD2D74C71F846F85900C85805" + $"FFF06306020106033AC71C0000000000003AB6DB4A6A0045300000F2F2F2FFBC" + $"A184AB7D7A7A02000602388A280000000000004000004AF00000000000C85804" + $"FFDC952F020006023B37D13A0397BB629E3CB4584A3EDF4A1E9400C6D7F5FF6B" + $"94DD020006023C71E33A0C78BA15E43C7D214B02AA49855700E3EDFFFF9EC2FF" + $"0200060239AB92381275BA365C3BEB2A4B2A844A9A5F00003CB0FF2C62D00200" + $"06033AC7B03884E3B903663B534D48B61F4958AE00FCFFDC7FF8F0BCFFF4DC8A" + $"020006023A7061B88A6E3B1AAE3CFAD946AC4F48C79100000000FFA9A06E130A" + $"053E303E4452445232452C0A043E303E444C444C360A063E304C3652324630C3" + $"BBB893452C0A044C44524452324C36020448224B22452242284225422B482E45" + $"2E4B2E4E284E2B4E250605E2024A60505A5660506054604C584A0A0346305232" + $"4A2E0A063A443A564A5E56535642463C0A043A443A564A5E4A4B0A043A444A4B" + $"5642463C0A044A4B4A5E565356420604AE342D223822382C4632524247080233" + $"33273B080231BCA9B6AFBEB40802BC10BCA92B40080237BDE8B821C0BF0802BC" + $"1DBF66B8A0C1D708023BBFF3304808023B44BA12C42E100A010105000A00010B" + $"1815FF01178400040A00010B18001501178500040A0A010B000A0B070E0D0C10" + $"0F12111815FF01178100040A0001001001178400040A020101000A030102000A" + $"040103000A060106000A0001041001178400040A050104000A00010710011784" + $"00040A070108000A09010A000A08010900" }; +resource(200, "icon heap") #'VICN' array { + $"6E63696605050104019202000603399E0F3D9C0ABF82B23B84A94B885046E193" + $"00A5B1FFBCEAF1FFFFB3B8FF020106023C71C43DE4E9BCEEA63BAE5F49867748" + $"01ECFFC0D5FF7C896EFF020106023C34913DBF47BD1EE83BAC5E49EA70498C6D" + $"FFC0D5FF7C896EFF040A07485E4A5E4C5F6043573D455D475D0606AE0BB40BBC" + $"1D33C07FB72CBE903C47C13EC408CA28BA52C118B656C51BB876BF07B53E3A23" + $"0605AE02B40BBF4D33C3AFB73CC1A43D50C13EC79ECA28BD823AB6BC0605AE02" + $"B40BC27D33C6DFB75DC4A3BDEFC937C13ECB34CA28C0B23AB9EC070A01010000" + $"0A0001031001178400040A040103000A0001021001178400040A030102000A00" + $"01011001178400040A02010100" +}; + +#else // HAIKU_TARGET_PLATFORM_HAIKU + resource large_icon array { $"FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF02020000FFFFFFFFFFFFFFFFFFFF" $"FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF041B17110802FFFFFFFFFFFFFFFFFF" @@ -81,6 +102,25 @@ $"FFFFFFFF0000000E0F0F0F0F0F0F0F0F0F0F0F00000E0E0EFFFFFFFFFFFFFFFF" }; +resource mini_icon array { + $"FFFFFFFFFFFFFFFF020200FFFFFFFFFF" + $"FFFFFFFFFFFFFF04151E1500FFFFFFFF" + $"FFFFFFFFFFFFFF021D1E1C00FFFFFFFF" + $"FFFFFFFF00FFFF00151B1600FFFFFFFF" + $"FFFFFF003F0000FA0000000000FFFFFF" + $"FFFF003FFD0000F9F9FAFAFAFA00FFFF" + $"FF003FFEFDFD00F9F9F9F97D7D00FFFF" + $"003F62FE89007B00F9F900007D00FFFF" + $"FF003FB0FD002F00F90060600000FFFF" + $"FF003FFE002F000000606060606000FF" + $"FF000000002F00003F3F606060D500FF" + $"002B00002F00FA00ACAC3F3FD5D500FF" + $"002B7B2CEB000000ACACACACD5D5000E" + $"FF002B2F00000E00ACACACACD5D5000E" + $"FF002B2F000E0E0F0000ACACD5000E0E" + $"FFFF00000E0F0F0F0F0F0000000E0EFF" +}; + resource(200, "icon heap") #'ICON' array { $"FFFFFFFFFFFFFFFFFFFFFFFF0000FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF" $"FFFFFFFFFFFFFFFFFFFFFF0060600000FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF" @@ -115,3 +155,5 @@ $"FFFFFFFFFFFFFFFFFFFFFFFFAEFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF" $"FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF" }; + +#endif // HAIKU_TARGET_PLATFORM_HAIKU Modified: haiku/trunk/src/preferences/filetypes/IconView.cpp =================================================================== --- haiku/trunk/src/preferences/filetypes/IconView.cpp 2007-04-14 18:11:42 UTC (rev 20683) +++ haiku/trunk/src/preferences/filetypes/IconView.cpp 2007-04-14 22:36:56 UTC (rev 20684) @@ -1053,13 +1053,32 @@ if (show) { BResources* resources = be_app->AppResources(); - const void* data = NULL; - // TODO: get vector heap icon! - if (resources != NULL) - data = resources->LoadResource('ICON', "icon heap", NULL); - if (data != NULL) { - fHeapIcon = Icon::AllocateBitmap(B_LARGE_ICON, B_CMAP8); - memcpy(fHeapIcon->Bits(), data, fHeapIcon->BitsLength()); + if (resources != NULL) { + const void* data = NULL; +#ifdef HAIKU_TARGET_PLATFORM_HAIKU + size_t size; + data = resources->LoadResource('VICN', "icon heap", &size); + if (data != NULL) { + // got vector icon data + fHeapIcon = Icon::AllocateBitmap(B_LARGE_ICON, B_RGBA32); + if (BIconUtils::GetVectorIcon((const uint8*)data, + size, fHeapIcon) != B_OK) { + // bad data + delete fHeapIcon; + fHeapIcon = NULL; + data = NULL; + } + } +#endif // HAIKU_TARGET_PLATFORM_HAIKU + if (data == NULL) { + // no vector icon or failed to get bitmap + // try bitmap icon + data = resources->LoadResource('ICON', "icon heap", NULL); + if (data != NULL) { + fHeapIcon = Icon::AllocateBitmap(B_LARGE_ICON, B_CMAP8); + memcpy(fHeapIcon->Bits(), data, fHeapIcon->BitsLength()); + } + } } } else { delete fHeapIcon; From stippi at mail.berlios.de Sun Apr 15 00:38:06 2007 From: stippi at mail.berlios.de (stippi at BerliOS) Date: Sun, 15 Apr 2007 00:38:06 +0200 Subject: [Haiku-commits] r20685 - haiku/trunk/src/preferences/backgrounds Message-ID: <200704142238.l3EMc6TW007165@sheep.berlios.de> Author: stippi Date: 2007-04-15 00:38:05 +0200 (Sun, 15 Apr 2007) New Revision: 20685 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20685&view=rev Modified: haiku/trunk/src/preferences/backgrounds/Backgrounds.rdef Log: * created vector icon Modified: haiku/trunk/src/preferences/backgrounds/Backgrounds.rdef =================================================================== --- haiku/trunk/src/preferences/backgrounds/Backgrounds.rdef 2007-04-14 22:36:56 UTC (rev 20684) +++ haiku/trunk/src/preferences/backgrounds/Backgrounds.rdef 2007-04-14 22:38:05 UTC (rev 20685) @@ -18,6 +18,48 @@ resource app_flags B_SINGLE_LAUNCH; +#ifdef HAIKU_TARGET_PLATFORM_HAIKU + +resource vector_icon { + $"6E6369660E05000400670200060336FFFF0000000000003AC000479E664A48A3" + $"00D3A966C784572AFFAB7A4A0200060236FFFF0000000000003AC000479E664A" + $"48A300A97F57FF673E16020006023A210C3AC8A8BAC7B53A2052484F9C490135" + $"00E3AE62FFBE8B480200060238328634EE08B7213C3A58ED496BC24932540093" + $"663BFFA77543020006023B200000000000000040000047C800C61800009C6D2A" + $"FF6D400B020006023B852539E0BDBB39023CECE448C21AC0A26300EBBF5FFFE3" + $"B649020006023AD3E33859CCB6BB5B39493D472D3747102400FFECB3FFFFDE90" + $"05F8020016033980000000000000004000004AF00000000000D9FFADD0980200" + $"16023980000000000000004000004A800000000000DDFFA70200160438000000" + $"00000000004000004B200000000000AD4886FFADD89902001602380F9632E8EC" + $"B4C61739EDD44B51664925FF00FFFFA0160604CBC91D4F5C4FC91D4F4E605460" + $"55605C60510A0832542E583858405C465C4C563A4C324C0614A7F9E3BEE63253" + $"325732534438473E41363D35402F3E303F2E3E2B3E2D3E2B3C2A3C2A392A3632" + $"262F252F252E222C2628222A24272422282627242A243022313C2C412C532C53" + $"2C57060CFAE3BE38383D35402F3E303F2E3E2B3E2D3E2B3C2A3C2A392A363226" + $"2F252F252E222C2628222A24272422282627242A243002042C422C462C422C53" + $"2C532C5732533257325332433243324806047E2C3C2C422C422C463243324832" + $"433C0A042231223C3847383A0A04383A38473E413E360A04282E2231383A3E36" + $"06033B23282A2A26B7BD26302A322A322B2D0604E72C28B841B6A3B7F9B72532" + $"3135312A2F2E312A0204363736373634382E3730382E332A352DBAC1B8123236" + $"3031323606033E3838392E3D2D39303637373636370606FF0E4E22C71622C391" + $"22462546B45546254654465446C9094E5AC3915A4E5A56545625562556B45502" + $"044E22C71622C39122462546B45546B5A64E28C39128C71628562556B5A656B4" + $"5502064E28C71628C39128462546B5A6462546C45646C4564C4E4E5A4E5AC716" + $"5A565456C90956545625562556B5A6020346C4564C4E46C4564654465446C909" + $"4E5AC3915A4E5A02044E24C5C424C4E3244C254CB4C54CB5364E26C4E326C5C4" + $"26502550B53650B4C506067F0F56285628542B5134C749B82B4E3F4E4F4E464E" + $"4F5E515B4F5C535A5655565856550608FFF75627562756B679C705B954C807B6" + $"5CC6DBB9CF5134C6B0BA5AC5C8BDAFC585C516C5BEC1A0C562C7354E5B4EC925" + $"4E5B5E515B4F5C535A56555658565502035A3A5A3A5735542B55344F364E4F4E" + $"46514002045A3A5A3A5735542B553456335D3B5A355A3E4E4F553F5140120A01" + $"020001000A0001021001178400040A020104000A030105000A040106000A0501" + $"07000A060108000A070103000A0804090A0B0C000A00010D1001178400040A09" + $"010E000A0A010F000A0B0110000A000111000A0001121001178402040A0C0113" + $"000A0D0114000A00011500" +}; + +#else // HAIKU_TARGET_PLATFORM_HAIKU + resource large_icon { $"FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF" $"FFFFFFFFFF0000FFFFFFFFFFFFFFFFFFFFFFFF0000000000FFFFFFFFFFFFFFFF" @@ -71,3 +113,5 @@ $"FF002B2F00FFFF0F0F0F000D000F0F0F" $"FFFF00000E0F0F0F0F0F0F000F0F0FFF" }; + +#endif // HAIKU_TARGET_PLATFORM_HAIKU From axeld at pinc-software.de Sun Apr 15 00:53:37 2007 From: axeld at pinc-software.de (Axel =?iso-8859-15?q?D=F6rfler?=) Date: Sun, 15 Apr 2007 00:53:37 +0200 CEST Subject: [Haiku-commits] r20684 - haiku/trunk/src/preferences/filetypes In-Reply-To: <200704142237.l3EMb440004288@sheep.berlios.de> Message-ID: <48176482579-BeMail@zon> stippi at BerliOS wrote: > Log: > * added vector icons for application and supported types > * added "icon heap" icon > * implemented loading vector icon for "icon heap" Cool, thanks! :-) Bye, Axel. From stippi at mail.berlios.de Sun Apr 15 01:07:38 2007 From: stippi at mail.berlios.de (stippi at BerliOS) Date: Sun, 15 Apr 2007 01:07:38 +0200 Subject: [Haiku-commits] r20686 - haiku/trunk/src/apps/midiplayer Message-ID: <200704142307.l3EN7cSI014396@sheep.berlios.de> Author: stippi Date: 2007-04-15 01:07:37 +0200 (Sun, 15 Apr 2007) New Revision: 20686 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20686&view=rev Modified: haiku/trunk/src/apps/midiplayer/MidiPlayer.rdef Log: * icon contained some left over unused paths Modified: haiku/trunk/src/apps/midiplayer/MidiPlayer.rdef =================================================================== --- haiku/trunk/src/apps/midiplayer/MidiPlayer.rdef 2007-04-14 22:38:05 UTC (rev 20685) +++ haiku/trunk/src/apps/midiplayer/MidiPlayer.rdef 2007-04-14 23:07:37 UTC (rev 20686) @@ -27,24 +27,20 @@ $"A71F00FFFFC902001602375F6837E895BD682D3CF09A4A666B478BC300E2FF89" $"05970201060238800000000000000037000049C0004A500000FFB3B3FFED0606" $"0201060238800000000000000037000049C0004A500000FFF589FFFF96300201" - $"060238800000000000000037000049C0004A50000075FF75FF04A9040F0A045C" + $"060238800000000000000037000049C0004A50000075FF75FF04A9040D0A045C" $"BF82405C465C60C04E0A06223F224B405A5A405A343E2A0A04404C223F224B40" $"5A0A04404C5A345A40405A0A04404C5A343E2A223F0A06C0CBB88BC0E0B93AC1" $"ACB986B9E8C07EB9FCC0C8C258B9370A06B91BC018C0DFB93AC0CBB88BB86FC0" $"01B9FCC0C8B9E7C07E0A04B9E7C07EC1ABB986C0DFB93AB91BC01806079A3636" $"3433373A393D3C3A373935BD91BBABBC5FBB120606BA0E363433373638BB2BBC" $"43BC5DBCDC393A3C373935BD8FBBAABC5DBB110605660333373A393D3A3638BC" - $"5DBCDCBB2BBC430A04393A393D3C3A3C370205C175B90EC175B90EC193B8CDC2" - $"4BB8ECC1F3B8BDC2A4B91AC2B5B9B6C2D2B975C297B9F7C1E0B9D8C237BA07C1" - $"86B9A9C176B90EC157B94FC176B90E0205C1AAB959C1AAB959C1BFB92DC239B9" - $"42C1FEB923C274B961C280B9C9C293B99EC26CB9F4C1F2B9E0C22CB9FFC1B6B9" - $"C0C1ABB959C196B984C1ABB95902043D43BEFE43BE1D433BC18B3BC1363BC1DF" - $"3D46BE1D46BEFE463FC18B3FC1DF3FC136140A010100000A0001011001178400" - $"040A020102000A030103000A040104000A060105000A030106000A050107000A" - $"0001081001178400040A070109000A08010A000A09010B000A00010E1815FF01" - $"178200040A0C010E000A00010E38251B15FF01178200040A0C010E20251B0A00" - $"010E382A1615FF01178200040A0B010E202A160A00010E382F1115FF01178200" - $"040A0A010E202F11" + $"5DBCDCBB2BBC430A04393A393D3C3A3C3702043D43BEFE43BE1D433BC18B3BC1" + $"363BC1DF3D46BE1D46BEFE463FC18B3FC1DF3FC136140A010100000A00010110" + $"01178400040A020102000A030103000A040104000A060105000A030106000A05" + $"0107000A0001081001178400040A070109000A08010A000A09010B000A00010C" + $"1815FF01178200040A0C010C000A00010C38251B15FF01178200040A0C010C20" + $"251B0A00010C382A1615FF01178200040A0B010C202A160A00010C382F1115FF" + $"01178200040A0A010C202F11" }; #else // HAIKU_TARGET_PLATFORM_HAIKU From superstippi at gmx.de Sun Apr 15 01:12:17 2007 From: superstippi at gmx.de (Stephan Assmus) Date: Sun, 15 Apr 2007 01:12:17 +0200 Subject: [Haiku-commits] r20684 - haiku/trunk/src/preferences/filetypes In-Reply-To: <48176482579-BeMail@zon> References: <48176482579-BeMail@zon> Message-ID: <20070415011217.715.1@stippis.nameserver> On 2007-04-15 at 00:53:37 [+0200], Axel D?rfler wrote: > stippi at BerliOS wrote: > > Log: > > * added vector icons for application and supported types > > * added "icon heap" icon > > * implemented loading vector icon for "icon heap" > > Cool, thanks! :-) No worries! :-) Best regards, -Stephan From stippi at mail.berlios.de Sun Apr 15 01:13:18 2007 From: stippi at mail.berlios.de (stippi at BerliOS) Date: Sun, 15 Apr 2007 01:13:18 +0200 Subject: [Haiku-commits] r20687 - haiku/trunk/src/preferences/media Message-ID: <200704142313.l3ENDIXq019297@sheep.berlios.de> Author: stippi Date: 2007-04-15 01:13:18 +0200 (Sun, 15 Apr 2007) New Revision: 20687 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20687&view=rev Modified: haiku/trunk/src/preferences/media/media.rdef Log: * created vector icon Modified: haiku/trunk/src/preferences/media/media.rdef =================================================================== --- haiku/trunk/src/preferences/media/media.rdef 2007-04-14 23:07:37 UTC (rev 20686) +++ haiku/trunk/src/preferences/media/media.rdef 2007-04-14 23:13:18 UTC (rev 20687) @@ -20,6 +20,31 @@ resource file_types message; +#ifdef HAIKU_TARGET_PLATFORM_HAIKU + +resource vector_icon { + $"6E6369660A0500040063020006023A9CFB3B0744BD682D3CF09A498CD74A42F0" + $"00798291FF5B697D0200060239D8C838576FBB1EA33C90064B3B284A08CD0024" + $"344BFF485567020006023D00000000000000004000004A000044000000C6CBD2" + $"FF666F7D032A264005C70200160236227D3657C8B769C1371C1E4889A148271F" + $"00FFFFC902001602375F6837E895BD682D3CF09A498CD7464BC300E2FF890597" + $"0C0A045CC11A465A4C5A60C1E60A062240224646585A445A38382C0A04465022" + $"40224646580A0446505A385A4446580A0446505A38382C22400A06BD9BB7BFBD" + $"B0B86EBE7CB8BAB8B6BE1AB8CABE64BF28B86B0A06B7E9BDB4BDAFB86EBD9BB7" + $"BFB73DBD9DB8CABE64B8B5BE1A0A04B8B5BE1ABE7BB8BABDAFB86EB7E9BDB406" + $"079A362E302B333631393436333131BA61BA13B92FB97A0606BA0E2E302B332E" + $"34B7FBBAABB92DBB44313634333131BA5FBA12B92DB979060566032B33363139" + $"362E34B92DBB44B7FBBAAB0A0431363139343634331A0A010100000A00010110" + $"01178400040A020102000A030103000A040104000A0601052020240A03010620" + $"20240A0501072020240A00010830212401178400040A0701092021240A08010A" + $"2021240A09010B2021240A0601052029280A0301062029280A0501072029280A" + $"00010830322101178400040A0701092032210A08010A2032210A09010B203221" + $"0A06010520332C0A03010620332C0A05010720332C0A00010830372A01178400" + $"040A07010920372A0A08010A20372A0A09010B20372A" +}; + +#else // HAIKU_TARGET_PLATFORM_HAIKU + resource large_icon { $"FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF00FFFFFFFFFFFFFFFFFFFFFFFFFFFF" $"FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF00FFFFFFFFFFFFFFFFFFFFFFFFFFFF" @@ -73,3 +98,6 @@ $"FFFFFFFFFFFF002B2F00FF0404040F0F" $"FFFFFFFFFFFFFF00000E0F0F0F0FFFFF" }; + +#endif // HAIKU_TARGET_PLATFORM_HAIKU + From stippi at mail.berlios.de Sun Apr 15 01:22:51 2007 From: stippi at mail.berlios.de (stippi at BerliOS) Date: Sun, 15 Apr 2007 01:22:51 +0200 Subject: [Haiku-commits] r20688 - haiku/trunk/src/add-ons/tracker/filetype Message-ID: <200704142322.l3ENMpQL006101@sheep.berlios.de> Author: stippi Date: 2007-04-15 01:22:51 +0200 (Sun, 15 Apr 2007) New Revision: 20688 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20688&view=rev Modified: haiku/trunk/src/add-ons/tracker/filetype/FileType.rdef haiku/trunk/src/add-ons/tracker/filetype/Jamfile Log: * added same vector icon as FileTypes preflet, but somehow the resources are not added for the "Addon" target type? Ingo? Modified: haiku/trunk/src/add-ons/tracker/filetype/FileType.rdef =================================================================== --- haiku/trunk/src/add-ons/tracker/filetype/FileType.rdef 2007-04-14 23:13:18 UTC (rev 20687) +++ haiku/trunk/src/add-ons/tracker/filetype/FileType.rdef 2007-04-14 23:22:51 UTC (rev 20688) @@ -25,25 +25,34 @@ long_info = "FileType, Copyright 2006 Haiku Inc." }; -resource mini_icon array { - $"FFFFFFFFFFFFFFFF020200FFFFFFFFFF" - $"FFFFFFFFFFFFFF04151E1500FFFFFFFF" - $"FFFFFFFFFFFFFF021D1E1C00FFFFFFFF" - $"FFFFFFFF00FFFF00151B1600FFFFFFFF" - $"FFFFFF003F0000FA0000000000FFFFFF" - $"FFFF003FFD0000F9F9FAFAFAFA00FFFF" - $"FF003FFEFDFD00F9F9F9F97D7D00FFFF" - $"003F62FE89FD00F9F9F900007D00FFFF" - $"FF003FB0FD89FA00F90060600000FFFF" - $"FF003FFEB0FD620000606060606000FF" - $"FFFF003FFD89FA003F3F606060D500FF" - $"FFFF003FFDFDFA00ACAC3F3FD5D5000E" - $"FFFFFF003FFD0000ACACACACD5D5000E" - $"FFFFFF003F000E00ACACACACD5D5000E" - $"FFFFFFFF000E0E0E0000ACACD5000E0E" - $"FFFFFFFFFFFFFFFFFFFF0000000E0EFF" +#ifdef HAIKU_TARGET_PLATFORM_HAIKU + +resource vector_icon { + $"6E6369660C0500040169020006023CADF43D104EBF02CA3EA2224BF02046648D" + $"00FFDB97FFFCAF29020006023A6496BA3F153EBCDD3EEA91492CB5C09D5100FF" + $"F7EAFEFDD17B020006023AB3673751B2BC59783FD2D74C71F846F85900C85805" + $"FFF06306020106033AC71C0000000000003AB6DB4A6A0045300000F2F2F2FFBC" + $"A184AB7D7A7A02000602388A280000000000004000004AF00000000000C85804" + $"FFDC952F020006023B37D13A0397BB629E3CB4584A3EDF4A1E9400C6D7F5FF6B" + $"94DD020006023C71E33A0C78BA15E43C7D214B02AA49855700E3EDFFFF9EC2FF" + $"0200060239AB92381275BA365C3BEB2A4B2A844A9A5F00003CB0FF2C62D00200" + $"06033AC7B03884E3B903663B534D48B61F4958AE00FCFFDC7FF8F0BCFFF4DC8A" + $"020006023A7061B88A6E3B1AAE3CFAD946AC4F48C79100000000FFA9A06E130A" + $"053E303E4452445232452C0A043E303E444C444C360A063E304C3652324630C3" + $"BBB893452C0A044C44524452324C36020448224B22452242284225422B482E45" + $"2E4B2E4E284E2B4E250605E2024A60505A5660506054604C584A0A0346305232" + $"4A2E0A063A443A564A5E56535642463C0A043A443A564A5E4A4B0A043A444A4B" + $"5642463C0A044A4B4A5E565356420604AE342D223822382C4632524247080233" + $"33273B080231BCA9B6AFBEB40802BC10BCA92B40080237BDE8B821C0BF0802BC" + $"1DBF66B8A0C1D708023BBFF3304808023B44BA12C42E100A010105000A00010B" + $"1815FF01178400040A00010B18001501178500040A0A010B000A0B070E0D0C10" + $"0F12111815FF01178100040A0001001001178400040A020101000A030102000A" + $"040103000A060106000A0001041001178400040A050104000A00010710011784" + $"00040A070108000A09010A000A08010900" }; +#else // HAIKU_TARGET_PLATFORM_HAIKU + resource large_icon array { $"FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF02020008FFFFFFFFFFFFFFFFFFFF" $"FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF041B17110802FFFFFFFFFFFFFFFFFF" @@ -78,3 +87,25 @@ $"FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF0000ACD5000E0E0EFFFFFFFFFFFFFF" $"FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF00000E0E0EFFFFFFFFFFFFFFFF" }; + +resource mini_icon array { + $"FFFFFFFFFFFFFFFF020200FFFFFFFFFF" + $"FFFFFFFFFFFFFF04151E1500FFFFFFFF" + $"FFFFFFFFFFFFFF021D1E1C00FFFFFFFF" + $"FFFFFFFF00FFFF00151B1600FFFFFFFF" + $"FFFFFF003F0000FA0000000000FFFFFF" + $"FFFF003FFD0000F9F9FAFAFAFA00FFFF" + $"FF003FFEFDFD00F9F9F9F97D7D00FFFF" + $"003F62FE89FD00F9F9F900007D00FFFF" + $"FF003FB0FD89FA00F90060600000FFFF" + $"FF003FFEB0FD620000606060606000FF" + $"FFFF003FFD89FA003F3F606060D500FF" + $"FFFF003FFDFDFA00ACAC3F3FD5D5000E" + $"FFFFFF003FFD0000ACACACACD5D5000E" + $"FFFFFF003F000E00ACACACACD5D5000E" + $"FFFFFFFF000E0E0E0000ACACD5000E0E" + $"FFFFFFFFFFFFFFFFFFFF0000000E0EFF" +}; + +#endif // HAIKU_TARGET_PLATFORM_HAIKU + Modified: haiku/trunk/src/add-ons/tracker/filetype/Jamfile =================================================================== --- haiku/trunk/src/add-ons/tracker/filetype/Jamfile 2007-04-14 23:13:18 UTC (rev 20687) +++ haiku/trunk/src/add-ons/tracker/filetype/Jamfile 2007-04-14 23:22:51 UTC (rev 20688) @@ -2,6 +2,7 @@ SetSubDirSupportedPlatformsBeOSCompatible ; +# TODO: does not seem to work: AddResources FileType-F : FileType.rdef ; Addon FileType-F : From stippi at mail.berlios.de Sun Apr 15 02:41:25 2007 From: stippi at mail.berlios.de (stippi at BerliOS) Date: Sun, 15 Apr 2007 02:41:25 +0200 Subject: [Haiku-commits] r20689 - haiku/trunk/src/apps/fontdemo Message-ID: <200704150041.l3F0fP1R011692@sheep.berlios.de> Author: stippi Date: 2007-04-15 02:41:24 +0200 (Sun, 15 Apr 2007) New Revision: 20689 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20689&view=rev Modified: haiku/trunk/src/apps/fontdemo/FontDemo.rdef Log: * copied vector icon from font preflet Modified: haiku/trunk/src/apps/fontdemo/FontDemo.rdef =================================================================== --- haiku/trunk/src/apps/fontdemo/FontDemo.rdef 2007-04-14 23:22:51 UTC (rev 20688) +++ haiku/trunk/src/apps/fontdemo/FontDemo.rdef 2007-04-15 00:41:24 UTC (rev 20689) @@ -18,6 +18,26 @@ resource app_flags B_SINGLE_LAUNCH; +#ifdef HAIKU_TARGET_PLATFORM_HAIKU + +resource vector_icon { + $"6E63696608050004005F020006023D5F39368F62B905F93FFB6B4ACB36BEDE32" + $"00032288FF1944E7020006023AAFCC3BFAA8BF50A93E3D044B460F48AEEC0002" + $"0258FF1919E7020006023BA7EB3CD6E4BF5D013E2A4C4B0DDA478DDF0097C3FF" + $"FF376AFF02000602380D3A384399BEF6CA3EAF9C4B2833C6F2DC00E3ECFFFFAC" + $"C7FF02000602371F7FB98A813FA8F13D3A58C4B8AC48909300CEDEFFFF3778FF" + $"02000602371F7FB98A813FA8F13D3A58C60C5648909300BADAFFFF032E850B0A" + $"0432482C503E543C4B0A0550485452485E565A60500A0A47273D24322A244A2C" + $"4E34C2B0BE5BC408BFBFC94F485C52520A0447273C2D485C52520A08BE5AC40E" + $"4058485CBE3D2D322A244A2C4EB935C20F0A03BC12BB843BC1D3B9EBC0700A03" + $"BC12BB84BCC2BE1AB9EBC0700A03BD75C0B13BC1D3B9EBC0700A03BCC2BE1ABD" + $"75C0B1B9EBC0700A032C4E34C2B0B939C20A0A043D24322A3C2D4727090A0102" + $"0001000A0001021001178400040A020103000A030109000A030106000A060107" + $"000A070108000A04020405000A05010A00" +}; + +#else // HAIKU_TARGET_PLATFORM_HAIKU + resource large_icon array { $"FFFFFFFFFFFFFFFFFFFFFFFFFF0000FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF" $"FFFFFFFFFFFFFFFFFFFFFFFF008C8C0000FFFFFFFFFFFFFFFFFFFFFFFFFFFFFF" @@ -71,3 +91,5 @@ $"FFFFFFFFFFFFFF00B28C21000F0E0FFF" $"FFFFFFFFFFFFFFFF0000000E0F0FFFFF" }; + +#endif // HAIKU_TARGET_PLATFORM_HAIKU From bonefish at cs.tu-berlin.de Sun Apr 15 03:53:45 2007 From: bonefish at cs.tu-berlin.de (Ingo Weinhold) Date: Sun, 15 Apr 2007 03:53:45 +0200 Subject: [Haiku-commits] r20688 - haiku/trunk/src/add-ons/tracker/filetype In-Reply-To: <200704142322.l3ENMpQL006101@sheep.berlios.de> References: <200704142322.l3ENMpQL006101@sheep.berlios.de> Message-ID: <20070415035345.4747.3@cs.tu-berlin.de> On 2007-04-15 at 01:22:51 [+0200], stippi at BerliOS wrote: > Author: stippi > Date: 2007-04-15 01:22:51 +0200 (Sun, 15 Apr 2007) > New Revision: 20688 > ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20688&view=rev > > Modified: > haiku/trunk/src/add-ons/tracker/filetype/FileType.rdef > haiku/trunk/src/add-ons/tracker/filetype/Jamfile > Log: > * added same vector icon as FileTypes preflet, but somehow the > resources are not added for the "Addon" target type? Ingo? Works fine here (tested under Linux). What exactly goes wrong on your machine? CU, Ingo From hugosantos at mail.berlios.de Sun Apr 15 04:44:18 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Sun, 15 Apr 2007 04:44:18 +0200 Subject: [Haiku-commits] r20690 - in haiku/trunk: headers/posix/netinet headers/private/net src/add-ons/kernel/network/protocols/ipv4 src/add-ons/kernel/network/stack Message-ID: <200704150244.l3F2iIgL017639@sheep.berlios.de> Author: hugosantos Date: 2007-04-15 04:44:01 +0200 (Sun, 15 Apr 2007) New Revision: 20690 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20690&view=rev Added: haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/multicast.cpp haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/multicast.h Modified: haiku/trunk/headers/posix/netinet/in.h haiku/trunk/headers/private/net/net_datalink.h haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/Jamfile haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp Log: initial steps towards IPv4 Multicast Filter Delta API (RFC 3678) Modified: haiku/trunk/headers/posix/netinet/in.h =================================================================== --- haiku/trunk/headers/posix/netinet/in.h 2007-04-15 00:41:24 UTC (rev 20689) +++ haiku/trunk/headers/posix/netinet/in.h 2007-04-15 02:44:01 UTC (rev 20690) @@ -80,6 +80,30 @@ }; /* the address is therefore at sin_addr.s_addr */ +/* RFC 3678 - Socket Interface Extensions for Multicast Source Filters */ + +struct ip_mreq { + struct in_addr imr_multiaddr; /* IP address of group */ + struct in_addr imr_interface; /* IP address of interface */ +}; + +struct ip_mreq_source { + struct in_addr imr_multiaddr; /* IP address of group */ + struct in_addr imr_sourceaddr; /* IP address of source */ + struct in_addr imr_interface; /* IP address of interface */ +}; + +struct group_req { + uint32_t gr_interface; /* interface index */ + struct sockaddr_storage gr_group; /* group address */ +}; + +struct group_source_req { + uint32_t gsr_interface; /* interface index */ + struct sockaddr_storage gsr_group; /* group address */ + struct sockaddr_storage gsr_source; /* source address */ +}; + /* * Options for use with [gs]etsockopt at the IP level. * First word of comment is data type; bool is stored in int. @@ -97,6 +121,16 @@ #define IP_MULTICAST_LOOP 11 /* u_char; set/get IP multicast loopback */ #define IP_ADD_MEMBERSHIP 12 /* ip_mreq; add an IP group membership */ #define IP_DROP_MEMBERSHIP 13 /* ip_mreq; drop an IP group membership */ +#define IP_BLOCK_SOURCE 14 /* ip_mreq_source */ +#define IP_UNBLOCK_SOURCE 15 /* ip_mreq_source */ +#define IP_ADD_SOURCE_MEMBERSHIP 16 /* ip_mreq_source */ +#define IP_DROP_SOURCE_MEMBERSHIP 17 /* ip_mreq_source */ +#define MCAST_JOIN_GROUP 18 /* group_req */ +#define MCAST_BLOCK_SOURCE 19 /* group_source_req */ +#define MCAST_UNBLOCK_SOURCE 20 /* group_source_req */ +#define MCAST_LEAVE_GROUP 21 /* group_req */ +#define MCAST_JOIN_SOURCE_GROUP 22 /* group_source_req */ +#define MCAST_LEAVE_SOURCE_GROUP 23 /* group_source_req */ #define __IPADDR(x) ((uint32_t)htonl((uint32_t)(x))) Modified: haiku/trunk/headers/private/net/net_datalink.h =================================================================== --- haiku/trunk/headers/private/net/net_datalink.h 2007-04-15 00:41:24 UTC (rev 20689) +++ haiku/trunk/headers/private/net/net_datalink.h 2007-04-15 02:44:01 UTC (rev 20690) @@ -71,6 +71,8 @@ const struct sockaddr *address, net_interface **_interface, uint32 *_matchedType); + net_interface *(*get_interface_with_address)(struct net_domain *domain, + const struct sockaddr *address); // routes status_t (*add_route)(struct net_domain *domain, Modified: haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/Jamfile =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/Jamfile 2007-04-15 00:41:24 UTC (rev 20689) +++ haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/Jamfile 2007-04-15 02:44:01 UTC (rev 20690) @@ -15,6 +15,7 @@ KernelAddon ipv4 : ipv4.cpp ipv4_address.cpp + multicast.cpp ; # Installation Modified: haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp 2007-04-15 00:41:24 UTC (rev 20689) +++ haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp 2007-04-15 02:44:01 UTC (rev 20690) @@ -8,6 +8,7 @@ #include "ipv4_address.h" +#include "multicast.h" #include #include @@ -126,6 +127,8 @@ uint8 service_type; uint8 time_to_live; uint32 flags; + + MulticastFilter multicast_filter; }; // protocol flags @@ -618,6 +621,86 @@ } +static status_t +ipv4_delta_group(MulticastFilter::GroupState *group, int option, + net_interface *interface, in_addr *sourceAddr) +{ + switch (option) { + case IP_ADD_MEMBERSHIP: + return group->Add(interface); + case IP_DROP_MEMBERSHIP: + return group->Drop(interface); + case IP_BLOCK_SOURCE: + return group->BlockSource(interface, *sourceAddr); + case IP_UNBLOCK_SOURCE: + return group->UnblockSource(interface, *sourceAddr); + case IP_ADD_SOURCE_MEMBERSHIP: + return group->AddSSM(interface, *sourceAddr); + case IP_DROP_SOURCE_MEMBERSHIP: + return group->DropSSM(interface, *sourceAddr); + } + + return B_ERROR; +} + + +static status_t +ipv4_delta_membership(ipv4_protocol *protocol, int option, + in_addr *interfaceAddr, in_addr *groupAddr, in_addr *sourceAddr) +{ + net_interface *interface = NULL; + + if (interfaceAddr->s_addr == INADDR_ANY) { + interface = sDatalinkModule->get_interface_with_address(sDomain, NULL); + } else { + sockaddr_in address; + + memset(&address, 0, sizeof(address)); + address.sin_family = AF_INET; + address.sin_len = sizeof(address); + address.sin_addr = *interfaceAddr; + + interface = sDatalinkModule->get_interface_with_address(sDomain, + (sockaddr *)&address); + } + + if (interface == NULL) + return ENODEV; + + MulticastFilter &filter = protocol->multicast_filter; + MulticastFilter::GroupState *group = NULL; + + switch (option) { + case IP_ADD_MEMBERSHIP: + case IP_ADD_SOURCE_MEMBERSHIP: + group = filter.GetGroup(*groupAddr, true); + if (group == NULL) + return ENOBUFS; + break; + + case IP_DROP_MEMBERSHIP: + case IP_BLOCK_SOURCE: + case IP_UNBLOCK_SOURCE: + case IP_DROP_SOURCE_MEMBERSHIP: + group = filter.GetGroup(*groupAddr, false); + if (group == NULL) { + if (option == IP_DROP_SOURCE_MEMBERSHIP + || option == IP_DROP_SOURCE_MEMBERSHIP) + return EADDRNOTAVAIL; + else + return EINVAL; + } + break; + } + + status_t status = ipv4_delta_group(group, option, interface, sourceAddr); + + filter.ReturnGroup(group); + + return status; +} + + // #pragma mark - @@ -756,6 +839,17 @@ return user_memcpy(value, &serviceType, sizeof(serviceType)); } + case IP_ADD_MEMBERSHIP: + case IP_DROP_MEMBERSHIP: + case IP_BLOCK_SOURCE: + case IP_UNBLOCK_SOURCE: + case IP_ADD_SOURCE_MEMBERSHIP: + case IP_DROP_SOURCE_MEMBERSHIP: + // RFC 3678, Section 4.1: + // ``An error of EOPNOTSUPP is returned if these options are + // used with getsockopt().'' + return EOPNOTSUPP; + default: dprintf("IPv4::control(): get unknown option: %d\n", option); return ENOPROTOOPT; @@ -804,6 +898,34 @@ return B_OK; } + case IP_ADD_MEMBERSHIP: + case IP_DROP_MEMBERSHIP: + { + ip_mreq mreq; + if (*_length != sizeof(ip_mreq)) + return B_BAD_VALUE; + if (user_memcpy(&mreq, value, sizeof(ip_mreq)) < B_OK) + return B_BAD_ADDRESS; + + return ipv4_delta_membership(protocol, option, &mreq.imr_interface, + &mreq.imr_multiaddr, NULL); + } + + case IP_BLOCK_SOURCE: + case IP_UNBLOCK_SOURCE: + case IP_ADD_SOURCE_MEMBERSHIP: + case IP_DROP_SOURCE_MEMBERSHIP: + { + ip_mreq_source mreq; + if (*_length != sizeof(ip_mreq_source)) + return B_BAD_VALUE; + if (user_memcpy(&mreq, value, sizeof(ip_mreq_source)) < B_OK) + return B_BAD_ADDRESS; + + return ipv4_delta_membership(protocol, option, &mreq.imr_interface, + &mreq.imr_multiaddr, &mreq.imr_sourceaddr); + } + default: dprintf("IPv4::control(): set unknown option: %d\n", option); return ENOPROTOOPT; Added: haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/multicast.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/multicast.cpp 2007-04-15 00:41:24 UTC (rev 20689) +++ haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/multicast.cpp 2007-04-15 02:44:01 UTC (rev 20690) @@ -0,0 +1,272 @@ +/* + * Copyright 2007, Haiku, Inc. All Rights Reserved. + * Distributed under the terms of the MIT License. + * + * Authors: + * Hugo Santos, hugosantos at gmail.com + */ + +#include "multicast.h" + +#include + +#include + +template class MulticastFilter; +template class MulticastGroupState; +template class MulticastGroupInterfaceState; + +static inline bool +operator==(const in_addr &a1, const in_addr &a2) +{ + return a1.s_addr == a2.s_addr; +} + +using std::nothrow; + + +template +MulticastGroupInterfaceState::MulticastGroupInterfaceState( + net_interface *interface) + : fInterface(interface) +{ +} + + +template +MulticastGroupInterfaceState::~MulticastGroupInterfaceState() +{ + SourceList::Iterator iterator = fSources.GetIterator(); + while (iterator.HasNext()) { + _Remove(iterator.Next()); + } +} + + +template status_t +MulticastGroupInterfaceState::Add(const AddressType &address) +{ + return _Get(address, true) ? B_OK : ENOBUFS; +} + + +template status_t +MulticastGroupInterfaceState::Remove(const AddressType &address) +{ + Source *state = _Get(address, false); + if (state == NULL) + return EADDRNOTAVAIL; + + _Remove(state); + return B_OK; +} + + +template MulticastGroupInterfaceState::Source * +MulticastGroupInterfaceState::_Get(const AddressType &address, + bool create) +{ + SourceList::Iterator iterator = fSources.GetIterator(); + while (iterator.HasNext()) { + Source *state = iterator.Next(); + if (state->address == address) + return state; + } + + if (!create) + return false; + + Source *state = new (nothrow) Source; + if (state) { + state->address = address; + fSources.Add(state); + } + + return state; +} + + +template void +MulticastGroupInterfaceState::_Remove(Source *state) +{ + fSources.Remove(state); + delete state; +} + + +template +MulticastGroupState::MulticastGroupState(const AddressType &address) + : fMulticastAddress(address), fFilterMode(kInclude) +{ +} + + +template +MulticastGroupState::~MulticastGroupState() +{ + InterfaceList::Iterator iterator = fInterfaces.GetIterator(); + while (iterator.HasNext()) + _RemoveInterface(iterator.Next()); +} + + +template status_t +MulticastGroupState::Add(net_interface *interface) +{ + if (fFilterMode == kInclude && !fInterfaces.IsEmpty()) + return EINVAL; + + fFilterMode = kExclude; + + return _GetInterface(interface, true) != NULL ? B_OK : ENOBUFS; +} + + +template status_t +MulticastGroupState::Drop(net_interface *interface) +{ + InterfaceState *state = _GetInterface(interface, false); + if (state == NULL) + return EADDRNOTAVAIL; + + _RemoveInterface(state); + + if (fInterfaces.IsEmpty()) + fFilterMode = kInclude; + + return B_OK; +} + + +template status_t +MulticastGroupState::BlockSource(net_interface *interface, + const AddressType &sourceAddress) +{ + if (fFilterMode != kExclude) + return EINVAL; + + InterfaceState *state = _GetInterface(interface, false); + if (state == NULL) + return EINVAL; + + return state->Add(sourceAddress); +} + + +template status_t +MulticastGroupState::UnblockSource(net_interface *interface, + const AddressType &sourceAddress) +{ + if (fFilterMode != kExclude) + return EINVAL; + + InterfaceState *state = _GetInterface(interface, false); + if (state == NULL) + return EINVAL; + + return state->Remove(sourceAddress); +} + +template status_t +MulticastGroupState::AddSSM(net_interface *interface, + const AddressType &sourceAddress) +{ + if (fFilterMode == kExclude) + return EINVAL; + + InterfaceState *state = _GetInterface(interface, true); + if (state == NULL) + return ENOBUFS; + + return state->Add(sourceAddress); +} + + +template status_t +MulticastGroupState::DropSSM(net_interface *interface, + const AddressType &sourceAddress) +{ + if (fFilterMode == kExclude) + return EINVAL; + + InterfaceState *state = _GetInterface(interface, false); + if (state == NULL) + return EADDRNOTAVAIL; + + return state->Remove(sourceAddress); +} + + +template MulticastGroupState::InterfaceState * +MulticastGroupState::_GetInterface(net_interface *interface, + bool create) +{ + InterfaceList::Iterator iterator = fInterfaces.GetIterator(); + while (iterator.HasNext()) { + InterfaceState *state = iterator.Next(); + if (state->Interface() == interface) + return state; + } + + if (!create) + return false; + + InterfaceState *state = new (nothrow) InterfaceState(interface); + if (state) + fInterfaces.Add(state); + + return state; +} + + +template void +MulticastGroupState::_RemoveInterface(InterfaceState *state) +{ + fInterfaces.Remove(state); + delete state; +} + + +template +MulticastFilter::~MulticastFilter() +{ + States::Iterator iterator = fStates.GetIterator(); + while (iterator.HasNext()) { + GroupState *state = iterator.Next(); + fStates.Remove(state); + delete state; + } +} + + +template MulticastFilter::GroupState * +MulticastFilter::GetGroup(const AddressType &groupAddress, + bool create) +{ + States::Iterator iterator = fStates.GetIterator(); + + while (iterator.HasNext()) { + GroupState *state = iterator.Next(); + if (state->Address() == groupAddress) + return state; + } + + if (!create) + return NULL; + + GroupState *state = new (nothrow) GroupState(groupAddress); + if (state) + fStates.Add(state); + return state; +} + + +template void +MulticastFilter::ReturnGroup(GroupState *group) +{ + if (group->IsEmpty()) { + fStates.Remove(group); + delete group; + } +} + Added: haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/multicast.h =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/multicast.h 2007-04-15 00:41:24 UTC (rev 20689) +++ haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/multicast.h 2007-04-15 02:44:01 UTC (rev 20690) @@ -0,0 +1,106 @@ +/* + * Copyright 2007, Haiku, Inc. All Rights Reserved. + * Distributed under the terms of the MIT License. + * + * Authors: + * Hugo Santos, hugosantos at gmail.com + */ + +#ifndef _PRIVATE_MULTICAST_H_ +#define _PRIVATE_MULTICAST_H_ + +#include +#include + +struct net_interface; + +template +struct MulticastSource { + AddressType address; + list_link link; +}; + +template +class MulticastGroupInterfaceState { +public: + MulticastGroupInterfaceState(net_interface *interface); + ~MulticastGroupInterfaceState(); + + net_interface *Interface() const { return fInterface; } + + status_t Add(const AddressType &address); + status_t Remove(const AddressType &address); + + list_link link; +private: + typedef MulticastSource Source; + typedef DoublyLinkedListCLink SourceLink; + typedef DoublyLinkedList SourceList; + + Source *_Get(const AddressType &address, bool create); + void _Remove(Source *state); + + net_interface *fInterface; + // TODO make this an hash table as well + SourceList fSources; +}; + +template +class MulticastGroupState { +public: + MulticastGroupState(const AddressType &address); + ~MulticastGroupState(); + + const AddressType &Address() const { return fMulticastAddress; } + bool IsEmpty() const + { return fFilterMode == kInclude && fInterfaces.IsEmpty(); } + + status_t Add(net_interface *interface); + status_t Drop(net_interface *interface); + status_t BlockSource(net_interface *interface, + const AddressType &sourceAddress); + status_t UnblockSource(net_interface *interface, + const AddressType &sourceAddress); + status_t AddSSM(net_interface *interface, + const AddressType &sourceAddress); + status_t DropSSM(net_interface *interface, + const AddressType &sourceAddress); + + list_link link; +private: + typedef MulticastGroupInterfaceState InterfaceState; + typedef DoublyLinkedListCLink InterfaceStateLink; + typedef DoublyLinkedList InterfaceList; + + InterfaceState *_GetInterface(net_interface *interface, bool create); + void _RemoveInterface(InterfaceState *state); + + enum FilterMode { + kInclude, + kExclude + }; + + AddressType fMulticastAddress; + FilterMode fFilterMode; + InterfaceList fInterfaces; +}; + +template +class MulticastFilter { +public: + typedef MulticastGroupState GroupState; + + ~MulticastFilter(); + + GroupState *GetGroup(const AddressType &groupAddress, bool create); + void ReturnGroup(GroupState *group); + +private: + typedef DoublyLinkedListCLink GroupStateLink; + typedef DoublyLinkedList States; + + // TODO change this into an hash table or tree + States fStates; +}; + +#endif Modified: haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp 2007-04-15 00:41:24 UTC (rev 20689) +++ haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp 2007-04-15 02:44:01 UTC (rev 20690) @@ -419,6 +419,36 @@ } +net_interface * +datalink_get_interface_with_address(net_domain *_domain, + const sockaddr *address) +{ + net_domain_private *domain = (net_domain_private *)_domain; + if (domain == NULL) + return NULL; + + BenaphoreLocker _(domain->lock); + + net_interface *interface = NULL; + + while (true) { + interface = (net_interface *)list_get_next_item( + &domain->interfaces, interface); + if (interface == NULL) + break; + + if (address == NULL) + return interface; + + if (domain->address_module->equal_addresses(interface->address, + address)) + return interface; + } + + return NULL; +} + + static status_t datalink_std_ops(int32 op, ...) { @@ -745,6 +775,7 @@ datalink_control, datalink_send_data, datalink_is_local_address, + datalink_get_interface_with_address, add_route, remove_route, From hugosantos at mail.berlios.de Sun Apr 15 05:07:40 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Sun, 15 Apr 2007 05:07:40 +0200 Subject: [Haiku-commits] r20691 - in haiku/trunk: headers/private/net src/add-ons/kernel/network/protocols/ipv4 src/add-ons/kernel/network/stack Message-ID: <200704150307.l3F37e4p018844@sheep.berlios.de> Author: hugosantos Date: 2007-04-15 05:07:28 +0200 (Sun, 15 Apr 2007) New Revision: 20691 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20691&view=rev Modified: haiku/trunk/headers/private/net/net_datalink.h haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/multicast.cpp haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/multicast.h haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp Log: support RFC 3678's Protocol-Independent setsockopt()s for IPv4 multicast. Modified: haiku/trunk/headers/private/net/net_datalink.h =================================================================== --- haiku/trunk/headers/private/net/net_datalink.h 2007-04-15 02:44:01 UTC (rev 20690) +++ haiku/trunk/headers/private/net/net_datalink.h 2007-04-15 03:07:28 UTC (rev 20691) @@ -71,6 +71,7 @@ const struct sockaddr *address, net_interface **_interface, uint32 *_matchedType); + net_interface *(*get_interface)(struct net_domain *domain, uint32 index); net_interface *(*get_interface_with_address)(struct net_domain *domain, const struct sockaddr *address); Modified: haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp 2007-04-15 02:44:01 UTC (rev 20690) +++ haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp 2007-04-15 03:07:28 UTC (rev 20691) @@ -123,6 +123,9 @@ }; struct ipv4_protocol : net_protocol { + ipv4_protocol(net_socket *socket) + : multicast_filter(socket) {} + RawSocket *raw; uint8 service_type; uint8 time_to_live; @@ -623,7 +626,7 @@ static status_t ipv4_delta_group(MulticastFilter::GroupState *group, int option, - net_interface *interface, in_addr *sourceAddr) + net_interface *interface, const in_addr *sourceAddr) { switch (option) { case IP_ADD_MEMBERSHIP: @@ -646,27 +649,9 @@ static status_t ipv4_delta_membership(ipv4_protocol *protocol, int option, - in_addr *interfaceAddr, in_addr *groupAddr, in_addr *sourceAddr) + net_interface *interface, const in_addr *groupAddr, + const in_addr *sourceAddr) { - net_interface *interface = NULL; - - if (interfaceAddr->s_addr == INADDR_ANY) { - interface = sDatalinkModule->get_interface_with_address(sDomain, NULL); - } else { - sockaddr_in address; - - memset(&address, 0, sizeof(address)); - address.sin_family = AF_INET; - address.sin_len = sizeof(address); - address.sin_addr = *interfaceAddr; - - interface = sDatalinkModule->get_interface_with_address(sDomain, - (sockaddr *)&address); - } - - if (interface == NULL) - return ENODEV; - MulticastFilter &filter = protocol->multicast_filter; MulticastFilter::GroupState *group = NULL; @@ -701,13 +686,68 @@ } +static status_t +ipv4_delta_membership(ipv4_protocol *protocol, int option, + in_addr *interfaceAddr, in_addr *groupAddr, in_addr *sourceAddr) +{ + net_interface *interface = NULL; + + if (interfaceAddr->s_addr == INADDR_ANY) { + interface = sDatalinkModule->get_interface_with_address(sDomain, NULL); + } else { + sockaddr_in address; + + memset(&address, 0, sizeof(address)); + address.sin_family = AF_INET; + address.sin_len = sizeof(address); + address.sin_addr = *interfaceAddr; + + interface = sDatalinkModule->get_interface_with_address(sDomain, + (sockaddr *)&address); + } + + if (interface == NULL) + return ENODEV; + + return ipv4_delta_membership(protocol, option, interface, groupAddr, + sourceAddr); +} + + +static status_t +ipv4_generic_delta_membership(ipv4_protocol *protocol, int option, + uint32 index, const sockaddr_storage *_groupAddr, + const sockaddr_storage *_sourceAddr) +{ + if (_groupAddr->ss_family != AF_INET) + return EINVAL; + + if (_sourceAddr && _sourceAddr->ss_family != AF_INET) + return EINVAL; + + net_interface *interface = sDatalinkModule->get_interface(sDomain, index); + if (interface == NULL) + return ENODEV; + + const in_addr *groupAddr, *sourceAddr = NULL; + + groupAddr = &((const sockaddr_in *)_groupAddr)->sin_addr; + + if (_sourceAddr) + sourceAddr = &((const sockaddr_in *)_sourceAddr)->sin_addr; + + return ipv4_delta_membership(protocol, option, interface, groupAddr, + sourceAddr); +} + + // #pragma mark - net_protocol * ipv4_init_protocol(net_socket *socket) { - ipv4_protocol *protocol = new (std::nothrow) ipv4_protocol; + ipv4_protocol *protocol = new (std::nothrow) ipv4_protocol(socket); if (protocol == NULL) return NULL; @@ -845,6 +885,12 @@ case IP_UNBLOCK_SOURCE: case IP_ADD_SOURCE_MEMBERSHIP: case IP_DROP_SOURCE_MEMBERSHIP: + case MCAST_JOIN_GROUP: + case MCAST_LEAVE_GROUP: + case MCAST_BLOCK_SOURCE: + case MCAST_UNBLOCK_SOURCE: + case MCAST_JOIN_SOURCE_GROUP: + case MCAST_LEAVE_SOURCE_GROUP: // RFC 3678, Section 4.1: // ``An error of EOPNOTSUPP is returned if these options are // used with getsockopt().'' @@ -926,6 +972,34 @@ &mreq.imr_multiaddr, &mreq.imr_sourceaddr); } + case MCAST_JOIN_GROUP: + case MCAST_LEAVE_GROUP: + { + group_req greq; + if (*_length != sizeof(group_req)) + return B_BAD_VALUE; + if (user_memcpy(&greq, value, sizeof(group_req)) < B_OK) + return B_BAD_ADDRESS; + + return ipv4_generic_delta_membership(protocol, option, + greq.gr_interface, &greq.gr_group, NULL); + } + + case MCAST_BLOCK_SOURCE: + case MCAST_UNBLOCK_SOURCE: + case MCAST_JOIN_SOURCE_GROUP: + case MCAST_LEAVE_SOURCE_GROUP: + { + group_source_req greq; + if (*_length != sizeof(group_source_req)) + return B_BAD_VALUE; + if (user_memcpy(&greq, value, sizeof(group_source_req)) < B_OK) + return B_BAD_ADDRESS; + + return ipv4_generic_delta_membership(protocol, option, + greq.gsr_interface, &greq.gsr_group, &greq.gsr_source); + } + default: dprintf("IPv4::control(): set unknown option: %d\n", option); return ENOPROTOOPT; Modified: haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/multicast.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/multicast.cpp 2007-04-15 02:44:01 UTC (rev 20690) +++ haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/multicast.cpp 2007-04-15 03:07:28 UTC (rev 20691) @@ -95,8 +95,9 @@ template -MulticastGroupState::MulticastGroupState(const AddressType &address) - : fMulticastAddress(address), fFilterMode(kInclude) +MulticastGroupState::MulticastGroupState( + MulticastFilter *parent, const AddressType &address) + : fParent(parent), fMulticastAddress(address), fFilterMode(kInclude) { } @@ -228,6 +229,13 @@ template +MulticastFilter::MulticastFilter(net_socket *socket) + : fParent(socket) +{ +} + + +template MulticastFilter::~MulticastFilter() { States::Iterator iterator = fStates.GetIterator(); @@ -254,7 +262,7 @@ if (!create) return NULL; - GroupState *state = new (nothrow) GroupState(groupAddress); + GroupState *state = new (nothrow) GroupState(this, groupAddress); if (state) fStates.Add(state); return state; Modified: haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/multicast.h =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/multicast.h 2007-04-15 02:44:01 UTC (rev 20690) +++ haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/multicast.h 2007-04-15 03:07:28 UTC (rev 20691) @@ -13,7 +13,10 @@ #include struct net_interface; +struct net_socket; +template class MulticastFilter; + template struct MulticastSource { AddressType address; @@ -48,7 +51,8 @@ template class MulticastGroupState { public: - MulticastGroupState(const AddressType &address); + MulticastGroupState(MulticastFilter *parent, + const AddressType &address); ~MulticastGroupState(); const AddressType &Address() const { return fMulticastAddress; } @@ -80,6 +84,7 @@ kExclude }; + MulticastFilter *fParent; AddressType fMulticastAddress; FilterMode fFilterMode; InterfaceList fInterfaces; @@ -90,8 +95,11 @@ public: typedef MulticastGroupState GroupState; + MulticastFilter(net_socket *parent); ~MulticastFilter(); + net_socket *Parent() const { return fParent; } + GroupState *GetGroup(const AddressType &groupAddress, bool create); void ReturnGroup(GroupState *group); @@ -99,6 +107,8 @@ typedef DoublyLinkedListCLink GroupStateLink; typedef DoublyLinkedList States; + net_socket *fParent; + // TODO change this into an hash table or tree States fStates; }; Modified: haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp 2007-04-15 02:44:01 UTC (rev 20690) +++ haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp 2007-04-15 03:07:28 UTC (rev 20691) @@ -449,6 +449,16 @@ } +net_interface * +datalink_get_interface(net_domain *domain, uint32 index) +{ + if (index == 0) + return datalink_get_interface_with_address(domain, NULL); + + return find_interface(domain, index); +} + + static status_t datalink_std_ops(int32 op, ...) { @@ -775,6 +785,7 @@ datalink_control, datalink_send_data, datalink_is_local_address, + datalink_get_interface, datalink_get_interface_with_address, add_route, From hugosantos at mail.berlios.de Sun Apr 15 06:02:10 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Sun, 15 Apr 2007 06:02:10 +0200 Subject: [Haiku-commits] r20692 - haiku/trunk/src/add-ons/kernel/network/protocols/ipv4 Message-ID: <200704150402.l3F42A8d021137@sheep.berlios.de> Author: hugosantos Date: 2007-04-15 06:02:02 +0200 (Sun, 15 Apr 2007) New Revision: 20692 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20692&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp Log: initial IPv4 multicast receive path. Modified: haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp 2007-04-15 03:07:28 UTC (rev 20691) +++ haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp 2007-04-15 04:02:02 UTC (rev 20692) @@ -115,13 +115,30 @@ net_timer fTimer; }; -typedef DoublyLinkedList RawSocketList; +class MulticastGroup { +public: + MulticastGroup(const in_addr &address); + status_t Deliver(net_buffer *buffer); + + static uint32 Hash(void *address, const void *key, uint32 range); + static int Compare(void *address, const void *key); + static int32 NextOffset() { return offsetof(MulticastGroup, fNext); } + + static const int kMaxGroups = 64; + +private: + MulticastGroup *fNext; + in_addr fMulticastAddress; +}; + class RawSocket : public DoublyLinkedListLinkImpl, public DatagramSocket<> { public: RawSocket(net_socket *socket); }; +typedef DoublyLinkedList RawSocketList; + struct ipv4_protocol : net_protocol { ipv4_protocol(net_socket *socket) : multicast_filter(socket) {} @@ -151,6 +168,8 @@ static benaphore sRawSocketsLock; static benaphore sFragmentLock; static hash_table *sFragmentHash; +static benaphore sMulticastGroupsLock; +static hash_table *sMulticastGroups; static net_protocol_module_info *sReceivingProtocol[256]; static benaphore sReceivingProtocolLock; @@ -393,6 +412,46 @@ } +MulticastGroup::MulticastGroup(const in_addr &address) + : fMulticastAddress(address) +{ +} + + +status_t +MulticastGroup::Deliver(net_buffer *buffer) +{ + return B_ERROR; +} + + +int +MulticastGroup::Compare(void *_group, const void *_key) +{ + MulticastGroup *group = (MulticastGroup *)_group; + + return memcmp(&group->fMulticastAddress, _key, sizeof(in_addr)); +} + + +uint32 +MulticastGroup::Hash(void *_group, const void *_key, uint32 range) +{ + const in_addr *address = (const in_addr *)_key; + if (_group != NULL) + address = &((MulticastGroup *)_group)->fMulticastAddress; + + union { + in_addr_t address; + uint8 data[4]; + } addr; + + addr.address = address->s_addr & IN_CLASSD_HOST; + + return (addr.data[0] ^ addr.data[1] ^ addr.data[2] ^ addr.data[3]) % range; +} + + // #pragma mark - @@ -604,6 +663,22 @@ } +static status_t +deliver_multicast(net_buffer *buffer) +{ + BenaphoreLocker _(sMulticastGroupsLock); + + MulticastGroup *group = (MulticastGroup *)hash_lookup(sMulticastGroups, + &buffer->destination); + if (group == NULL) + return B_OK; + + // RAW sockets will be registered just like any other + + return group->Deliver(buffer); +} + + static net_protocol_module_info * receiving_protocol(uint8 protocol) { @@ -1252,15 +1327,27 @@ destination.sin_family = AF_INET; destination.sin_addr.s_addr = header.destination; - // test if the packet is really for us - uint32 matchedAddressType; - if (!sDatalinkModule->is_local_address(sDomain, (sockaddr*)&destination, - &buffer->interface, &matchedAddressType)) { - TRACE(" ReceiveData(): packet was not for us %lx -> %lx", - ntohl(header.source), ntohl(header.destination)); - return B_ERROR; - } - if (matchedAddressType != 0) { + // lower layers notion of Broadcast or Multicast have no relevance to us + buffer->flags &= ~(MSG_BCAST | MSG_MCAST); + + if (header.destination == INADDR_BROADCAST) { + buffer->flags |= MSG_BCAST; + // TODO set incoming interface. we should have some notion from which + // device interface this buffer is coming from. + buffer->interface = NULL; + } else if (IN_MULTICAST(header.destination)) { + buffer->flags |= MSG_MCAST; + buffer->interface = NULL; + } else { + uint32 matchedAddressType = 0; + // test if the packet is really for us + if (!sDatalinkModule->is_local_address(sDomain, (sockaddr*)&destination, + &buffer->interface, &matchedAddressType)) { + TRACE(" ReceiveData(): packet was not for us %lx -> %lx", + ntohl(header.source), ntohl(header.destination)); + return B_ERROR; + } + // copy over special address types (MSG_BCAST or MSG_MCAST): buffer->flags |= matchedAddressType; } @@ -1290,6 +1377,14 @@ } } + if (buffer->flags & MSG_MCAST) { + // Unfortunely historical reasons dictate that the IP multicast + // model be a little different from the unicast one. We deliver + // this frame directly to all sockets registered with interest + // for this multicast group. + return deliver_multicast(buffer); + } + // Since the buffer might have been changed (reassembled fragment) // we must no longer access bufferHeader or header anymore after // this point @@ -1341,14 +1436,24 @@ if (status < B_OK) goto err1; - status = benaphore_init(&sReceivingProtocolLock, "IPv4 receiving protocols"); + status = benaphore_init(&sMulticastGroupsLock, "IPv4 multicast groups"); if (status < B_OK) goto err2; + status = benaphore_init(&sReceivingProtocolLock, "IPv4 receiving protocols"); + if (status < B_OK) + goto err3; + + sMulticastGroups = hash_init(MulticastGroup::kMaxGroups, + MulticastGroup::NextOffset(), &MulticastGroup::Compare, + &MulticastGroup::Hash); + if (sMulticastGroups == NULL) + goto err4; + sFragmentHash = hash_init(MAX_HASH_FRAGMENTS, FragmentPacket::NextOffset(), &FragmentPacket::Compare, &FragmentPacket::Hash); if (sFragmentHash == NULL) - goto err3; + goto err5; new (&sRawSockets) RawSocketList; // static initializers do not work in the kernel, @@ -1358,19 +1463,23 @@ status = gStackModule->register_domain_protocols(AF_INET, SOCK_RAW, 0, "network/protocols/ipv4/v1", NULL); if (status < B_OK) - goto err4; + goto err6; status = gStackModule->register_domain(AF_INET, "internet", &gIPv4Module, &gIPv4AddressModule, &sDomain); if (status < B_OK) - goto err4; + goto err6; return B_OK; +err6: + hash_uninit(sFragmentHash); +err5: + hash_uninit(sMulticastGroups); err4: - hash_uninit(sFragmentHash); + benaphore_destroy(&sReceivingProtocolLock); err3: - benaphore_destroy(&sReceivingProtocolLock); + benaphore_destroy(&sMulticastGroupsLock); err2: benaphore_destroy(&sFragmentLock); err1: @@ -1393,8 +1502,10 @@ gStackModule->unregister_domain(sDomain); benaphore_unlock(&sReceivingProtocolLock); + hash_uninit(sMulticastGroups); hash_uninit(sFragmentHash); + benaphore_destroy(&sMulticastGroupsLock); benaphore_destroy(&sFragmentLock); benaphore_destroy(&sRawSocketsLock); benaphore_destroy(&sReceivingProtocolLock); From hugosantos at mail.berlios.de Sun Apr 15 07:23:28 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Sun, 15 Apr 2007 07:23:28 +0200 Subject: [Haiku-commits] r20693 - in haiku/trunk/src/add-ons/kernel/network: datalink_protocols/arp protocols/ipv4 Message-ID: <200704150523.l3F5NSve002441@sheep.berlios.de> Author: hugosantos Date: 2007-04-15 07:23:18 +0200 (Sun, 15 Apr 2007) New Revision: 20693 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20693&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/datalink_protocols/arp/arp.cpp haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp Log: made IPv4's send path be multicast aware. - also added IP_MULTICAST_TTL support. Modified: haiku/trunk/src/add-ons/kernel/network/datalink_protocols/arp/arp.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/datalink_protocols/arp/arp.cpp 2007-04-15 04:02:02 UTC (rev 20692) +++ haiku/trunk/src/add-ons/kernel/network/datalink_protocols/arp/arp.cpp 2007-04-15 05:23:18 UTC (rev 20693) @@ -780,8 +780,6 @@ { sStackModule->unregister_device_handler(protocol->interface->device, ETHER_FRAME_TYPE | ETHER_TYPE_ARP); - sStackModule->unregister_device_handler(protocol->interface->device, - ETHER_FRAME_TYPE | ETHER_TYPE_IP); delete protocol; return B_OK; @@ -806,7 +804,30 @@ memcpy(&buffer->source, &entry->hardware_address, entry->hardware_address.sdl_len); - if ((buffer->flags & MSG_BCAST) == 0) { + if (buffer->flags & MSG_MCAST) { + // RFC 1112 - Host extensions for IP multicasting + // + // ``An IP host group address is mapped to an Ethernet multicast + // address by placing the low-order 23-bits of the IP address into + // the low-order 23 bits of the Ethernet multicast address + // 01-00-5E-00-00-00 (hex).'' + + sockaddr_dl *destination = (sockaddr_dl *)&buffer->destination; + + memmove(((uint8 *)destination->sdl_data) + 2, + &((sockaddr_in *)&buffer->destination)->sin_addr, sizeof(in_addr)); + + destination->sdl_len = sizeof(sockaddr_dl); + destination->sdl_family = AF_DLI; + destination->sdl_index = 0; + destination->sdl_type = IFT_ETHER; + destination->sdl_e_type = ETHER_TYPE_IP; + destination->sdl_nlen = destination->sdl_slen = 0; + destination->sdl_alen = ETHER_ADDRESS_LENGTH; + + uint32 *data = (uint32 *)destination->sdl_data; + data[0] = (data[0] & htonl(0x7f)) | htonl(0x01005e00); + } else if ((buffer->flags & MSG_BCAST) == 0) { // Lookup destination (we may need to wait for this) entry = arp_entry::Lookup( ((struct sockaddr_in *)&buffer->destination)->sin_addr.s_addr); Modified: haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp 2007-04-15 04:02:02 UTC (rev 20692) +++ haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp 2007-04-15 05:23:18 UTC (rev 20693) @@ -146,15 +146,20 @@ RawSocket *raw; uint8 service_type; uint8 time_to_live; + uint8 multicast_time_to_live; uint32 flags; - MulticastFilter multicast_filter; + MulticastFilter multicast_filter; }; // protocol flags #define IP_FLAG_HEADER_INCLUDED 0x01 +static const int kDefaultTTL = 254; +static const int kDefaultMulticastTTL = 1; + + extern net_protocol_module_info gIPv4Module; // we need this in ipv4_std_ops() for registering the AF_INET domain @@ -699,6 +704,16 @@ } +static inline void +fill_sockaddr_in(sockaddr_in *target, in_addr_t address) +{ + memset(target, 0, sizeof(sockaddr_in)); + target->sin_family = AF_INET; + target->sin_len = sizeof(sockaddr_in); + target->sin_addr.s_addr = address; +} + + static status_t ipv4_delta_group(MulticastFilter::GroupState *group, int option, net_interface *interface, const in_addr *sourceAddr) @@ -771,12 +786,8 @@ interface = sDatalinkModule->get_interface_with_address(sDomain, NULL); } else { sockaddr_in address; + fill_sockaddr_in(&address, interfaceAddr->s_addr); - memset(&address, 0, sizeof(address)); - address.sin_family = AF_INET; - address.sin_len = sizeof(address); - address.sin_addr = *interfaceAddr; - interface = sDatalinkModule->get_interface_with_address(sDomain, (sockaddr *)&address); } @@ -828,7 +839,8 @@ protocol->raw = NULL; protocol->service_type = 0; - protocol->time_to_live = 254; + protocol->time_to_live = kDefaultTTL; + protocol->multicast_time_to_live = kDefaultMulticastTTL; protocol->flags = 0; return protocol; } @@ -914,6 +926,32 @@ } +static status_t +get_int_option(void *target, size_t length, int value) +{ + if (length != sizeof(int)) + return B_BAD_VALUE; + + return user_memcpy(target, &value, sizeof(int)); +} + + +template static status_t +set_int_option(Type &target, void *_value, size_t length) +{ + int value; + + if (length != sizeof(int)) + return B_BAD_VALUE; + + if (user_memcpy(&value, _value, sizeof(int)) < B_OK) + return B_BAD_ADDRESS; + + target = value; + return B_OK; +} + + status_t ipv4_control(net_protocol *_protocol, int level, int option, void *value, size_t *_length) @@ -928,31 +966,18 @@ switch (option) { case IP_HDRINCL: - { - if (*_length != sizeof(int)) - return B_BAD_VALUE; + return get_int_option(value, *_length, + (protocol->flags & IP_FLAG_HEADER_INCLUDED) != 0); - int headerIncluded = (protocol->flags & IP_FLAG_HEADER_INCLUDED) != 0; - return user_memcpy(value, &headerIncluded, sizeof(headerIncluded)); - } - case IP_TTL: - { - if (*_length != sizeof(int)) - return B_BAD_VALUE; + return get_int_option(value, *_length, protocol->time_to_live); - int timeToLive = protocol->time_to_live; - return user_memcpy(value, &timeToLive, sizeof(timeToLive)); - } - case IP_TOS: - { - if (*_length != sizeof(int)) - return B_BAD_VALUE; + return get_int_option(value, *_length, protocol->service_type); - int serviceType = protocol->service_type; - return user_memcpy(value, &serviceType, sizeof(serviceType)); - } + case IP_MULTICAST_TTL: + return get_int_option(value, *_length, + protocol->multicast_time_to_live); case IP_ADD_MEMBERSHIP: case IP_DROP_MEMBERSHIP: @@ -996,28 +1021,14 @@ } case IP_TTL: - { - int timeToLive; - if (*_length != sizeof(int)) - return B_BAD_VALUE; - if (user_memcpy(&timeToLive, value, sizeof(timeToLive)) < B_OK) - return B_BAD_ADDRESS; + return set_int_option(protocol->time_to_live, value, *_length); - protocol->time_to_live = timeToLive; - return B_OK; - } - case IP_TOS: - { - int serviceType; - if (*_length != sizeof(int)) - return B_BAD_VALUE; - if (user_memcpy(&serviceType, value, sizeof(serviceType)) < B_OK) - return B_BAD_ADDRESS; + return set_int_option(protocol->service_type, value, *_length); - protocol->service_type = serviceType; - return B_OK; - } + case IP_MULTICAST_TTL: + return set_int_option(protocol->multicast_time_to_live, value, + *_length); case IP_ADD_MEMBERSHIP: case IP_DROP_MEMBERSHIP: @@ -1148,6 +1159,19 @@ if (protocol != NULL) headerIncluded = (protocol->flags & IP_FLAG_HEADER_INCLUDED) != 0; + buffer->flags &= ~(MSG_BCAST | MSG_MCAST); + + if (destination.sin_addr.s_addr == INADDR_ANY) + return EDESTADDRREQ; + else if (destination.sin_addr.s_addr == INADDR_BROADCAST) { + // TODO check for local broadcast addresses as well? + if (protocol && !(protocol->socket->options & SO_BROADCAST)) + return B_BAD_VALUE; + buffer->flags |= MSG_BCAST; + } else if (IN_MULTICAST(destination.sin_addr.s_addr)) { + buffer->flags |= MSG_MCAST; + } + // Add IP header (if needed) if (!headerIncluded) { @@ -1161,7 +1185,12 @@ header->total_length = htons(buffer->size); header->id = htons(atomic_add(&sPacketID, 1)); header->fragment_offset = 0; - header->time_to_live = protocol ? protocol->time_to_live : 254; + if (protocol) + header->time_to_live = (buffer->flags & MSG_MCAST) ? + protocol->multicast_time_to_live : protocol->time_to_live; + else + header->time_to_live = (buffer->flags & MSG_MCAST) ? + kDefaultMulticastTTL : kDefaultTTL; header->protocol = protocol ? protocol->socket->protocol : buffer->protocol; header->checksum = 0; @@ -1206,18 +1235,25 @@ status_t -ipv4_send_data(net_protocol *protocol, net_buffer *buffer) +ipv4_send_data(net_protocol *_protocol, net_buffer *buffer) { + ipv4_protocol *protocol = (ipv4_protocol *)_protocol; + TRACE_SK(protocol, "SendData(%p [%ld bytes])", buffer, buffer->size); - sockaddr_in &destination = *(sockaddr_in *)&buffer->destination; + if (protocol) { + if (protocol->flags & IP_FLAG_HEADER_INCLUDED) { + if (buffer->size < sizeof(ipv4_header)) + return EINVAL; - if (destination.sin_len == 0 || destination.sin_addr.s_addr == INADDR_ANY) - return EDESTADDRREQ; - else if (destination.sin_addr.s_addr == INADDR_BROADCAST) { - // TODO check for local broadcast addresses as well? - if (protocol && !(protocol->socket->options & SO_BROADCAST)) - return B_BAD_VALUE; + sockaddr_in *source = (sockaddr_in *)&buffer->source; + sockaddr_in *destination = (sockaddr_in *)&buffer->destination; + + fill_sockaddr_in(source, *NetBufferField(buffer)); + fill_sockaddr_in(destination, *NetBufferField(buffer)); + } } net_route *route = NULL; @@ -1319,14 +1355,9 @@ struct sockaddr_in &source = *(struct sockaddr_in *)&buffer->source; struct sockaddr_in &destination = *(struct sockaddr_in *)&buffer->destination; - source.sin_len = sizeof(sockaddr_in); - source.sin_family = AF_INET; - source.sin_addr.s_addr = header.source; + fill_sockaddr_in(&source, header.source); + fill_sockaddr_in(&destination, header.destination); - destination.sin_len = sizeof(sockaddr_in); - destination.sin_family = AF_INET; - destination.sin_addr.s_addr = header.destination; - // lower layers notion of Broadcast or Multicast have no relevance to us buffer->flags &= ~(MSG_BCAST | MSG_MCAST); From hugosantos at mail.berlios.de Sun Apr 15 07:23:39 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Sun, 15 Apr 2007 07:23:39 +0200 Subject: [Haiku-commits] r20694 - in haiku/trunk/src/add-ons/kernel/network/protocols: ipv4 udp Message-ID: <200704150523.l3F5NdIW002457@sheep.berlios.de> Author: hugosantos Date: 2007-04-15 07:23:28 +0200 (Sun, 15 Apr 2007) New Revision: 20694 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20694&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp Log: made UDP's send_data call into IPv4's, so we can handle of the datagram stuff in one place. Modified: haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp 2007-04-15 05:23:18 UTC (rev 20693) +++ haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp 2007-04-15 05:23:28 UTC (rev 20694) @@ -1260,7 +1260,11 @@ status_t status = sDatalinkModule->get_buffer_route(sDomain, buffer, &route); if (status >= B_OK) { - status = ipv4_send_routed_data(protocol, route, buffer); + if (protocol) + status = protocol->socket->first_protocol->module->send_routed_data( + protocol->socket->first_protocol, route, buffer); + else + status = ipv4_send_routed_data(NULL, route, buffer); sDatalinkModule->put_route(sDomain, route); } Modified: haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp 2007-04-15 05:23:18 UTC (rev 20693) +++ haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp 2007-04-15 05:23:28 UTC (rev 20694) @@ -894,15 +894,10 @@ { TRACE_EP("SendData(%p [%lu bytes])", buffer, buffer->size); - net_route *route = NULL; - status_t status = gDatalinkModule->get_buffer_route(Domain(), - buffer, &route); - if (status >= B_OK) { - status = SendRoutedData(buffer, route); - gDatalinkModule->put_route(Domain(), route); - } - - return status; + // This will call into IPv4 which will do all of the obtaining + // routes and other datagram related dirty work and eventually + // call back into our send_routed_data. + return next->module->send_data(next, buffer); } From hugosantos at mail.berlios.de Sun Apr 15 09:31:21 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Sun, 15 Apr 2007 09:31:21 +0200 Subject: [Haiku-commits] r20695 - in haiku/trunk: headers/private/net src/add-ons/kernel/network/protocols/icmp src/add-ons/kernel/network/protocols/ipv4 src/add-ons/kernel/network/protocols/tcp src/add-ons/kernel/network/protocols/udp src/add-ons/kernel/network/stack Message-ID: <200704150731.l3F7VLI4008238@sheep.berlios.de> Author: hugosantos Date: 2007-04-15 09:31:04 +0200 (Sun, 15 Apr 2007) New Revision: 20695 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20695&view=rev Modified: haiku/trunk/headers/private/net/net_protocol.h haiku/trunk/src/add-ons/kernel/network/protocols/icmp/icmp.cpp haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/multicast.cpp haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/multicast.h haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.cpp haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp haiku/trunk/src/add-ons/kernel/network/stack/link.cpp Log: glued the multicast filter handling to the receive path: we are now capable of receiving multicast frames in datagram sockets. Modified: haiku/trunk/headers/private/net/net_protocol.h =================================================================== --- haiku/trunk/headers/private/net/net_protocol.h 2007-04-15 05:23:28 UTC (rev 20694) +++ haiku/trunk/headers/private/net/net_protocol.h 2007-04-15 07:31:04 UTC (rev 20695) @@ -55,8 +55,9 @@ size_t (*get_mtu)(net_protocol *self, const struct sockaddr *address); status_t (*receive_data)(net_buffer *data); + status_t (*deliver_data)(net_protocol *protocol, net_buffer *data); + status_t (*error)(uint32 code, net_buffer *data); - status_t (*error_reply)(net_protocol *self, net_buffer *causedError, uint32 code, void *errorData); }; Modified: haiku/trunk/src/add-ons/kernel/network/protocols/icmp/icmp.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/icmp/icmp.cpp 2007-04-15 05:23:28 UTC (rev 20694) +++ haiku/trunk/src/add-ons/kernel/network/protocols/icmp/icmp.cpp 2007-04-15 07:31:04 UTC (rev 20695) @@ -342,6 +342,7 @@ icmp_get_domain, icmp_get_mtu, icmp_receive_data, + NULL, icmp_error, icmp_error_reply, }; Modified: haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp 2007-04-15 05:23:28 UTC (rev 20694) +++ haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp 2007-04-15 07:31:04 UTC (rev 20695) @@ -117,10 +117,16 @@ class MulticastGroup { public: + typedef MulticastGroupLink Link; + MulticastGroup(const in_addr &address); - status_t Deliver(net_buffer *buffer); + status_t Deliver(net_protocol_module_info *module, net_buffer *buffer); + void Add(Link *link); + void Remove(Link *link); + bool IsEmpty() const { return fLinks.IsEmpty(); } + static uint32 Hash(void *address, const void *key, uint32 range); static int Compare(void *address, const void *key); static int32 NextOffset() { return offsetof(MulticastGroup, fNext); } @@ -128,8 +134,12 @@ static const int kMaxGroups = 64; private: + typedef DoublyLinkedListCLink LinkLink; + typedef DoublyLinkedList Links; + MulticastGroup *fNext; in_addr fMulticastAddress; + Links fLinks; }; class RawSocket : public DoublyLinkedListLinkImpl, public DatagramSocket<> { @@ -139,9 +149,11 @@ typedef DoublyLinkedList RawSocketList; +typedef MulticastFilter IPv4MulticastFilter; + struct ipv4_protocol : net_protocol { - ipv4_protocol(net_socket *socket) - : multicast_filter(socket) {} + ipv4_protocol() + : multicast_filter(this) {} RawSocket *raw; uint8 service_type; @@ -149,7 +161,7 @@ uint8 multicast_time_to_live; uint32 flags; - MulticastFilter multicast_filter; + IPv4MulticastFilter multicast_filter; }; // protocol flags @@ -424,12 +436,38 @@ status_t -MulticastGroup::Deliver(net_buffer *buffer) +MulticastGroup::Deliver(net_protocol_module_info *module, net_buffer *buffer) { - return B_ERROR; + if (module->deliver_data == NULL) + return B_OK; + + Links::Iterator iterator = fLinks.GetIterator(); + + while (iterator.HasNext()) { + Link *link = iterator.Next(); + + if (link->group->FilterAccepts(buffer)) + module->deliver_data(link->group->Socket(), buffer); + } + + return B_OK; } +void +MulticastGroup::Add(Link *link) +{ + fLinks.Add(link); +} + + +void +MulticastGroup::Remove(Link *link) +{ + fLinks.Remove(link); +} + + int MulticastGroup::Compare(void *_group, const void *_key) { @@ -669,7 +707,7 @@ static status_t -deliver_multicast(net_buffer *buffer) +deliver_multicast(net_protocol_module_info *module, net_buffer *buffer) { BenaphoreLocker _(sMulticastGroupsLock); @@ -678,12 +716,57 @@ if (group == NULL) return B_OK; - // RAW sockets will be registered just like any other + // TODO fix sending multicast to RAW sockets, right now + // they are receiving the frames without the IP header - return group->Deliver(buffer); + return group->Deliver(module, buffer); } +status_t +IPv4Multicast::JoinGroup(const in_addr &groupAddr, MulticastGroup::Link *link) +{ + BenaphoreLocker _(sMulticastGroupsLock); + + MulticastGroup *group = (MulticastGroup *)hash_lookup(sMulticastGroups, + &groupAddr); + if (group == NULL) { + group = new (std::nothrow) MulticastGroup(groupAddr); + if (group == NULL) + return B_NO_MEMORY; + + status_t status = hash_insert(sMulticastGroups, group); + if (status < B_OK) { + delete group; + return status; + } + } + + group->Add(link); + return B_OK; +} + + +status_t +IPv4Multicast::LeaveGroup(const in_addr &groupAddr, MulticastGroup::Link *link) +{ + BenaphoreLocker _(sMulticastGroupsLock); + + MulticastGroup *group = (MulticastGroup *)hash_lookup(sMulticastGroups, + &groupAddr); + if (group == NULL) + return ENOENT; + + group->Remove(link); + if (group->IsEmpty()) { + hash_remove(sMulticastGroups, group); + delete group; + } + + return B_OK; +} + + static net_protocol_module_info * receiving_protocol(uint8 protocol) { @@ -715,7 +798,7 @@ static status_t -ipv4_delta_group(MulticastFilter::GroupState *group, int option, +ipv4_delta_group(IPv4MulticastFilter::GroupState *group, int option, net_interface *interface, const in_addr *sourceAddr) { switch (option) { @@ -742,8 +825,8 @@ net_interface *interface, const in_addr *groupAddr, const in_addr *sourceAddr) { - MulticastFilter &filter = protocol->multicast_filter; - MulticastFilter::GroupState *group = NULL; + IPv4MulticastFilter &filter = protocol->multicast_filter; + IPv4MulticastFilter::GroupState *group = NULL; switch (option) { case IP_ADD_MEMBERSHIP: @@ -833,7 +916,7 @@ net_protocol * ipv4_init_protocol(net_socket *socket) { - ipv4_protocol *protocol = new (std::nothrow) ipv4_protocol(socket); + ipv4_protocol *protocol = new (std::nothrow) ipv4_protocol(); if (protocol == NULL) return NULL; @@ -1412,19 +1495,12 @@ } } - if (buffer->flags & MSG_MCAST) { - // Unfortunely historical reasons dictate that the IP multicast - // model be a little different from the unicast one. We deliver - // this frame directly to all sockets registered with interest - // for this multicast group. - return deliver_multicast(buffer); - } - // Since the buffer might have been changed (reassembled fragment) // we must no longer access bufferHeader or header anymore after // this point - raw_receive_data(buffer); + if (!(buffer->flags & MSG_MCAST)) + raw_receive_data(buffer); gBufferModule->remove_header(buffer, headerLength); // the header is of variable size and may include IP options @@ -1436,11 +1512,31 @@ return EAFNOSUPPORT; } + if (buffer->flags & MSG_MCAST) { + // Unfortunely historical reasons dictate that the IP multicast + // model be a little different from the unicast one. We deliver + // this frame directly to all sockets registered with interest + // for this multicast group. + return deliver_multicast(module, buffer); + } + return module->receive_data(buffer); } status_t +ipv4_deliver_data(net_protocol *_protocol, net_buffer *buffer) +{ + ipv4_protocol *protocol = (ipv4_protocol *)_protocol; + + if (protocol->raw == NULL) + return B_ERROR; + + return protocol->raw->SocketEnqueue(buffer); +} + + +status_t ipv4_error(uint32 code, net_buffer *data) { return B_ERROR; @@ -1591,6 +1687,7 @@ ipv4_get_domain, ipv4_get_mtu, ipv4_receive_data, + ipv4_deliver_data, ipv4_error, ipv4_error_reply, }; Modified: haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/multicast.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/multicast.cpp 2007-04-15 05:23:28 UTC (rev 20694) +++ haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/multicast.cpp 2007-04-15 07:31:04 UTC (rev 20695) @@ -8,12 +8,14 @@ #include "multicast.h" +#include + #include #include -template class MulticastFilter; -template class MulticastGroupState; +template class MulticastFilter; +template class MulticastGroupState; template class MulticastGroupInterfaceState; static inline bool @@ -94,25 +96,23 @@ } -template -MulticastGroupState::MulticastGroupState( - MulticastFilter *parent, const AddressType &address) - : fParent(parent), fMulticastAddress(address), fFilterMode(kInclude) +template +MulticastGroupState::MulticastGroupState(net_protocol *socket, + const AddressType &address) + : fSocket(socket), fMulticastAddress(address), fFilterMode(kInclude) { } -template -MulticastGroupState::~MulticastGroupState() +template +MulticastGroupState::~MulticastGroupState() { - InterfaceList::Iterator iterator = fInterfaces.GetIterator(); - while (iterator.HasNext()) - _RemoveInterface(iterator.Next()); + Clear(); } -template status_t -MulticastGroupState::Add(net_interface *interface) +template status_t +MulticastGroupState::Add(net_interface *interface) { if (fFilterMode == kInclude && !fInterfaces.IsEmpty()) return EINVAL; @@ -123,8 +123,8 @@ } -template status_t -MulticastGroupState::Drop(net_interface *interface) +template status_t +MulticastGroupState::Drop(net_interface *interface) { InterfaceState *state = _GetInterface(interface, false); if (state == NULL) @@ -139,8 +139,8 @@ } -template status_t -MulticastGroupState::BlockSource(net_interface *interface, +template status_t +MulticastGroupState::BlockSource(net_interface *interface, const AddressType &sourceAddress) { if (fFilterMode != kExclude) @@ -154,8 +154,8 @@ } -template status_t -MulticastGroupState::UnblockSource(net_interface *interface, +template status_t +MulticastGroupState::UnblockSource(net_interface *interface, const AddressType &sourceAddress) { if (fFilterMode != kExclude) @@ -168,8 +168,8 @@ return state->Remove(sourceAddress); } -template status_t -MulticastGroupState::AddSSM(net_interface *interface, +template status_t +MulticastGroupState::AddSSM(net_interface *interface, const AddressType &sourceAddress) { if (fFilterMode == kExclude) @@ -183,8 +183,8 @@ } -template status_t -MulticastGroupState::DropSSM(net_interface *interface, +template status_t +MulticastGroupState::DropSSM(net_interface *interface, const AddressType &sourceAddress) { if (fFilterMode == kExclude) @@ -198,8 +198,31 @@ } -template MulticastGroupState::InterfaceState * -MulticastGroupState::_GetInterface(net_interface *interface, +template void +MulticastGroupState::Clear() +{ + InterfaceList::Iterator iterator = fInterfaces.GetIterator(); + while (iterator.HasNext()) + _RemoveInterface(iterator.Next()); +} + + +template bool +MulticastGroupState::FilterAccepts(net_buffer *buffer) +{ + InterfaceState *state = _GetInterface(buffer->interface, false); + if (state == NULL) + return false; + + bool has = state->Contains(*Addressing::AddressFromSockAddr( + (sockaddr *)&buffer->source)); + + return (has && fFilterMode == kInclude) || (!has && fFilterMode == kExclude); +} + + +template MulticastGroupState::InterfaceState * +MulticastGroupState::_GetInterface(net_interface *interface, bool create) { InterfaceList::Iterator iterator = fInterfaces.GetIterator(); @@ -220,35 +243,35 @@ } -template void -MulticastGroupState::_RemoveInterface(InterfaceState *state) +template void +MulticastGroupState::_RemoveInterface(InterfaceState *state) { fInterfaces.Remove(state); delete state; } -template -MulticastFilter::MulticastFilter(net_socket *socket) +template +MulticastFilter::MulticastFilter(net_protocol *socket) : fParent(socket) { } -template -MulticastFilter::~MulticastFilter() +template +MulticastFilter::~MulticastFilter() { States::Iterator iterator = fStates.GetIterator(); while (iterator.HasNext()) { GroupState *state = iterator.Next(); - fStates.Remove(state); - delete state; + state->Clear(); + ReturnGroup(state); } } -template MulticastFilter::GroupState * -MulticastFilter::GetGroup(const AddressType &groupAddress, +template MulticastFilter::GroupState * +MulticastFilter::GetGroup(const AddressType &groupAddress, bool create) { States::Iterator iterator = fStates.GetIterator(); @@ -262,17 +285,26 @@ if (!create) return NULL; - GroupState *state = new (nothrow) GroupState(this, groupAddress); - if (state) + GroupState *state = new (nothrow) GroupState(fParent, groupAddress); + if (state) { + if (Addressing::JoinGroup(groupAddress, state->ProtocolLink()) < B_OK) { + delete state; + return NULL; + } + fStates.Add(state); + } + return state; } -template void -MulticastFilter::ReturnGroup(GroupState *group) +template void +MulticastFilter::ReturnGroup(GroupState *group) { if (group->IsEmpty()) { + Addressing::LeaveGroup(group->Address(), group->ProtocolLink()); + fStates.Remove(group); delete group; } Modified: haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/multicast.h =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/multicast.h 2007-04-15 05:23:28 UTC (rev 20694) +++ haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/multicast.h 2007-04-15 07:31:04 UTC (rev 20695) @@ -12,11 +12,31 @@ #include #include +#include + +struct net_buffer; struct net_interface; -struct net_socket; +struct net_protocol; -template class MulticastFilter; +// This code is template'ized as it is reusable for IPv6 +template class MulticastFilter; +template struct MulticastGroupLink; +template class MulticastGroupState; + +// TODO move this elsewhere... +struct IPv4Multicast { + typedef struct in_addr AddressType; + + static status_t JoinGroup(const in_addr &, MulticastGroupLink *); + static status_t LeaveGroup(const in_addr &, MulticastGroupLink *); + + static in_addr *AddressFromSockAddr(sockaddr *sockaddr) + { + return &((sockaddr_in *)sockaddr)->sin_addr; + } +}; + template struct MulticastSource { AddressType address; @@ -34,6 +54,9 @@ status_t Add(const AddressType &address); status_t Remove(const AddressType &address); + bool Contains(const AddressType &address) + { return _Get(address, false) != NULL; } + list_link link; private: typedef MulticastSource Source; @@ -48,13 +71,22 @@ SourceList fSources; }; -template +template +struct MulticastGroupLink { + MulticastGroupState *group; + list_link link; +}; + +template class MulticastGroupState { public: - MulticastGroupState(MulticastFilter *parent, - const AddressType &address); + typedef typename Addressing::AddressType AddressType; + + MulticastGroupState(net_protocol *parent, const AddressType &address); ~MulticastGroupState(); + net_protocol *Socket() const { return fSocket; } + const AddressType &Address() const { return fMulticastAddress; } bool IsEmpty() const { return fFilterMode == kInclude && fInterfaces.IsEmpty(); } @@ -70,6 +102,12 @@ status_t DropSSM(net_interface *interface, const AddressType &sourceAddress); + void Clear(); + + bool FilterAccepts(net_buffer *buffer); + + MulticastGroupLink *ProtocolLink() { return &fInternalLink; } + list_link link; private: typedef MulticastGroupInterfaceState InterfaceState; @@ -84,21 +122,23 @@ kExclude }; - MulticastFilter *fParent; + net_protocol *fSocket; AddressType fMulticastAddress; FilterMode fFilterMode; InterfaceList fInterfaces; + MulticastGroupLink fInternalLink; }; -template +template class MulticastFilter { public: - typedef MulticastGroupState GroupState; + typedef typename Addressing::AddressType AddressType; + typedef MulticastGroupState GroupState; - MulticastFilter(net_socket *parent); + MulticastFilter(net_protocol *parent); ~MulticastFilter(); - net_socket *Parent() const { return fParent; } + net_protocol *Parent() const { return fParent; } GroupState *GetGroup(const AddressType &groupAddress, bool create); void ReturnGroup(GroupState *group); @@ -107,7 +147,7 @@ typedef DoublyLinkedListCLink GroupStateLink; typedef DoublyLinkedList States; - net_socket *fParent; + net_protocol *fParent; // TODO change this into an hash table or tree States fStates; Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.cpp 2007-04-15 05:23:28 UTC (rev 20694) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.cpp 2007-04-15 07:31:04 UTC (rev 20695) @@ -718,6 +718,7 @@ tcp_get_domain, tcp_get_mtu, tcp_receive_data, + NULL, tcp_error, tcp_error_reply, }; Modified: haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp 2007-04-15 05:23:28 UTC (rev 20694) +++ haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp 2007-04-15 07:31:04 UTC (rev 20695) @@ -82,6 +82,7 @@ net_buffer **_buffer); status_t StoreData(net_buffer *buffer); + status_t DeliverData(net_buffer *buffer); net_domain * Domain() const { @@ -179,6 +180,7 @@ ~UdpEndpointManager(); status_t ReceiveData(net_buffer *buffer); + status_t Deframe(net_buffer *buffer); UdpDomainSupport *OpenEndpoint(UdpEndpoint *endpoint); status_t FreeEndpoint(UdpDomainSupport *domain); @@ -544,8 +546,40 @@ status_t UdpEndpointManager::ReceiveData(net_buffer *buffer) { + status_t status = Deframe(buffer); + if (status < B_OK) + return status; + TRACE_EPM("ReceiveData(%p [%ld bytes])", buffer, buffer->size); + net_domain *domain = buffer->interface->domain; + + BenaphoreLocker _(fLock); + + UdpDomainSupport *domainSupport = _GetDomain(domain, false); + if (domainSupport == NULL) { + // we don't instantiate domain supports in the + // RX path as we are only interested in delivering + // data to existing sockets. + return B_ERROR; + } + + status = domainSupport->DemuxIncomingBuffer(buffer); + if (status < B_OK) { + TRACE_EPM(" ReceiveData(): no endpoint."); + // TODO: send ICMP-error + return B_ERROR; + } + + return B_ERROR; +} + + +status_t +UdpEndpointManager::Deframe(net_buffer *buffer) +{ + TRACE_EPM("Deframe(%p [%ld bytes])", buffer, buffer->size); + NetBufferHeaderReader bufferHeader(buffer); if (bufferHeader.Status() < B_OK) return bufferHeader.Status(); @@ -556,7 +590,7 @@ struct sockaddr *destination = (struct sockaddr *)&buffer->destination; if (buffer->interface == NULL || buffer->interface->domain == NULL) { - TRACE_EPM(" ReceiveData(): UDP packed dropped as there was no domain " + TRACE_EPM(" Deframe(): UDP packed dropped as there was no domain " "specified (interface %p).", buffer->interface); return B_BAD_VALUE; } @@ -564,18 +598,16 @@ net_domain *domain = buffer->interface->domain; net_address_module_info *addressModule = domain->address_module; - BenaphoreLocker _(fLock); - addressModule->set_port(source, header.source_port); addressModule->set_port(destination, header.destination_port); - TRACE_EPM(" ReceiveData(): data from %s to %s", + TRACE_EPM(" Deframe(): data from %s to %s", AddressString(domain, source, true).Data(), AddressString(domain, destination, true).Data()); uint16 udpLength = ntohs(header.udp_length); if (udpLength > buffer->size) { - TRACE_EPM(" ReceiveData(): buffer is too short, expected %hu.", + TRACE_EPM(" Deframe(): buffer is too short, expected %hu.", udpLength); return B_MISMATCHED_VALUES; } @@ -596,7 +628,7 @@ << Checksum::BufferHelper(buffer, gBufferModule); uint16 sum = udpChecksum; if (sum != 0) { - TRACE_EPM(" ReceiveData(): bad checksum 0x%hx.", sum); + TRACE_EPM(" Deframe(): bad checksum 0x%hx.", sum); return B_BAD_VALUE; } } @@ -604,22 +636,7 @@ bufferHeader.Remove(); // remove UDP-header from buffer before passing it on - UdpDomainSupport *domainSupport = _GetDomain(domain, false); - if (domainSupport == NULL) { - // we don't instantiate domain supports in the - // RX path as we are only interested in delivering - // data to existing sockets. - return B_ERROR; - } - - status_t status = domainSupport->DemuxIncomingBuffer(buffer); - if (status < B_OK) { - TRACE_EPM(" ReceiveData(): no endpoint."); - // TODO: send ICMP-error - return B_ERROR; - } - - return B_ERROR; + return B_OK; } @@ -937,6 +954,25 @@ } +status_t +UdpEndpoint::DeliverData(net_buffer *_buffer) +{ + net_buffer *buffer = gBufferModule->clone(_buffer, false); + if (buffer == NULL) + return B_NO_MEMORY; + + status_t status = sUdpEndpointManager->Deframe(buffer); + if (status < B_OK) { + gBufferModule->free(buffer); + return status; + } + + // we call Enqueue() instead of SocketEnqueue() as there is + // no need to clone the buffer again. + return Enqueue(buffer); +} + + // #pragma mark - protocol interface @@ -1094,6 +1130,13 @@ status_t +udp_deliver_data(net_protocol *protocol, net_buffer *buffer) +{ + return ((UdpEndpoint *)protocol)->DeliverData(buffer); +} + + +status_t udp_error(uint32 code, net_buffer *data) { return B_ERROR; @@ -1204,6 +1247,7 @@ udp_get_domain, udp_get_mtu, udp_receive_data, + udp_deliver_data, udp_error, udp_error_reply, }; Modified: haiku/trunk/src/add-ons/kernel/network/stack/link.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/link.cpp 2007-04-15 05:23:28 UTC (rev 20694) +++ haiku/trunk/src/add-ons/kernel/network/stack/link.cpp 2007-04-15 07:31:04 UTC (rev 20695) @@ -510,6 +510,7 @@ link_get_domain, link_get_mtu, link_receive_data, + NULL, link_error, link_error_reply, }; From revol at free.fr Sun Apr 15 09:45:13 2007 From: revol at free.fr (=?windows-1252?q?Fran=E7ois?= Revol) Date: Sun, 15 Apr 2007 09:45:13 +0200 CEST Subject: [Haiku-commits] =?windows-1252?q?r20690_-_in_haiku/trunk=3A_heade?= =?windows-1252?q?rs/posix/netinet_headers/private/net__src/add-ons/kernel?= =?windows-1252?q?/network/protocols/ipv4_src/add-ons/kernel/network/stack?= In-Reply-To: <200704150244.l3F2iIgL017639@sheep.berlios.de> Message-ID: <603016118-BeMail@laptop> > Log: > initial steps towards IPv4 Multicast Filter Delta API (RFC 3678) Cool :) I can hope to get rtsp support in VLC working someday and watch my DSL tv without windows =) Btw, remember most NIC drivers don't support adding MACs to filter yet. Fran?ois. From hugosantos at mail.berlios.de Sun Apr 15 09:46:38 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Sun, 15 Apr 2007 09:46:38 +0200 Subject: [Haiku-commits] r20696 - haiku/trunk/src/add-ons/kernel/network/protocols/ipv4 Message-ID: <200704150746.l3F7kcsN008742@sheep.berlios.de> Author: hugosantos Date: 2007-04-15 09:46:30 +0200 (Sun, 15 Apr 2007) New Revision: 20696 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20696&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp Log: fixed the reception of multicast frames by RAW sockets. Modified: haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp 2007-04-15 07:31:04 UTC (rev 20695) +++ haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp 2007-04-15 07:46:30 UTC (rev 20696) @@ -121,7 +121,8 @@ MulticastGroup(const in_addr &address); - status_t Deliver(net_protocol_module_info *module, net_buffer *buffer); + status_t Deliver(net_protocol_module_info *module, net_buffer *buffer, + bool raw); void Add(Link *link); void Remove(Link *link); @@ -436,7 +437,8 @@ status_t -MulticastGroup::Deliver(net_protocol_module_info *module, net_buffer *buffer) +MulticastGroup::Deliver(net_protocol_module_info *module, net_buffer *buffer, + bool deliverToRaw) { if (module->deliver_data == NULL) return B_OK; @@ -446,8 +448,25 @@ while (iterator.HasNext()) { Link *link = iterator.Next(); - if (link->group->FilterAccepts(buffer)) - module->deliver_data(link->group->Socket(), buffer); + // we are pretty sure of this cast since multicast filters + // are installed with the IPv4 protocol reference + ipv4_protocol *protocol = (ipv4_protocol *)link->group->Socket(); + + if (deliverToRaw && protocol->raw == NULL) + continue; + + if (link->group->FilterAccepts(buffer)) { + // as Multicast filters are installed with an IPv4 protocol + // reference, we need to go and find the appropriate instance + // related to the 'receiving protocol' with module 'module'. + net_protocol *proto = link->group->Socket(); + + while (proto && proto->module != module) + proto = proto->next; + + if (proto) + module->deliver_data(proto, buffer); + } } return B_OK; @@ -688,41 +707,51 @@ } +static status_t +deliver_multicast(net_protocol_module_info *module, net_buffer *buffer, + bool deliverToRaw) +{ + BenaphoreLocker _(sMulticastGroupsLock); + + MulticastGroup *group = (MulticastGroup *)hash_lookup(sMulticastGroups, + &buffer->destination); + if (group == NULL) + return B_OK; + + return group->Deliver(module, buffer, deliverToRaw); +} + + static void raw_receive_data(net_buffer *buffer) { BenaphoreLocker locker(sRawSocketsLock); + if (sRawSockets.IsEmpty()) + return; + TRACE("RawReceiveData(%i)", buffer->protocol); - RawSocketList::Iterator iterator = sRawSockets.GetIterator(); + if (buffer->flags & MSG_MCAST) { + // we need to call deliver_multicast here separately as + // buffer still has the IP header, and it won't in the + // next call. This isn't very optimized but works for now. + // A better solution would be to hold separate hash tables + // and lists for RAW and non-RAW sockets. + deliver_multicast(&gIPv4Module, buffer, true); + } else { + RawSocketList::Iterator iterator = sRawSockets.GetIterator(); - while (iterator.HasNext()) { - RawSocket *raw = iterator.Next(); + while (iterator.HasNext()) { + RawSocket *raw = iterator.Next(); - if (raw->Socket()->protocol == buffer->protocol) - raw->SocketEnqueue(buffer); + if (raw->Socket()->protocol == buffer->protocol) + raw->SocketEnqueue(buffer); + } } } -static status_t -deliver_multicast(net_protocol_module_info *module, net_buffer *buffer) -{ - BenaphoreLocker _(sMulticastGroupsLock); - - MulticastGroup *group = (MulticastGroup *)hash_lookup(sMulticastGroups, - &buffer->destination); - if (group == NULL) - return B_OK; - - // TODO fix sending multicast to RAW sockets, right now - // they are receiving the frames without the IP header - - return group->Deliver(module, buffer); -} - - status_t IPv4Multicast::JoinGroup(const in_addr &groupAddr, MulticastGroup::Link *link) { @@ -1499,8 +1528,7 @@ // we must no longer access bufferHeader or header anymore after // this point - if (!(buffer->flags & MSG_MCAST)) - raw_receive_data(buffer); + raw_receive_data(buffer); gBufferModule->remove_header(buffer, headerLength); // the header is of variable size and may include IP options @@ -1517,7 +1545,7 @@ // model be a little different from the unicast one. We deliver // this frame directly to all sockets registered with interest // for this multicast group. - return deliver_multicast(module, buffer); + return deliver_multicast(module, buffer, false); } return module->receive_data(buffer); From hugosantos at gmail.com Sun Apr 15 09:51:56 2007 From: hugosantos at gmail.com (Hugo Santos) Date: Sun, 15 Apr 2007 08:51:56 +0100 Subject: [Haiku-commits] r20690 - in haiku/trunk: headers/posix/netinet headers/private/net src/add-ons/kernel/network/protocols/ipv4 src/add-ons/kernel/network/stack In-Reply-To: <603016118-BeMail@laptop> References: <200704150244.l3F2iIgL017639@sheep.berlios.de> <603016118-BeMail@laptop> Message-ID: <9c46321e0704150051pf107c0cmea6407525224c6a@mail.gmail.com> Yep, still some work to go. After the last few commits what is missing is: - adding multicast support to NICs (i'll do it for ipro1000) - implementing IGMPv3 support - and of course, testing. There are still some rough edges in this code, but it will get better during the following days. Comments are welcome as always. Hugo On 4/15/07, Fran?ois Revol wrote: > > Log: > > initial steps towards IPv4 Multicast Filter Delta API (RFC 3678) > > Cool :) > I can hope to get rtsp support in VLC working someday and watch my DSL > tv without windows =) > > Btw, remember most NIC drivers don't support adding MACs to filter yet. > > Fran?ois. > _______________________________________________ > Haiku-commits mailing list > Haiku-commits at lists.berlios.de > https://lists.berlios.de/mailman/listinfo/haiku-commits > From hugosantos at mail.berlios.de Sun Apr 15 10:24:53 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Sun, 15 Apr 2007 10:24:53 +0200 Subject: [Haiku-commits] r20697 - haiku/trunk/src/add-ons/kernel/network/protocols/ipv4 Message-ID: <200704150824.l3F8OrVu010005@sheep.berlios.de> Author: hugosantos Date: 2007-04-15 10:24:40 +0200 (Sun, 15 Apr 2007) New Revision: 20697 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20697&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/multicast.cpp Log: gcc 4 template instantiation fixes Modified: haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/multicast.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/multicast.cpp 2007-04-15 07:46:30 UTC (rev 20696) +++ haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/multicast.cpp 2007-04-15 08:24:40 UTC (rev 20697) @@ -14,10 +14,6 @@ #include -template class MulticastFilter; -template class MulticastGroupState; -template class MulticastGroupInterfaceState; - static inline bool operator==(const in_addr &a1, const in_addr &a2) { @@ -38,7 +34,7 @@ template MulticastGroupInterfaceState::~MulticastGroupInterfaceState() { - SourceList::Iterator iterator = fSources.GetIterator(); + typename SourceList::Iterator iterator = fSources.GetIterator(); while (iterator.HasNext()) { _Remove(iterator.Next()); } @@ -64,11 +60,11 @@ } -template MulticastGroupInterfaceState::Source * +template typename MulticastGroupInterfaceState::Source * MulticastGroupInterfaceState::_Get(const AddressType &address, bool create) { - SourceList::Iterator iterator = fSources.GetIterator(); + typename SourceList::Iterator iterator = fSources.GetIterator(); while (iterator.HasNext()) { Source *state = iterator.Next(); if (state->address == address) @@ -201,7 +197,7 @@ template void MulticastGroupState::Clear() { - InterfaceList::Iterator iterator = fInterfaces.GetIterator(); + typename InterfaceList::Iterator iterator = fInterfaces.GetIterator(); while (iterator.HasNext()) _RemoveInterface(iterator.Next()); } @@ -221,11 +217,11 @@ } -template MulticastGroupState::InterfaceState * +template typename MulticastGroupState::InterfaceState * MulticastGroupState::_GetInterface(net_interface *interface, bool create) { - InterfaceList::Iterator iterator = fInterfaces.GetIterator(); + typename InterfaceList::Iterator iterator = fInterfaces.GetIterator(); while (iterator.HasNext()) { InterfaceState *state = iterator.Next(); if (state->Interface() == interface) @@ -261,7 +257,7 @@ template MulticastFilter::~MulticastFilter() { - States::Iterator iterator = fStates.GetIterator(); + typename States::Iterator iterator = fStates.GetIterator(); while (iterator.HasNext()) { GroupState *state = iterator.Next(); state->Clear(); @@ -270,11 +266,11 @@ } -template MulticastFilter::GroupState * +template typename MulticastFilter::GroupState * MulticastFilter::GetGroup(const AddressType &groupAddress, bool create) { - States::Iterator iterator = fStates.GetIterator(); + typename States::Iterator iterator = fStates.GetIterator(); while (iterator.HasNext()) { GroupState *state = iterator.Next(); @@ -310,3 +306,7 @@ } } +// IPv4 explicit template instantiation +template class MulticastFilter; +template class MulticastGroupState; +template class MulticastGroupInterfaceState; From superstippi at gmx.de Sun Apr 15 11:06:36 2007 From: superstippi at gmx.de (Stephan Assmus) Date: Sun, 15 Apr 2007 11:06:36 +0200 Subject: [Haiku-commits] r20688 - haiku/trunk/src/add-ons/tracker/filetype In-Reply-To: <20070415035345.4747.3@cs.tu-berlin.de> References: <200704142322.l3ENMpQL006101@sheep.berlios.de> <20070415035345.4747.3@cs.tu-berlin.de> Message-ID: <20070415110636.358.1@stippis.nameserver> On 2007-04-15 at 03:53:45 [+0200], Ingo Weinhold wrote: > > On 2007-04-15 at 01:22:51 [+0200], stippi at BerliOS > > wrote: > > Author: stippi > > Date: 2007-04-15 01:22:51 +0200 (Sun, 15 Apr 2007) > > New Revision: 20688 > > ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20688&view=rev > > > > Modified: > > haiku/trunk/src/add-ons/tracker/filetype/FileType.rdef > > haiku/trunk/src/add-ons/tracker/filetype/Jamfile > > Log: > > * added same vector icon as FileTypes preflet, but somehow the > > resources are not added for the "Addon" target type? Ingo? > > Works fine here (tested under Linux). What exactly goes wrong on your > machine? Hm. I just don't see the icon. That's all. Best regards, -Stephan From axeld at pinc-software.de Sun Apr 15 11:17:58 2007 From: axeld at pinc-software.de (Axel =?iso-8859-15?q?D=F6rfler?=) Date: Sun, 15 Apr 2007 11:17:58 +0200 CEST Subject: [Haiku-commits] =?iso-8859-15?q?r20694_-_in_haiku/trunk/src/add-o?= =?iso-8859-15?q?ns/kernel/network/protocols=3A_ipv4_udp?= In-Reply-To: <200704150523.l3F5NdIW002457@sheep.berlios.de> Message-ID: <1068443502-BeMail@zon> hugosantos at mail.berlios.de wrote: > Log: > made UDP's send_data call into IPv4's, so we can handle of the > datagram > stuff in one place. I find that change rather ugly, is there any reasoning for this? It completely breaks the semantics of the send_data() function IMO. Bye, Axel. From axeld at pinc-software.de Sun Apr 15 12:32:45 2007 From: axeld at pinc-software.de (Axel =?iso-8859-15?q?D=F6rfler?=) Date: Sun, 15 Apr 2007 12:32:45 +0200 CEST Subject: [Haiku-commits] =?iso-8859-15?q?r20690_-_in_haiku/trunk=3A_header?= =?iso-8859-15?q?s/posix/netinet_headers/private/net__src/add-ons/kernel/n?= =?iso-8859-15?q?etwork/protocols/ipv4_src/add-ons/kernel/network/stack?= In-Reply-To: <9c46321e0704150051pf107c0cmea6407525224c6a@mail.gmail.com> Message-ID: <5555907853-BeMail@zon> "Hugo Santos" wrote: > There are still some rough edges in this code, but it will get > better during the following days. Comments are welcome as always. Very cool, nice work! :-) Bye, Axel. From stippi at mail.berlios.de Sun Apr 15 12:43:01 2007 From: stippi at mail.berlios.de (stippi at BerliOS) Date: Sun, 15 Apr 2007 12:43:01 +0200 Subject: [Haiku-commits] r20698 - haiku/trunk/src/preferences/appearance Message-ID: <200704151043.l3FAh1gJ006933@sheep.berlios.de> Author: stippi Date: 2007-04-15 12:42:48 +0200 (Sun, 15 Apr 2007) New Revision: 20698 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20698&view=rev Modified: haiku/trunk/src/preferences/appearance/Appearance.rdef Log: * created icon * added some previously missing information to rdef Modified: haiku/trunk/src/preferences/appearance/Appearance.rdef =================================================================== --- haiku/trunk/src/preferences/appearance/Appearance.rdef 2007-04-15 08:24:40 UTC (rev 20697) +++ haiku/trunk/src/preferences/appearance/Appearance.rdef 2007-04-15 10:42:48 UTC (rev 20698) @@ -1,5 +1,47 @@ -resource(1, "BEOS:L:STD_ICON") #'ICON' array +resource app_signature "application/x-vnd.haiku-Appearance"; + +resource app_version { + major = 1, + middle = 0, + minor = 0, + + /* 0 = development 1 = alpha 2 = beta + 3 = gamma 4 = golden master 5 = final */ + variety = 2, + + internal = 0, + + short_info = "Appearance", + long_info = "Appearance ?2002-2007 Haiku" +}; + +resource app_flags B_SINGLE_LAUNCH; + +#ifdef HAIKU_TARGET_PLATFORM_HAIKU + +resource vector_icon { + $"6E636966050500020106023AB09C387275BA11FB3C46904852304A0DE300FFE7" + $"DCFFE29C7A020002043C233C3AF073BE44203F4BD14A79EB417FF50DF1F6FFCB" + $"7B8288AC67D4F2F7F9B1FFB4BDD79704016B05FF0C0609BF2E034C524C525052" + $"5850C86DC7735C4A60406044603C5E3A5C3CCB50BFBA5E3ECA9EC11F584A5054" + $"4EC819C490C74DC62806062F0F323A3A3C3C3A4034BF59354232423044423644" + $"32C040BC5A383E3E3E383E0607A22B3058363A5C405A445A445A485A46503A48" + $"0204B44B2FB5172DB37F31B3E53AB3E538B3E53CB99342B8C744BA5F40B99335" + $"BA5F37B8C7330204BEA73CBF733ABDDB3EBEA748BE26C1EDBF734CC4D450C408" + $"52C564C58FC4D442C5A044C408400204363EBD353E323E2C4C28483050BDDBC4" + $"3BBD0FC507BE2CC3EABD60C20FBD47C305BD86C096060BEEEC2E3046264A2646" + $"264C284E2652245028542C2C582856305A3456385C345C3C5C3C58445AC037CB" + $"3C48563C4A04032E24B87A3EB5BD3AB42542B755422E04032E4E425A3256345E" + $"305E3A0202263028302230263624362A360202413E433E3D3E40463E46444602" + $"024B494C4C4B4B484E4B4E4C4F070A0303000102000A00040304070810011784" + $"20040A02020304000A000106000A0001051001178400040A010105000A040309" + $"0A0B00" +}; + +#else // HAIKU_TARGET_PLATFORM_HAIKU + +resource large_icon { $"FFFFFFFFFFFFFF000000FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF" $"FFFFFFFFFFFFFF00F9F90000FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF" @@ -35,7 +77,7 @@ $"FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF00000E0F0F0F" }; -resource(2, "BEOS:M:STD_ICON") #'MICN' array +resource mini_icon { $"FFFFFF000000FFFFFFFFFFFFFFFFFFFF" $"FFFFFF00E5F90000FFFFFFFFFFFFFFFF" @@ -54,3 +96,5 @@ $"FF002B2F00FFFFFFFFFF00001900FFFF" $"FFFF00000E0F0F0F0FFFFFFF00000E0E" }; + +#endif // HAIKU_TARGET_PLATFORM_HAIKU From korli at mail.berlios.de Sun Apr 15 12:50:34 2007 From: korli at mail.berlios.de (korli at BerliOS) Date: Sun, 15 Apr 2007 12:50:34 +0200 Subject: [Haiku-commits] r20699 - haiku/trunk/build/jam Message-ID: <200704151050.l3FAoYlQ013558@sheep.berlios.de> Author: korli Date: 2007-04-15 12:50:33 +0200 (Sun, 15 Apr 2007) New Revision: 20699 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20699&view=rev Modified: haiku/trunk/build/jam/HaikuImage Log: added frcode, updatedb instead of updatedb Modified: haiku/trunk/build/jam/HaikuImage =================================================================== --- haiku/trunk/build/jam/HaikuImage 2007-04-15 10:42:48 UTC (rev 20698) +++ haiku/trunk/build/jam/HaikuImage 2007-04-15 10:50:33 UTC (rev 20699) @@ -24,7 +24,7 @@ chmod chop chown cksum clear clockconfig cmp comm compress cp copyattr csplit ctags cut date dc dd desklink df diff diff3 dircolors dirname driveinfo dstcheck du dump_cis dump_cisreg echo eject env error expand - expr factor false fdinfo ffm find finddir fmt fold fortune ftp funzip gawk + expr factor false fdinfo ffm find finddir fmt fold fortune frcode ftp funzip gawk $(X86_ONLY)gdb grep groups gzip gzexe hd head hey hostname id ident ideinfo idestatus ifconfig install installsound iroster isvolume join keymap kill less lessecho lesskey link listarea listattr listdev listimage @@ -36,7 +36,7 @@ safemode screen_blanker sed settype setversion setvolume seq sh shar shutdown sleep sort split strace stty su sum sync sysinfo tac tail tar tcpdump tee telnet telnetd test top touch tput tr traceroute translate true tsort - tty uname unchop unexpand unmount uniq unrar unshar unzip unzipsfx updatedb + tty uname unchop unexpand unmount uniq unrar unshar unzip unzipsfx updatedb uptime usb_dev_info uudecode uuencode vdir version vim waitfor wc wget whoami xargs xres yes zdiff zforce zgrep zip zipcloak zipgrep zipnote zipsplit zmore znew From korli at mail.berlios.de Sun Apr 15 12:51:34 2007 From: korli at mail.berlios.de (korli at BerliOS) Date: Sun, 15 Apr 2007 12:51:34 +0200 Subject: [Haiku-commits] r20700 - haiku/trunk/src/bin/findutils/locate Message-ID: <200704151051.l3FApYMB013957@sheep.berlios.de> Author: korli Date: 2007-04-15 12:51:32 +0200 (Sun, 15 Apr 2007) New Revision: 20700 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20700&view=rev Modified: haiku/trunk/src/bin/findutils/locate/Jamfile Log: clean up Modified: haiku/trunk/src/bin/findutils/locate/Jamfile =================================================================== --- haiku/trunk/src/bin/findutils/locate/Jamfile 2007-04-15 10:50:33 UTC (rev 20699) +++ haiku/trunk/src/bin/findutils/locate/Jamfile 2007-04-15 10:51:32 UTC (rev 20700) @@ -20,27 +20,11 @@ locate.c : libfindutils.a : $(findutils_rsrc) ; -BinCommand bigram : - bigram.c - : libfindutils.a : $(findutils_rsrc) ; - -# TODO: Must be done in HaikuImage. -#MakeLocate bigram : [ FDirName $(HAIKU_ETC_DIR) libexec locate ] ; - BinCommand frcode : frcode.c : libfindutils.a : $(findutils_rsrc) ; -# TODO: Must be done in HaikuImage. -#MakeLocate frcode : [ FDirName $(HAIKU_ETC_DIR) libexec locate ] ; -BinCommand code : - code.c - : libfindutils.a : $(findutils_rsrc) ; - -# TODO: Must be done in HaikuImage. -#MakeLocate code : [ FDirName $(HAIKU_ETC_DIR) libexec locate ] ; - rule MkUpdateDb { SEARCH on $(>) = $(SEARCH_SOURCE) ; From stippi at mail.berlios.de Sun Apr 15 13:39:59 2007 From: stippi at mail.berlios.de (stippi at BerliOS) Date: Sun, 15 Apr 2007 13:39:59 +0200 Subject: [Haiku-commits] r20701 - haiku/trunk/src/preferences/sounds Message-ID: <200704151139.l3FBdxfJ030695@sheep.berlios.de> Author: stippi Date: 2007-04-15 13:39:59 +0200 (Sun, 15 Apr 2007) New Revision: 20701 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20701&view=rev Modified: haiku/trunk/src/preferences/sounds/Sounds.rdef Log: * created vector icon * updated copyright Modified: haiku/trunk/src/preferences/sounds/Sounds.rdef =================================================================== --- haiku/trunk/src/preferences/sounds/Sounds.rdef 2007-04-15 10:51:32 UTC (rev 20700) +++ haiku/trunk/src/preferences/sounds/Sounds.rdef 2007-04-15 11:39:59 UTC (rev 20701) @@ -15,11 +15,35 @@ internal = 0, short_info = "Sounds", - long_info = "Sounds ?2003-2006 Haiku" + long_info = "Sounds ?2003-2007 Haiku" }; resource file_types message; +#ifdef HAIKU_TARGET_PLATFORM_HAIKU + +resource vector_icon { + $"6E636966070500020106023880000000000000003CE00049400045000000F7C0" + $"7FFFA76B240201060237000000000000000036FFFF49400049E00000C7873BFF" + $"A76B24020106033C9FA4328F99B3A6D13DBDB148D1B24A3BBE00FFFFFF49FDED" + $"7BFF8A8C22020012023B40000000000000004000004B300000000000016AFF01" + $"46020106033CA17634580DB35F0B3BC8A1481BAE4AEAE400FEFADD49FDED7BFF" + $"ADA93D020106033CA17634580DB35F0B3BC8A149FBAE4A3AE400FEFADD49FDED" + $"7BFFADA93D0602063C3EC01F3EBC303E3249BAC6C0EA314D2E512E4D2EC8483C" + $"5ABB135AC13C5A4A514AC8484A4D4649474DC189C0EA0605FB023C2240223822" + $"3828BD4CBD41BCDFBA38BD4CBD41BEFFBD5BBEFFBD5BBF6EBA4F40280203BD4C" + $"BD41BD4CBD41BD8EBF153C4236424242BEFFBD5BBEBEBF22BEFFBD5B0605BB03" + $"3E5C3E5C465E52566054605A604E52523E4E464C3E4E0204B9EC4ABA5248B991" + $"C472BB1E54B8BA52BC5055BF8055BF1A56BFE654BB8451BCB653BA524F020841" + $"44C05BC122BFE7C196C16AC4C4C0EDC357C18BC526C22BC5B9C1D8C57AC25EC5" + $"DEC2AFC693C29AC63448544358C0CAC94AC1A4C96949534855C396C6D0C2F4C5" + $"55C34DC5B2C2A9C505C215C3FBC24BC49AC1A8C2B7080A040103000A00010010" + $"01178400040A030100000A000201021001178400040A010101000A020102000A" + $"050104000A06010500" +}; + +#else // HAIKU_TARGET_PLATFORM_HAIKU + resource large_icon { $"FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF0000FFFFFFFFFFFFFFFFFFFFFF" @@ -75,3 +99,5 @@ $"FF002B2F00FFFFFFFFFFFFFF0F0F0FFF" $"FFFF00000E0F0F0F0FFFFFFFFFFFFFFF" }; + +#endif // HAIKU_TARGET_PLATFORM_HAIKU From stippi at mail.berlios.de Sun Apr 15 14:22:38 2007 From: stippi at mail.berlios.de (stippi at BerliOS) Date: Sun, 15 Apr 2007 14:22:38 +0200 Subject: [Haiku-commits] r20702 - haiku/trunk/src/preferences/menu Message-ID: <200704151222.l3FCMcaZ003001@sheep.berlios.de> Author: stippi Date: 2007-04-15 14:22:37 +0200 (Sun, 15 Apr 2007) New Revision: 20702 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20702&view=rev Modified: haiku/trunk/src/preferences/menu/Menu.rdef Log: * created vector icon Modified: haiku/trunk/src/preferences/menu/Menu.rdef =================================================================== --- haiku/trunk/src/preferences/menu/Menu.rdef 2007-04-15 11:39:59 UTC (rev 20701) +++ haiku/trunk/src/preferences/menu/Menu.rdef 2007-04-15 12:22:37 UTC (rev 20702) @@ -15,11 +15,31 @@ internal = 0, short_info = "Menu", - long_info = "Menu ?2002-2006 Haiku" + long_info = "Menu ?2002-2007 Haiku" }; resource(1, "BEOS:FILE_TYPES") message; +#ifdef HAIKU_TARGET_PLATFORM_HAIKU + +resource vector_icon { + $"6E636966060501040174020006033A2EBFBCDD943FBCF33CD8E2401A3B485438" + $"00F6D1772AFFDC89FFE3B04302000602371E52BAB3FA3FD7E43C378C43AAE547" + $"D3D100C57930FFAE5D0E03572C0203D705050D0605AE02476054534C555C5160" + $"514C48435E0607BE2E425E4A56C31BC9744E50C9EBBBADC81BBFA9CAC0B9D75E" + $"2E3C262E42BB81BBD1B675C3F822500606BE0F432B3D2A3F293B2B39373A3538" + $"39333F3A3739393B353E2C3D2D3F2B0606BE0F512F5832C91CB966C983BAF150" + $"3DC672BDBFC5CDBF5C4C494F3CC567BEF6C60CBD595532C813BAB2C828B9A506" + $"08EEEE2C4D274E274C27503554415A3E5A455A4355405843583D5835542B4F2D" + $"51294D080243314C3408023C384C3E08023E3C463F0802364248490802384642" + $"4A08022F4945520802344E3C520607BA39472FC43BB96C4F2D502F4E2B4BB8D3" + $"2B492E472BC340B706452C080A010100000A0001011001178400040A02010100" + $"0A0303020304000A04040506080A1815FF01178120040A040307090B1815FF01" + $"178120040A040405080A0618001501178300040A05010C00" +}; + +#else // HAIKU_TARGET_PLATFORM_HAIKU + resource large_icon { $"FFFFFFFFFFFFFF000000FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF" $"FFFFFFFFFFFFFF003F3F0000FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF" @@ -74,6 +94,8 @@ $"FFFF00000E0F0F0F0FFFFFFF00000E0F" }; +#endif // HAIKU_TARGET_PLATFORM_HAIKU + resource(128, "CTL") array { $"424D760400000000000036000000280000001100000010000000010020000000" $"000040040000130B0000130B0000000000000000000077747700777477007774" From korli at mail.berlios.de Sun Apr 15 16:00:00 2007 From: korli at mail.berlios.de (korli at BerliOS) Date: Sun, 15 Apr 2007 16:00:00 +0200 Subject: [Haiku-commits] r20703 - in haiku/trunk: headers/private/media src/kits/media src/servers/media Message-ID: <200704151400.l3FE00FC007715@sheep.berlios.de> Author: korli Date: 2007-04-15 15:59:59 +0200 (Sun, 15 Apr 2007) New Revision: 20703 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20703&view=rev Modified: haiku/trunk/headers/private/media/DecoderPlugin.h haiku/trunk/src/kits/media/PluginManager.cpp haiku/trunk/src/servers/media/MMediaFilesManager.cpp haiku/trunk/src/servers/media/MMediaFilesManager.h Log: fixed some warnings code style of MMediaFilesManager.* Modified: haiku/trunk/headers/private/media/DecoderPlugin.h =================================================================== --- haiku/trunk/headers/private/media/DecoderPlugin.h 2007-04-15 12:22:37 UTC (rev 20702) +++ haiku/trunk/headers/private/media/DecoderPlugin.h 2007-04-15 13:59:59 UTC (rev 20703) @@ -11,6 +11,7 @@ class ChunkProvider { public: + virtual ~ChunkProvider() {}; virtual status_t GetNextChunk(const void **chunkBuffer, size_t *chunkSize, media_header *mediaHeader) = 0; }; Modified: haiku/trunk/src/kits/media/PluginManager.cpp =================================================================== --- haiku/trunk/src/kits/media/PluginManager.cpp 2007-04-15 12:22:37 UTC (rev 20702) +++ haiku/trunk/src/kits/media/PluginManager.cpp 2007-04-15 13:59:59 UTC (rev 20703) @@ -143,7 +143,7 @@ { CALLED(); while (!fPluginList->IsEmpty()) { - plugin_info *info; + plugin_info *info = NULL; fPluginList->Get(fPluginList->CountItems() - 1, &info); printf("PluginManager: Error, unloading PlugIn %s with usecount %d\n", info->name, info->usecount); delete info->plugin; Modified: haiku/trunk/src/servers/media/MMediaFilesManager.cpp =================================================================== --- haiku/trunk/src/servers/media/MMediaFilesManager.cpp 2007-04-15 12:22:37 UTC (rev 20702) +++ haiku/trunk/src/servers/media/MMediaFilesManager.cpp 2007-04-15 13:59:59 UTC (rev 20703) @@ -1,4 +1,4 @@ -/* +/* * Copyright 2003, J?r?me Duval. All rights reserved. * Distributed under the terms of the MIT License. */ @@ -12,7 +12,7 @@ MMediaFilesManager::MMediaFilesManager() - : fLocker(new BLocker("media files manager locker")), + : fLocker(new BLocker("media files manager locker")), fRegistryMap(new Map >), fRunner(NULL) { @@ -32,38 +32,38 @@ } -int32 +int32 MMediaFilesManager::ReadPascalString(BFile &file, char **str) { uint32 len; - *str=NULL; + *str = NULL; if (file.Read(&len, 4) < 4) - return -1; + return -1; if (len == 0) - return 0; + return 0; *str = (char *)malloc(len); if (file.Read(*str, len) < (int32)len) { - free(*str); - *str = NULL; - return -1; + free(*str); + *str = NULL; + return -1; } return (int32)len; } -int32 +int32 MMediaFilesManager::WritePascalString(BFile &file, const char *str) { - - if(str == NULL) - return -1; + + if (str == NULL) + return -1; uint32 len = strlen(str) + 1; if (file.Write(&len, 4) < 4) - return -1; + return -1; if (len == 0) - return 0; + return 0; if (file.Write(str, len) < (int32)len) { - return -1; + return -1; } return (int32)len; } @@ -76,16 +76,16 @@ CALLED(); status_t err = B_OK; BPath path; - if((err = find_directory(B_USER_SETTINGS_DIRECTORY, &path))!=B_OK) + if ((err = find_directory(B_USER_SETTINGS_DIRECTORY, &path)) != B_OK) return err; - + path.Append("Media/MMediaFilesManager"); - + BFile file(path.Path(), B_READ_ONLY); - + uint32 category_count; - if (file.Read(header, sizeof(uint32)*3) < (int32)sizeof(uint32)*3) { - header[0] = 0xac00150c; + if (file.Read(header, sizeof(uint32)*3) < (int32)sizeof(uint32)*3) { + header[0] = 0xac00150c; header[1] = 0x18723462; header[2] = 0x00000001; return B_ERROR; @@ -106,35 +106,35 @@ break; TRACE("%s {\n", str); do { - len = ReadPascalString(file, &key); - if (len < 0) - return B_ERROR; - if (len == 0) - break; - len = ReadPascalString(file, &val); - if (len == 1) { - free(val); - val = strdup("(null)"); - } - /*if (file.Read(&vol, sizeof(uint32)) < (int32)sizeof(uint32)) - return B_ERROR;*/ - //TRACE(" %s: %s, volume: %f\n", key, val, *(float *)&vol); - - entry_ref ref; - if(len>1) { - BEntry entry(val); - if(entry.Exists()) - entry.GetRef(&ref); - } - SetRefFor(str, key, ref, false); - - free(key); - free(val); + len = ReadPascalString(file, &key); + if (len < 0) + return B_ERROR; + if (len == 0) + break; + len = ReadPascalString(file, &val); + if (len == 1) { + free(val); + val = strdup("(null)"); + } + /*if (file.Read(&vol, sizeof(uint32)) < (int32)sizeof(uint32)) + return B_ERROR;*/ + //TRACE(" %s: %s, volume: %f\n", key, val, *(float *)&vol); + + entry_ref ref; + if (len > 1) { + BEntry entry(val); + if (entry.Exists()) + entry.GetRef(&ref); + } + SetRefFor(str, key, ref, false); + + free(key); + free(val); } while (true); TRACE("}\n"); free(str); } - + return B_OK; } @@ -145,42 +145,42 @@ CALLED(); status_t err = B_OK; BPath path; - if((err = find_directory(B_USER_SETTINGS_DIRECTORY, &path))!=B_OK) + if ((err = find_directory(B_USER_SETTINGS_DIRECTORY, &path)) != B_OK) return err; - + path.Append("Media/MMediaFilesManager"); - + BFile file(path.Path(), B_WRITE_ONLY | B_CREATE_FILE); uint32 zero = 0; - + if (file.Write(header, sizeof(uint32)*3) < (int32)sizeof(uint32)*3) return B_ERROR; uint32 category_count = fRegistryMap->CountItems(); - if (file.Write(&category_count, sizeof(uint32)) < (int32)sizeof(uint32)) + if (file.Write(&category_count, sizeof(uint32)) < (int32)sizeof(uint32)) return B_ERROR; - - BString *type; + + BString *type = NULL; Map *map; - BString *item; + BString *item = NULL; entry_ref *ref; - for (fRegistryMap->Rewind(); fRegistryMap->GetNext(&map); ) { + for (fRegistryMap->Rewind(); fRegistryMap->GetNext(&map);) { fRegistryMap->GetCurrentKey(&type); - + WritePascalString(file, type->String()); - + for (map->Rewind(); map->GetNext(&ref);) { map->GetCurrentKey(&item); BPath path(ref); - + WritePascalString(file, item->String()); WritePascalString(file, path.Path() ? path.Path() : ""); - + } - + file.Write(&zero, sizeof(uint32)); } file.Write(&zero, sizeof(uint32)); - + return B_OK; } @@ -190,22 +190,22 @@ { BAutolock lock(fLocker); printf("\n"); - + /* for each type, the registry map contains a map of item/entry_ref */ printf("MMediaFilesManager: registry map follows\n"); - BString *type; + BString *type = NULL; Map *map; - BString *item; + BString *item = NULL; entry_ref *ref; - for (fRegistryMap->Rewind(); fRegistryMap->GetNext(&map); ) { + for (fRegistryMap->Rewind(); fRegistryMap->GetNext(&map);) { fRegistryMap->GetCurrentKey(&type); - + for (map->Rewind(); map->GetNext(&ref);) { map->GetCurrentKey(&item); BPath path(ref); - printf(" type \"%s\", item \"%s\", path \"%s\"\n", - type->String(), item->String(), (path.InitCheck() == B_OK) ? path.Path() : "INVALID"); + printf(" type \"%s\", item \"%s\", path \"%s\"\n", + type->String(), item->String(), (path.InitCheck() == B_OK) ? path.Path() : "INVALID"); } } printf("MMediaFilesManager: list end\n"); @@ -218,21 +218,21 @@ MMediaFilesManager::RewindTypes(BString ***types, int32 *count) { CALLED(); - if(types==NULL || count == NULL) + if (types == NULL || count == NULL) return B_BAD_VALUE; - + Map *map; - BString *type; - + BString *type = NULL; + *count = fRegistryMap->CountItems(); *types = new BString*[*count]; - int32 i=0; - - for (fRegistryMap->Rewind(); i<*count && fRegistryMap->GetNext(&map); i++) { + int32 i = 0; + + for (fRegistryMap->Rewind(); i < *count && fRegistryMap->GetNext(&map); i++) { fRegistryMap->GetCurrentKey(&type); - (*types)[i] = type; + (*types)[i] = type; } - + return B_OK; } @@ -241,87 +241,87 @@ MMediaFilesManager::RewindRefs(const char* type, BString ***items, int32 *count) { CALLED(); - if(type == NULL || items==NULL || count == NULL) + if (type == NULL || items == NULL || count == NULL) return B_BAD_VALUE; - - Map *map; + + Map *map = NULL; entry_ref *ref; - BString *item; - + BString *item = NULL; + *count = 0; *items = NULL; - + if (!fRegistryMap->Get(BString(type), &map)) return B_OK; - + *count = map->CountItems(); *items = new BString*[*count]; - int32 i=0; - - for (map->Rewind(); i<*count && map->GetNext(&ref); i++) { + int32 i = 0; + + for (map->Rewind(); i < *count && map->GetNext(&ref); i++) { map->GetCurrentKey(&item); - (*items)[i] = item; + (*items)[i] = item; } - + return B_OK; } status_t MMediaFilesManager::GetRefFor(const char *type, - const char *item, - entry_ref **out_ref) + const char *item, + entry_ref **out_ref) { CALLED(); - Map *map; - if(!fRegistryMap->Get(BString(type), &map)) + Map *map = NULL; + if (!fRegistryMap->Get(BString(type), &map)) return B_ENTRY_NOT_FOUND; - if(!map->Get(BString(item), out_ref)) + if (!map->Get(BString(item), out_ref)) return B_ENTRY_NOT_FOUND; - + return B_OK; } status_t MMediaFilesManager::SetRefFor(const char *type, - const char *item, - const entry_ref &ref, bool save) + const char *item, + const entry_ref &ref, bool save) { CALLED(); TRACE("MMediaFilesManager::SetRefFor %s %s\n", type, item); - + BString itemString(item); itemString.Truncate(B_MEDIA_NAME_LENGTH); BString typeString(type); Map *map; - if(!fRegistryMap->Get(typeString, &map)) { + if (!fRegistryMap->Get(typeString, &map)) { map = new Map; fRegistryMap->Insert(typeString, *map); - fRegistryMap->Get(typeString, &map); + fRegistryMap->Get(typeString, &map); } - - if(map->Has(itemString)) + + if (map->Has(itemString)) map->Remove(itemString); map->Insert(itemString, ref); - if(save) + if (save) LaunchTimer(); - + return B_OK; } status_t MMediaFilesManager::RemoveRefFor(const char *type, - const char *item, - const entry_ref &ref) + const char *item, + const entry_ref &ref) { CALLED(); BString itemString(item); BString typeString(type); Map *map; - if(fRegistryMap->Get(typeString, &map)) { + if (fRegistryMap->Get(typeString, &map)) { map->Remove(itemString); map->Insert(itemString, *(new entry_ref)); LaunchTimer(); @@ -332,13 +332,13 @@ status_t MMediaFilesManager::RemoveItem(const char *type, - const char *item) + const char *item) { CALLED(); BString itemString(item); BString typeString(type); Map *map; - if(fRegistryMap->Get(typeString, &map)) { + if (fRegistryMap->Get(typeString, &map)) { map->Remove(itemString); LaunchTimer(); } @@ -349,9 +349,9 @@ void MMediaFilesManager::LaunchTimer() { - if(!fRunner) - fRunner = new BMessageRunner(be_app, - new BMessage(MMEDIAFILESMANAGER_SAVE_TIMER), 3 * 1000000, 1); + if (!fRunner) + fRunner = new BMessageRunner(be_app, + new BMessage(MMEDIAFILESMANAGER_SAVE_TIMER), 3 * 1000000LL, 1); } @@ -360,6 +360,6 @@ { SaveState(); delete fRunner; - fRunner = NULL; + fRunner = NULL; } Modified: haiku/trunk/src/servers/media/MMediaFilesManager.h =================================================================== --- haiku/trunk/src/servers/media/MMediaFilesManager.h 2007-04-15 12:22:37 UTC (rev 20702) +++ haiku/trunk/src/servers/media/MMediaFilesManager.h 2007-04-15 13:59:59 UTC (rev 20703) @@ -1,4 +1,4 @@ -/* +/* * Copyright 2003, J?r?me Duval. All rights reserved. * Distributed under the terms of the MIT License. */ @@ -15,52 +15,52 @@ class MMediaFilesManager { -public: - MMediaFilesManager(); - ~MMediaFilesManager(); + public: + MMediaFilesManager(); + ~MMediaFilesManager(); - status_t LoadState(); - status_t SaveState(); + status_t LoadState(); + status_t SaveState(); - void Dump(); - - status_t RewindTypes( - BString ***types, - int32 *count); - status_t RewindRefs( - const char * type, - BString ***items, - int32 *count); - status_t GetRefFor( - const char * type, - const char * item, - entry_ref ** out_ref); - status_t SetRefFor( - const char * type, - const char * item, - const entry_ref & ref, - bool save = true); - status_t RemoveRefFor( // This might better be called "ClearRefFor" - const char * type, // but it's too late now... - const char * item, - const entry_ref & ref); + void Dump(); - status_t RemoveItem( // new in 4.1, removes the whole item. - const char * type, - const char * item); + status_t RewindTypes( + BString ***types, + int32 *count); + status_t RewindRefs( + const char * type, + BString ***items, + int32 *count); + status_t GetRefFor( + const char * type, + const char * item, + entry_ref ** out_ref); + status_t SetRefFor( + const char * type, + const char * item, + const entry_ref & ref, + bool save = true); + status_t RemoveRefFor( + const char * type, + const char * item, + const entry_ref & ref); - void TimerMessage(); + status_t RemoveItem( + const char * type, + const char * item); -private: - static int32 ReadPascalString(BFile &file, char **str); - static int32 WritePascalString(BFile &file, const char *str); - void LaunchTimer(); -private: - BLocker *fLocker; - - Map > * fRegistryMap; - - uint32 header[3]; - - BMessageRunner *fRunner; + void TimerMessage(); + + private: + static int32 ReadPascalString(BFile &file, char **str); + static int32 WritePascalString(BFile &file, const char *str); + void LaunchTimer(); + private: + BLocker *fLocker; + + Map > * fRegistryMap; + + uint32 header[3]; + + BMessageRunner *fRunner; }; From korli at mail.berlios.de Sun Apr 15 16:17:02 2007 From: korli at mail.berlios.de (korli at BerliOS) Date: Sun, 15 Apr 2007 16:17:02 +0200 Subject: [Haiku-commits] r20704 - haiku/trunk/src/servers/input Message-ID: <200704151417.l3FEH2E6009315@sheep.berlios.de> Author: korli Date: 2007-04-15 16:17:02 +0200 (Sun, 15 Apr 2007) New Revision: 20704 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20704&view=rev Modified: haiku/trunk/src/servers/input/MethodMenuItem.cpp haiku/trunk/src/servers/input/MethodMenuItem.h haiku/trunk/src/servers/input/MethodReplicant.cpp haiku/trunk/src/servers/input/MethodReplicant.h Log: code style Modified: haiku/trunk/src/servers/input/MethodMenuItem.cpp =================================================================== --- haiku/trunk/src/servers/input/MethodMenuItem.cpp 2007-04-15 13:59:59 UTC (rev 20703) +++ haiku/trunk/src/servers/input/MethodMenuItem.cpp 2007-04-15 14:17:02 UTC (rev 20704) @@ -24,7 +24,7 @@ { SetLabel(name); fIcon.SetBits(icon, MENUITEM_ICON_SIZE * MENUITEM_ICON_SIZE, 0, B_CMAP8); - fMessenger = messenger; + fMessenger = messenger; } Modified: haiku/trunk/src/servers/input/MethodMenuItem.h =================================================================== --- haiku/trunk/src/servers/input/MethodMenuItem.h 2007-04-15 13:59:59 UTC (rev 20703) +++ haiku/trunk/src/servers/input/MethodMenuItem.h 2007-04-15 14:17:02 UTC (rev 20704) @@ -2,13 +2,13 @@ // // Copyright (c) 2004, Haiku // -// This software is part of the Haiku distribution and is covered +// This software is part of the Haiku distribution and is covered // by the Haiku license. // // // File: MethodMenuItem.h // Authors: J?r?me Duval, -// +// // Description: Input Server // Created: October 19, 2004 // @@ -23,27 +23,26 @@ #define MENUITEM_ICON_SIZE 16 class MethodMenuItem : public BMenuItem { -public: - MethodMenuItem(int32 cookie, const char *label, const uchar *icon, BMenu *subMenu, BMessenger &messenger); - MethodMenuItem(int32 cookie, const char *label, const uchar *icon); - - virtual ~MethodMenuItem(); + public: + MethodMenuItem(int32 cookie, const char *label, const uchar *icon, BMenu *subMenu, BMessenger &messenger); + MethodMenuItem(int32 cookie, const char *label, const uchar *icon); - virtual void DrawContent(); - virtual void GetContentSize(float *width, float *height); + virtual ~MethodMenuItem(); - void SetName(const char *name); - const char *Name() { return Label(); }; + virtual void DrawContent(); + virtual void GetContentSize(float *width, float *height); - void SetIcon(const uchar *icon); - const uchar *Icon() { return (uchar *)fIcon.Bits(); }; + void SetName(const char *name); + const char *Name() { return Label(); }; - const int32 Cookie() { return fCookie; }; -private: - BBitmap fIcon; - int32 fCookie; - BMessenger fMessenger; + void SetIcon(const uchar *icon); + const uchar *Icon() { return(uchar *)fIcon.Bits(); }; + + const int32 Cookie() { return fCookie; }; + private: + BBitmap fIcon; + int32 fCookie; + BMessenger fMessenger; }; -#endif - +#endif Modified: haiku/trunk/src/servers/input/MethodReplicant.cpp =================================================================== --- haiku/trunk/src/servers/input/MethodReplicant.cpp 2007-04-15 13:59:59 UTC (rev 20703) +++ haiku/trunk/src/servers/input/MethodReplicant.cpp 2007-04-15 14:17:02 UTC (rev 20704) @@ -2,13 +2,13 @@ // // Copyright (c) 2004, Haiku // -// This software is part of the Haiku distribution and is covered +// This software is part of the Haiku distribution and is covered // by the Haiku license. // // // File: MethodReplicant.cpp // Authors: J?r?me Duval, -// +// // Description: Input Server // Created: October 13, 2004 // @@ -33,29 +33,29 @@ #ifdef DEBUG #define CALLED() PRINT(("CALLED %s \n", __PRETTY_FUNCTION__)); #else - #define CALLED() + #define CALLED() #endif MethodReplicant::MethodReplicant(const char* signature) : BView(BRect(0, 0, 15, 15), REPLICANT_CTL_NAME, B_FOLLOW_ALL, B_WILL_DRAW), - fMenu("", false, false) + fMenu("", false, false) { // Background Bitmap fSegments = new BBitmap(BRect(0, 0, kRemoteWidth - 1, kRemoteHeight - 1), kRemoteColorSpace); fSegments->SetBits(kRemoteBits, kRemoteWidth*kRemoteHeight, 0, kRemoteColorSpace); // Background Color - SetViewColor(184,184,184); + SetViewColor(184, 184, 184); //add dragger BRect rect(Bounds()); - rect.left = rect.right-7.0; - rect.top = rect.bottom-7.0; + rect.left = rect.right - 7.0; + rect.top = rect.bottom - 7.0; BDragger *dragger = new BDragger(rect, this, B_FOLLOW_RIGHT | B_FOLLOW_BOTTOM); AddChild(dragger); dragger->SetViewColor(B_TRANSPARENT_32_BIT); - - ASSERT(signature!=NULL); + + ASSERT(signature != NULL); fSignature = strdup(signature); fMenu.SetFont(be_plain_font); @@ -65,15 +65,15 @@ MethodReplicant::MethodReplicant(BMessage *message) : BView(message), - fMenu("", false, false) + fMenu("", false, false) { // Background Bitmap fSegments = new BBitmap(BRect(0, 0, kRemoteWidth - 1, kRemoteHeight - 1), kRemoteColorSpace); fSegments->SetBits(kRemoteBits, kRemoteWidth*kRemoteHeight, 0, kRemoteColorSpace); - + const char *signature = NULL; message->FindString("add_on", &signature); - ASSERT(signature!=NULL); + ASSERT(signature != NULL); fSignature = strdup(signature); fMenu.SetFont(be_plain_font); @@ -99,7 +99,7 @@ } -status_t +status_t MethodReplicant::Archive(BMessage *data, bool deep) const { BView::Archive(data, deep); @@ -118,7 +118,7 @@ msg.AddMessenger("address", messenger); BMessenger inputMessenger(fSignature); - if (inputMessenger.SendMessage(&msg)!=B_OK) { + if (inputMessenger.SendMessage(&msg) != B_OK) { printf("error when contacting input_server\n"); } } @@ -127,45 +127,45 @@ void MethodReplicant::MessageReceived(BMessage *message) { - PRINT(("%s what:%c%c%c%c\n", __PRETTY_FUNCTION__, message->what>>24, message->what>>16, message->what>>8, message->what)); + PRINT(("%s what:%c%c%c%c\n", __PRETTY_FUNCTION__, message->what >> 24, message->what >> 16, message->what >> 8, message->what)); PRINT_OBJECT(*message); switch (message->what) { - case B_ABOUT_REQUESTED: - (new BAlert("About Method Replicant", "Method Replicant (Replicant)\n" - " Brought to you by J?r?me DUVAL.\n\n" - "Haiku, 2004","OK"))->Go(); - break; - case IS_UPDATE_NAME: - UpdateMethodName(message); - break; - case IS_UPDATE_ICON: - UpdateMethodIcon(message); - break; - case IS_UPDATE_MENU: - UpdateMethodMenu(message); - break; - case IS_UPDATE_METHOD: - UpdateMethod(message); - break; - case IS_ADD_METHOD: - AddMethod(message); - break; - case IS_REMOVE_METHOD: - RemoveMethod(message); - break; + case B_ABOUT_REQUESTED: + (new BAlert("About Method Replicant", "Method Replicant (Replicant)\n" + " Brought to you by J?r?me DUVAL.\n\n" + "Haiku, 2004", "OK"))->Go(); + break; + case IS_UPDATE_NAME: + UpdateMethodName(message); + break; + case IS_UPDATE_ICON: + UpdateMethodIcon(message); + break; + case IS_UPDATE_MENU: + UpdateMethodMenu(message); + break; + case IS_UPDATE_METHOD: + UpdateMethod(message); + break; + case IS_ADD_METHOD: + AddMethod(message); + break; + case IS_REMOVE_METHOD: + RemoveMethod(message); + break; - default: - BView::MessageReceived(message); - break; + default: + BView::MessageReceived(message); + break; } } -void +void MethodReplicant::Draw(BRect rect) { BView::Draw(rect); - + SetDrawingMode(B_OP_OVER); DrawBitmap(fSegments); } @@ -178,13 +178,13 @@ uint32 mouseButtons; BPoint where; GetMouse(&where, &mouseButtons, true); - + where = ConvertToScreen(point); - + fMenu.SetTargetForItems(this); - BMenuItem *item = fMenu.Go(where, true, true, + BMenuItem *item = fMenu.Go(where, true, true, BRect(where - BPoint(4, 4), where + BPoint(4, 4))); - + if (item && dynamic_cast(item)) { BMessage msg(IS_SET_METHOD); msg.AddInt32("cookie", ((MethodMenuItem*)item)->Cookie()); @@ -201,12 +201,12 @@ } -void +void MethodReplicant::UpdateMethod(BMessage *message) { CALLED(); int32 cookie; - if (message->FindInt32("cookie", &cookie)!=B_OK) { + if (message->FindInt32("cookie", &cookie) != B_OK) { fprintf(stderr, "can't find cookie in message\n"); return; } @@ -223,19 +223,19 @@ } -void +void MethodReplicant::UpdateMethodIcon(BMessage *message) { CALLED(); int32 cookie; - if (message->FindInt32("cookie", &cookie)!=B_OK) { + if (message->FindInt32("cookie", &cookie) != B_OK) { fprintf(stderr, "can't find cookie in message\n"); return; } const uchar *data; ssize_t numBytes; - if (message->FindData("icon", B_ANY_TYPE, (const void**)&data, &numBytes)!=B_OK) { + if (message->FindData("icon", B_ANY_TYPE, (const void**)&data, &numBytes) != B_OK) { fprintf(stderr, "can't find icon in message\n"); return; } @@ -250,25 +250,25 @@ } -void +void MethodReplicant::UpdateMethodMenu(BMessage *message) { CALLED(); int32 cookie; - if (message->FindInt32("cookie", &cookie)!=B_OK) { + if (message->FindInt32("cookie", &cookie) != B_OK) { fprintf(stderr, "can't find cookie in message\n"); return; } BMessage msg; - if (message->FindMessage("menu", &msg)!=B_OK) { + if (message->FindMessage("menu", &msg) != B_OK) { fprintf(stderr, "can't find menu in message\n"); return; } PRINT_OBJECT(msg); BMessenger messenger; - if (message->FindMessenger("target", &messenger)!=B_OK) { + if (message->FindMessenger("target", &messenger) != B_OK) { fprintf(stderr, "can't find target in message\n"); return; } @@ -288,7 +288,7 @@ MethodMenuItem *item2 = NULL; if (menu) - item2 = new MethodMenuItem(cookie, item->Label(), item->Icon(), + item2 = new MethodMenuItem(cookie, item->Label(), item->Icon(), menu, messenger); else item2 = new MethodMenuItem(cookie, item->Label(), item->Icon()); @@ -299,18 +299,18 @@ } -void +void MethodReplicant::UpdateMethodName(BMessage *message) { CALLED(); int32 cookie; - if (message->FindInt32("cookie", &cookie)!=B_OK) { + if (message->FindInt32("cookie", &cookie) != B_OK) { fprintf(stderr, "can't find cookie in message\n"); return; } const char *name; - if (message->FindString("name", &name)!=B_OK) { + if (message->FindString("name", &name) != B_OK) { fprintf(stderr, "can't find name in message\n"); return; } @@ -328,36 +328,36 @@ MethodMenuItem * MethodReplicant::FindItemByCookie(int32 cookie) { - for (int32 i=0; iCookie())); - if (item->Cookie()==cookie) + if (item->Cookie() == cookie) return item; - } + } return NULL; } -void +void MethodReplicant::AddMethod(BMessage *message) { CALLED(); int32 cookie; - if (message->FindInt32("cookie", &cookie)!=B_OK) { + if (message->FindInt32("cookie", &cookie) != B_OK) { fprintf(stderr, "can't find cookie in message\n"); return; } const char *name; - if (message->FindString("name", &name)!=B_OK) { + if (message->FindString("name", &name) != B_OK) { fprintf(stderr, "can't find name in message\n"); return; } - + const uchar *icon; ssize_t numBytes; - if (message->FindData("icon", B_ANY_TYPE, (const void**)&icon, &numBytes)!=B_OK) { + if (message->FindData("icon", B_ANY_TYPE, (const void**)&icon, &numBytes) != B_OK) { fprintf(stderr, "can't find icon in message\n"); return; } @@ -377,12 +377,12 @@ } -void +void MethodReplicant::RemoveMethod(BMessage *message) { CALLED(); int32 cookie; - if (message->FindInt32("cookie", &cookie)!=B_OK) { + if (message->FindInt32("cookie", &cookie) != B_OK) { fprintf(stderr, "can't find cookie in message\n"); return; } Modified: haiku/trunk/src/servers/input/MethodReplicant.h =================================================================== --- haiku/trunk/src/servers/input/MethodReplicant.h 2007-04-15 13:59:59 UTC (rev 20703) +++ haiku/trunk/src/servers/input/MethodReplicant.h 2007-04-15 14:17:02 UTC (rev 20704) @@ -2,13 +2,13 @@ // // Copyright (c) 2004, Haiku // -// This software is part of the Haiku distribution and is covered +// This software is part of the Haiku distribution and is covered // by the Haiku license. // // // File: MethodReplicant.h // Authors: J?r?me Duval, -// +// // Description: Input Server // Created: October 13, 2004 // @@ -26,39 +26,38 @@ class _EXPORT MethodReplicant; class MethodReplicant : public BView { -public: - MethodReplicant(const char* signature); - - MethodReplicant(BMessage *); + public: + MethodReplicant(const char* signature); + + MethodReplicant(BMessage *); // BMessage * based constructor needed to support archiving - virtual ~MethodReplicant(); + virtual ~MethodReplicant(); - // archiving overrides - static MethodReplicant *Instantiate(BMessage *data); - virtual status_t Archive(BMessage *data, bool deep = true) const; + // archiving overrides + static MethodReplicant *Instantiate(BMessage *data); + virtual status_t Archive(BMessage *data, bool deep = true) const; - virtual void AttachedToWindow(); + virtual void AttachedToWindow(); - // misc BView overrides - virtual void MouseDown(BPoint); - virtual void MouseUp(BPoint); - - virtual void Draw(BRect ); + // misc BView overrides + virtual void MouseDown(BPoint); + virtual void MouseUp(BPoint); - virtual void MessageReceived(BMessage *); -private: - BBitmap *fSegments; - char *fSignature; - BPopUpMenu fMenu; + virtual void Draw(BRect); - void UpdateMethod(BMessage *); - void UpdateMethodIcon(BMessage *); - void UpdateMethodMenu(BMessage *); - void UpdateMethodName(BMessage *); - void AddMethod(BMessage *message); - void RemoveMethod(BMessage *message); - MethodMenuItem *FindItemByCookie(int32 cookie); + virtual void MessageReceived(BMessage *); + private: + BBitmap *fSegments; + char *fSignature; + BPopUpMenu fMenu; + + void UpdateMethod(BMessage *); + void UpdateMethodIcon(BMessage *); + void UpdateMethodMenu(BMessage *); + void UpdateMethodName(BMessage *); + void AddMethod(BMessage *message); + void RemoveMethod(BMessage *message); + MethodMenuItem *FindItemByCookie(int32 cookie); }; -#endif - +#endif From hugosantos at gmail.com Sun Apr 15 16:40:33 2007 From: hugosantos at gmail.com (Hugo Santos) Date: Sun, 15 Apr 2007 15:40:33 +0100 Subject: [Haiku-commits] r20694 - in haiku/trunk/src/add-ons/kernel/network/protocols: ipv4 udp In-Reply-To: <1068443502-BeMail@zon> References: <200704150523.l3F5NdIW002457@sheep.berlios.de> <1068443502-BeMail@zon> Message-ID: <9c46321e0704150740m750cef78ke6112be9fee2b505@mail.gmail.com> Hey Axel, This changed the behavior of ipv4's send_data into that of a virtual function. It is as if the derived class call into the base class to do the send_data, and it thens re-feeds the packet now with whatever new information into the stack, and thus the handling begins from the derived class. The reasoning for this is that i want to concentrate most of the IP-specific datagram handling stuff in ipv4_send_data, and just want to handle UDP related stuff in UDP. udp_send_data -- nothing udp is required -> ipv4_send_data -- source address selection -> udp_send_routed_data -- udp framing -> ipv4_send_routed_data. -- ipv4 framing Do you feel it breaks the semantics because we are going up in the hierarchy? I can add a new function instead to do the common work, but i think this fits nicely into an object oriented approach. Let me know, Hugo On 4/15/07, Axel D?rfler wrote: > hugosantos at mail.berlios.de wrote: > > Log: > > made UDP's send_data call into IPv4's, so we can handle of the > > datagram > > stuff in one place. > > I find that change rather ugly, is there any reasoning for this? It > completely breaks the semantics of the send_data() function IMO. > > Bye, > Axel. > > _______________________________________________ > Haiku-commits mailing list > Haiku-commits at lists.berlios.de > https://lists.berlios.de/mailman/listinfo/haiku-commits > From korli at mail.berlios.de Sun Apr 15 16:46:12 2007 From: korli at mail.berlios.de (korli at BerliOS) Date: Sun, 15 Apr 2007 16:46:12 +0200 Subject: [Haiku-commits] r20705 - haiku/trunk/build/jam Message-ID: <200704151446.l3FEkCPO010831@sheep.berlios.de> Author: korli Date: 2007-04-15 16:46:12 +0200 (Sun, 15 Apr 2007) New Revision: 20705 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20705&view=rev Modified: haiku/trunk/build/jam/HaikuImage Log: added mail_daemon Modified: haiku/trunk/build/jam/HaikuImage =================================================================== --- haiku/trunk/build/jam/HaikuImage 2007-04-15 14:17:02 UTC (rev 20704) +++ haiku/trunk/build/jam/HaikuImage 2007-04-15 14:46:12 UTC (rev 20705) @@ -62,7 +62,7 @@ ; BEOS_SYSTEM_SERVERS = registrar debug_server syslog_daemon media_server net_server media_addon_server input_server app_server fake_app_server - midi_server print_server + midi_server print_server mail_daemon ; BEOS_NETWORK_DEVICES = ethernet loopback ; From hugosantos at mail.berlios.de Sun Apr 15 19:35:06 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Sun, 15 Apr 2007 19:35:06 +0200 Subject: [Haiku-commits] r20706 - haiku/trunk/src/add-ons/kernel/network/protocols/tcp Message-ID: <200704151735.l3FHZ6cF011877@sheep.berlios.de> Author: hugosantos Date: 2007-04-15 19:34:52 +0200 (Sun, 15 Apr 2007) New Revision: 20706 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20706&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h Log: fixed an issue where TCP would RST a connection when a peer trying to connect us re-sent their SYN. - In fact our SYN/ACK reply is being lost due to ARP resolving as we are waiting in the device's receive path, thus we never get replies before timing out. This requires queueing during ARP resolving. Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-15 14:46:12 UTC (rev 20705) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-15 17:34:52 UTC (rev 20706) @@ -90,6 +90,32 @@ } +static inline bool +in_window(const tcp_sequence &sequence, const tcp_sequence &rcvNext, + uint32 rcvWindow) +{ + return sequence >= rcvNext && sequence < (rcvNext + rcvWindow); +} + + +static inline bool +segment_in_sequence(const tcp_segment_header &segment, int size, + const tcp_sequence &rcvNext, uint32 rcvWindow) +{ + tcp_sequence sequence(segment.sequence); + if (size == 0) { + if (rcvWindow == 0) + return sequence == rcvNext; + return in_window(sequence, rcvNext, rcvWindow); + } else { + if (rcvWindow == 0) + return false; + return in_window(sequence, rcvNext, rcvWindow) + || in_window(sequence + size - 1, rcvNext, rcvWindow); + } +} + + WaitList::WaitList(const char *name) { fSem = create_sem(0, name); @@ -761,7 +787,7 @@ segment.flags &= ~TCP_FLAG_SYNCHRONIZE; // we handled this flag now, it must not be set for further processing - return endpoint->Receive(segment, buffer); + return endpoint->_Receive(segment, buffer); // TODO: here, the ack/delayed ack call will be made on the parent socket! } @@ -894,237 +920,19 @@ // The fast path was not applicable, so we continue with the standard // processing of the incoming segment - if (segment.flags & TCP_FLAG_RESET) { - // is this a valid reset? - if (fLastAcknowledgeSent <= segment.sequence - && tcp_sequence(segment.sequence) - < (fLastAcknowledgeSent + fReceiveWindow)) { - if (fState == SYNCHRONIZE_RECEIVED) { - // TODO: if we came from SYN-SENT signal connection refused - // and remove all segments from tx queue - } else if (fState == ESTABLISHED || fState == FINISH_SENT - || fState == FINISH_RECEIVED || fState == FINISH_ACKNOWLEDGED) { - // TODO: RFC 793 states that on ESTABLISHED, FIN-WAIT{1,2} - // or CLOSE-WAIT "All segment queues should be - // flushed". - } - - if (fState != TIME_WAIT && fReceiveQueue.Available() > 0) { - _NotifyReader(); - } else { - return DELETE | DROP; - } - - fError = ECONNREFUSED; - fState = CLOSED; - } - - return DROP; - } - - if ((segment.flags & TCP_FLAG_SYNCHRONIZE) != 0 - || (fState == SYNCHRONIZE_RECEIVED - && (fInitialReceiveSequence > segment.sequence - || (segment.flags & TCP_FLAG_ACKNOWLEDGE) != 0 - && (fSendUnacknowledged > segment.acknowledge - || fSendMax < segment.acknowledge)))) { - // reset the connection - either the initial SYN was faulty, or we - // received a SYN within the data stream - return DROP | RESET; - } - - fReceiveWindow = max_c(fReceiveQueue.Free(), fReceiveWindow); - // the window must not shrink - - // trim buffer to be within the receive window - int32 drop = fReceiveNext - segment.sequence; - if (drop > 0) { - if ((uint32)drop > buffer->size - || ((uint32)drop == buffer->size - && (segment.flags & TCP_FLAG_FINISH) == 0)) { - // don't accidently remove a FIN we shouldn't remove - segment.flags &= ~TCP_FLAG_FINISH; - drop = buffer->size; - } - - // remove duplicate data at the start - TRACE("* remove %ld bytes from the start", drop); - gBufferModule->remove_header(buffer, drop); - segment.sequence += drop; - } - - int32 action = KEEP; - - drop = segment.sequence + buffer->size - (fReceiveNext + fReceiveWindow); - if (drop > 0) { - // remove data exceeding our window - if ((uint32)drop >= buffer->size) { - // if we can accept data, or the segment is not what we'd expect, - // drop the segment (an immediate acknowledge is always triggered) - if (fReceiveWindow != 0 || segment.sequence != fReceiveNext) - return DROP | IMMEDIATE_ACKNOWLEDGE; - - action |= IMMEDIATE_ACKNOWLEDGE; - } - - if ((segment.flags & TCP_FLAG_FINISH) != 0) { - // we need to remove the finish, too, as part of the data - drop--; - } - - segment.flags &= ~(TCP_FLAG_FINISH | TCP_FLAG_PUSH); - TRACE("* remove %ld bytes from the end", drop); - gBufferModule->remove_trailer(buffer, drop); - } - - // Then look at the acknowledgement for any updates - - if ((segment.flags & TCP_FLAG_ACKNOWLEDGE) != 0) { - // process acknowledged data - if (fState == SYNCHRONIZE_RECEIVED) { - // TODO: window scaling! - if (socket->parent != NULL) { - gSocketModule->set_connected(socket); - release_sem_etc(fAcceptSemaphore, 1, B_DO_NOT_RESCHEDULE); - } - - fState = ESTABLISHED; - - fSendList.Signal(); - _NotifyReader(); - } - - if (fSendMax < segment.acknowledge || fState == TIME_WAIT) + if (fState != SYNCHRONIZE_SENT && fState != LISTEN && fState != CLOSED) { + // 1. check sequence number + if (!segment_in_sequence(segment, buffer->size, fReceiveNext, + fReceiveWindow)) { + TRACE(" Receive(): segment out of window, next: %lu wnd: %lu", + (uint32)fReceiveNext, fReceiveWindow); + if (segment.flags & TCP_FLAG_RESET) + return DROP; return DROP | IMMEDIATE_ACKNOWLEDGE; - if (fSendUnacknowledged >= segment.acknowledge) { - // this is a duplicate acknowledge - // TODO: handle this! - if (buffer->size == 0 && advertisedWindow == fSendWindow - && (segment.flags & TCP_FLAG_FINISH) == 0) { - TRACE("Receive(): duplicate ack!"); - fDuplicateAcknowledgeCount++; - - gStackModule->cancel_timer(&fRetransmitTimer); - - fSendNext = segment.acknowledge; - _SendQueued(); - return DROP; - } - } else { - // this segment acknowledges in flight data - fDuplicateAcknowledgeCount = 0; - - if (fSendMax == segment.acknowledge) { - // there is no outstanding data to be acknowledged - // TODO: if the transmit timer function is already waiting - // to acquire this endpoint's lock, we should stop it anyway - TRACE("Receive(): all inflight data ack'd!"); - gStackModule->cancel_timer(&fRetransmitTimer); - } else { - TRACE("Receive(): set retransmit timer!"); - // TODO: set retransmit timer correctly - if (!gStackModule->is_timer_active(&fRetransmitTimer)) - gStackModule->set_timer(&fRetransmitTimer, 1000000LL); - } - - fSendUnacknowledged = segment.acknowledge; - fSendQueue.RemoveUntil(segment.acknowledge); - - if (fSendNext < fSendUnacknowledged) - fSendNext = fSendUnacknowledged; - - if (segment.acknowledge > fSendQueue.LastSequence() && fState > ESTABLISHED) { - TRACE("Receive(): FIN has been acknowledged!"); - - switch (fState) { - case FINISH_SENT: - fState = FINISH_ACKNOWLEDGED; - break; - case CLOSING: - fState = TIME_WAIT; - _EnterTimeWait(); - break; - case WAIT_FOR_FINISH_ACKNOWLEDGE: - fState = CLOSED; - break; - - default: - break; - } - } } } - // TODO: update window - fSendWindow = advertisedWindow; - if (advertisedWindow > fSendMaxWindow) - fSendMaxWindow = advertisedWindow; - - if (segment.flags & TCP_FLAG_URGENT) { - if (fState == ESTABLISHED || fState == FINISH_SENT - || fState == FINISH_ACKNOWLEDGED) { - // TODO: Handle urgent data: - // - RCV.UP <- max(RCV.UP, SEG.UP) - // - signal the user that urgent data is available (SIGURG) - } - } - - bool notify = false; - - if (buffer->size > 0 && _ShouldReceive()) { - fReceiveQueue.Add(buffer, segment.sequence); - fReceiveNext += buffer->size; - notify = true; - TRACE("Receive(): adding data, receive next = %lu. Now have %lu bytes.", - (uint32)fReceiveNext, fReceiveQueue.Available()); - - if (segment.flags & TCP_FLAG_PUSH) - fReceiveQueue.SetPushPointer(); - } else { - action = (action & ~KEEP) | DROP; - } - - if (segment.flags & TCP_FLAG_FINISH) { - if (fState != CLOSED && fState != LISTEN && fState != SYNCHRONIZE_SENT) { - TRACE("Receive(): peer is finishing connection!"); - fReceiveNext++; - notify = true; - - // FIN implies PSH - fReceiveQueue.SetPushPointer(); - - // RFC 793 states that we must send an ACK to FIN - action |= IMMEDIATE_ACKNOWLEDGE; - - // other side is closing connection; change states - switch (fState) { - case ESTABLISHED: - case SYNCHRONIZE_RECEIVED: - fState = FINISH_RECEIVED; - break; - case FINISH_SENT: - // simultaneous close - fState = CLOSING; - break; - case FINISH_ACKNOWLEDGED: - fState = TIME_WAIT; - _EnterTimeWait(); - break; - default: - break; - } - } - } - - if (notify) - _NotifyReader(); - - if (buffer->size > 0 || (segment.flags & TCP_FLAG_SYNCHRONIZE) != 0) - action |= ACKNOWLEDGE; - - TRACE("Receive() Action %ld", action); - - return action; + return _Receive(segment, buffer); } @@ -1425,6 +1233,246 @@ } +int32 +TCPEndpoint::_Receive(tcp_segment_header &segment, net_buffer *buffer) +{ + uint32 advertisedWindow = (uint32)segment.advertised_window << fSendWindowShift; + + if (segment.flags & TCP_FLAG_RESET) { + // is this a valid reset? + if (fLastAcknowledgeSent <= segment.sequence + && tcp_sequence(segment.sequence) + < (fLastAcknowledgeSent + fReceiveWindow)) { + if (fState == SYNCHRONIZE_RECEIVED) { + // TODO: if we came from SYN-SENT signal connection refused + // and remove all segments from tx queue + } else if (fState == ESTABLISHED || fState == FINISH_SENT + || fState == FINISH_RECEIVED || fState == FINISH_ACKNOWLEDGED) { + // TODO: RFC 793 states that on ESTABLISHED, FIN-WAIT{1,2} + // or CLOSE-WAIT "All segment queues should be + // flushed". + } + + if (fState != TIME_WAIT && fReceiveQueue.Available() > 0) { + _NotifyReader(); + } else { + return DELETE | DROP; + } + + fError = ECONNREFUSED; + fState = CLOSED; + } + + return DROP; + } + + if ((segment.flags & TCP_FLAG_SYNCHRONIZE) != 0 + || (fState == SYNCHRONIZE_RECEIVED + && (fInitialReceiveSequence > segment.sequence + || (segment.flags & TCP_FLAG_ACKNOWLEDGE) != 0 + && (fSendUnacknowledged > segment.acknowledge + || fSendMax < segment.acknowledge)))) { + // reset the connection - either the initial SYN was faulty, or we + // received a SYN within the data stream + return DROP | RESET; + } + + fReceiveWindow = max_c(fReceiveQueue.Free(), fReceiveWindow); + // the window must not shrink + + // trim buffer to be within the receive window + int32 drop = fReceiveNext - segment.sequence; + if (drop > 0) { + if ((uint32)drop > buffer->size + || ((uint32)drop == buffer->size + && (segment.flags & TCP_FLAG_FINISH) == 0)) { + // don't accidently remove a FIN we shouldn't remove + segment.flags &= ~TCP_FLAG_FINISH; + drop = buffer->size; + } + + // remove duplicate data at the start + TRACE("* remove %ld bytes from the start", drop); + gBufferModule->remove_header(buffer, drop); + segment.sequence += drop; + } + + int32 action = KEEP; + + drop = segment.sequence + buffer->size - (fReceiveNext + fReceiveWindow); + if (drop > 0) { + // remove data exceeding our window + if ((uint32)drop >= buffer->size) { + // if we can accept data, or the segment is not what we'd expect, + // drop the segment (an immediate acknowledge is always triggered) + if (fReceiveWindow != 0 || segment.sequence != fReceiveNext) + return DROP | IMMEDIATE_ACKNOWLEDGE; + + action |= IMMEDIATE_ACKNOWLEDGE; + } + + if ((segment.flags & TCP_FLAG_FINISH) != 0) { + // we need to remove the finish, too, as part of the data + drop--; + } + + segment.flags &= ~(TCP_FLAG_FINISH | TCP_FLAG_PUSH); + TRACE("* remove %ld bytes from the end", drop); + gBufferModule->remove_trailer(buffer, drop); + } + + // Then look at the acknowledgement for any updates + + if ((segment.flags & TCP_FLAG_ACKNOWLEDGE) != 0) { + // process acknowledged data + if (fState == SYNCHRONIZE_RECEIVED) { + // TODO: window scaling! + if (socket->parent != NULL) { + gSocketModule->set_connected(socket); + release_sem_etc(fAcceptSemaphore, 1, B_DO_NOT_RESCHEDULE); + } + + fState = ESTABLISHED; + + fSendList.Signal(); + _NotifyReader(); + } + + if (fSendMax < segment.acknowledge || fState == TIME_WAIT) + return DROP | IMMEDIATE_ACKNOWLEDGE; + if (fSendUnacknowledged >= segment.acknowledge) { + // this is a duplicate acknowledge + // TODO: handle this! + if (buffer->size == 0 && advertisedWindow == fSendWindow + && (segment.flags & TCP_FLAG_FINISH) == 0) { + TRACE("Receive(): duplicate ack!"); + fDuplicateAcknowledgeCount++; + + gStackModule->cancel_timer(&fRetransmitTimer); + + fSendNext = segment.acknowledge; + _SendQueued(); + return DROP; + } + } else { + // this segment acknowledges in flight data + fDuplicateAcknowledgeCount = 0; + + if (fSendMax == segment.acknowledge) { + // there is no outstanding data to be acknowledged + // TODO: if the transmit timer function is already waiting + // to acquire this endpoint's lock, we should stop it anyway + TRACE("Receive(): all inflight data ack'd!"); + gStackModule->cancel_timer(&fRetransmitTimer); + } else { + TRACE("Receive(): set retransmit timer!"); + // TODO: set retransmit timer correctly + if (!gStackModule->is_timer_active(&fRetransmitTimer)) + gStackModule->set_timer(&fRetransmitTimer, 1000000LL); + } + + fSendUnacknowledged = segment.acknowledge; + fSendQueue.RemoveUntil(segment.acknowledge); + + if (fSendNext < fSendUnacknowledged) + fSendNext = fSendUnacknowledged; + + if (segment.acknowledge > fSendQueue.LastSequence() + && fState > ESTABLISHED) { + TRACE("Receive(): FIN has been acknowledged!"); + + switch (fState) { + case FINISH_SENT: + fState = FINISH_ACKNOWLEDGED; + break; + case CLOSING: + fState = TIME_WAIT; + _EnterTimeWait(); + break; + case WAIT_FOR_FINISH_ACKNOWLEDGE: + fState = CLOSED; + break; + + default: + break; + } + } + } + } + + // TODO: update window + fSendWindow = advertisedWindow; + if (advertisedWindow > fSendMaxWindow) + fSendMaxWindow = advertisedWindow; + + if (segment.flags & TCP_FLAG_URGENT) { + if (fState == ESTABLISHED || fState == FINISH_SENT + || fState == FINISH_ACKNOWLEDGED) { + // TODO: Handle urgent data: + // - RCV.UP <- max(RCV.UP, SEG.UP) + // - signal the user that urgent data is available (SIGURG) + } + } + + bool notify = false; + + if (buffer->size > 0 && _ShouldReceive()) { + fReceiveQueue.Add(buffer, segment.sequence); + fReceiveNext += buffer->size; + notify = true; + TRACE("Receive(): adding data, receive next = %lu. Now have %lu bytes.", + (uint32)fReceiveNext, fReceiveQueue.Available()); + + if (segment.flags & TCP_FLAG_PUSH) + fReceiveQueue.SetPushPointer(); + } else { + action = (action & ~KEEP) | DROP; + } + + if (segment.flags & TCP_FLAG_FINISH) { + if (fState != CLOSED && fState != LISTEN && fState != SYNCHRONIZE_SENT) { + TRACE("Receive(): peer is finishing connection!"); + fReceiveNext++; + notify = true; + + // FIN implies PSH + fReceiveQueue.SetPushPointer(); + + // RFC 793 states that we must send an ACK to FIN + action |= IMMEDIATE_ACKNOWLEDGE; + + // other side is closing connection; change states + switch (fState) { + case ESTABLISHED: + case SYNCHRONIZE_RECEIVED: + fState = FINISH_RECEIVED; + break; + case FINISH_SENT: + // simultaneous close + fState = CLOSING; + break; + case FINISH_ACKNOWLEDGED: + fState = TIME_WAIT; + _EnterTimeWait(); + break; + default: + break; + } + } + } + + if (notify) + _NotifyReader(); + + if (buffer->size > 0 || (segment.flags & TCP_FLAG_SYNCHRONIZE) != 0) + action |= ACKNOWLEDGE; + + TRACE("Receive() Action %ld", action); + + return action; +} + + // #pragma mark - timer Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h 2007-04-15 14:46:12 UTC (rev 20705) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h 2007-04-15 17:34:52 UTC (rev 20706) @@ -86,6 +86,7 @@ ssize_t _AvailableData() const; void _NotifyReader(); bool _ShouldReceive() const; + int32 _Receive(tcp_segment_header& segment, net_buffer *buffer); static void _TimeWaitTimer(net_timer *timer, void *data); static void _RetransmitTimer(net_timer *timer, void *data); From axeld at pinc-software.de Sun Apr 15 19:49:49 2007 From: axeld at pinc-software.de (Axel =?iso-8859-15?q?D=F6rfler?=) Date: Sun, 15 Apr 2007 19:49:49 +0200 CEST Subject: [Haiku-commits] =?iso-8859-15?q?r20694_-_in_haiku/trunk/src/add-o?= =?iso-8859-15?q?ns/kernel/network/protocols=3A_ipv4_udp?= In-Reply-To: <9c46321e0704150740m750cef78ke6112be9fee2b505@mail.gmail.com> Message-ID: <31779650077-BeMail@zon> "Hugo Santos" wrote: > Do you feel it breaks the semantics because we are going up in the > hierarchy? I can add a new function instead to do the common work, > but > i think this fits nicely into an object oriented approach. That would have been my preferred solution, indeed :-) I find it rather strange that send_data() suddenly works vastly different from send_routed_data(). A separate function to carry out the extra work would be fine, though; that keeps the call chain intact. Bye, Axel. From hugosantos at gmail.com Sun Apr 15 20:00:53 2007 From: hugosantos at gmail.com (Hugo Santos) Date: Sun, 15 Apr 2007 19:00:53 +0100 Subject: [Haiku-commits] r20694 - in haiku/trunk/src/add-ons/kernel/network/protocols: ipv4 udp In-Reply-To: <31779650077-BeMail@zon> References: <9c46321e0704150740m750cef78ke6112be9fee2b505@mail.gmail.com> <31779650077-BeMail@zon> Message-ID: <9c46321e0704151100p36226857u5dedcf5891ea7772@mail.gmail.com> Ok, i'll try to do this today. Right now i'm concentrating on adding queueing to ARP, as we can't really wait on resolve(). Consider that a packet is generated inside the stack in reply to a received packet, resolve() won't work as it will be waiting for ARP replies which will never arrive. Possible paths include: -> device handler thread -> received ICMP Echo Request -> reply ICMP Echo reply -- ARP resolve() may fail here -> device handler thread -> received TCP SYN -> send TCP SYN/ACK -- and here Hugo On 4/15/07, Axel D?rfler wrote: > "Hugo Santos" wrote: > > Do you feel it breaks the semantics because we are going up in the > > hierarchy? I can add a new function instead to do the common work, > > but > > i think this fits nicely into an object oriented approach. > > That would have been my preferred solution, indeed :-) > I find it rather strange that send_data() suddenly works vastly > different from send_routed_data(). A separate function to carry out the > extra work would be fine, though; that keeps the call chain intact. > > Bye, > Axel. > > _______________________________________________ > Haiku-commits mailing list > Haiku-commits at lists.berlios.de > https://lists.berlios.de/mailman/listinfo/haiku-commits > From marcusoverhagen at mail.berlios.de Sun Apr 15 20:42:09 2007 From: marcusoverhagen at mail.berlios.de (marcusoverhagen at BerliOS) Date: Sun, 15 Apr 2007 20:42:09 +0200 Subject: [Haiku-commits] r20707 - in haiku/trunk/src/add-ons/media/media-add-ons: . dvb Message-ID: <200704151842.l3FIg9NG025405@sheep.berlios.de> Author: marcusoverhagen Date: 2007-04-15 20:42:03 +0200 (Sun, 15 Apr 2007) New Revision: 20707 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20707&view=rev Added: haiku/trunk/src/add-ons/media/media-add-ons/dvb/ haiku/trunk/src/add-ons/media/media-add-ons/dvb/DVBCard.cpp haiku/trunk/src/add-ons/media/media-add-ons/dvb/DVBCard.h haiku/trunk/src/add-ons/media/media-add-ons/dvb/DVBMediaAddon.cpp haiku/trunk/src/add-ons/media/media-add-ons/dvb/DVBMediaAddon.h haiku/trunk/src/add-ons/media/media-add-ons/dvb/DVBMediaNode.cpp haiku/trunk/src/add-ons/media/media-add-ons/dvb/DVBMediaNode.h haiku/trunk/src/add-ons/media/media-add-ons/dvb/MediaFormat.cpp haiku/trunk/src/add-ons/media/media-add-ons/dvb/MediaFormat.h haiku/trunk/src/add-ons/media/media-add-ons/dvb/Packet.cpp haiku/trunk/src/add-ons/media/media-add-ons/dvb/Packet.h haiku/trunk/src/add-ons/media/media-add-ons/dvb/PacketQueue.cpp haiku/trunk/src/add-ons/media/media-add-ons/dvb/PacketQueue.h haiku/trunk/src/add-ons/media/media-add-ons/dvb/StringList.h haiku/trunk/src/add-ons/media/media-add-ons/dvb/TransportStreamDemux.cpp haiku/trunk/src/add-ons/media/media-add-ons/dvb/TransportStreamDemux.h haiku/trunk/src/add-ons/media/media-add-ons/dvb/config.h haiku/trunk/src/add-ons/media/media-add-ons/dvb/media_header_ex.h haiku/trunk/src/add-ons/media/media-add-ons/dvb/mpeg_ts_packet.h haiku/trunk/src/add-ons/media/media-add-ons/dvb/pes.cpp haiku/trunk/src/add-ons/media/media-add-ons/dvb/pes.h Log: Media add-on for DVB. Added: haiku/trunk/src/add-ons/media/media-add-ons/dvb/DVBCard.cpp =================================================================== --- haiku/trunk/src/add-ons/media/media-add-ons/dvb/DVBCard.cpp 2007-04-15 17:34:52 UTC (rev 20706) +++ haiku/trunk/src/add-ons/media/media-add-ons/dvb/DVBCard.cpp 2007-04-15 18:42:03 UTC (rev 20707) @@ -0,0 +1,292 @@ +/* + * Copyright (c) 2004-2007 Marcus Overhagen + * + * Permission is hereby granted, free of charge, to any person + * obtaining a copy of this software and associated documentation + * files (the "Software"), to deal in the Software without restriction, + * including without limitation the rights to use, copy, modify, + * merge, publish, distribute, sublicense, and/or sell copies of + * the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be + * included in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES + * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT + * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, + * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + */ + +#include +#include +#include +#include +#include +#include +#include // required on BeOS R5 +#include + +#include "DVBCard.h" + + +DVBCard::DVBCard(const char *path) + : fInitStatus(B_OK) + , fDev(-1) +{ + printf("DVBCard opening %s\n", path); + + fDev = open(path, O_RDWR); + if (fDev < 0) { + printf("DVBCard opening %s failed\n", path); + fInitStatus = B_ERROR; + return; + } + + dvb_frequency_info_t info; + if (do_ioctl(fDev, DVB_GET_FREQUENCY_INFO, &info) < 0) { + printf("DVB_GET_FREQUENCY_INFO failed with error %s\n", strerror(errno)); +// close(fDev); +// fDev = -1; +// return; + } + + fFreqMin = info.frequency_min; + fFreqMax = info.frequency_max; + fFreqStep = info.frequency_step; + + fCaptureActive = false; +} + + +DVBCard::~DVBCard() +{ + if (fDev > 0) + close(fDev); +} + + +status_t +DVBCard::InitCheck() +{ + return fInitStatus; +} + + +status_t +DVBCard::GetCardType(dvb_type_t *type) +{ + dvb_interface_info_t info; + + if (do_ioctl(fDev, DVB_GET_INTERFACE_INFO, &info) < 0) { + printf("DVB_GET_INTERFACE_INFO failed with error %s\n", strerror(errno)); + return errno; + } + + if (info.version < 1) { + printf("DVBCard::GetCardInfo wrong API version\n"); + return B_ERROR; + } + + *type = info.type; + return B_OK; +} + + +status_t +DVBCard::GetCardInfo(char *_name, int max_name_len, char *_info, int max_info_len) +{ + dvb_interface_info_t info; + + if (do_ioctl(fDev, DVB_GET_INTERFACE_INFO, &info) < 0) { + printf("DVB_GET_INTERFACE_INFO failed with error %s\n", strerror(errno)); + return errno; + } + +// strlcpy(_name, info.name, max_name_len); +// strlcpy(_info, info.info, max_info_len); + strcpy(_name, info.name); + strcpy(_info, info.info); + + if (info.version < 1) { + printf("DVBCard::GetCardInfo wrong API version\n"); + return B_ERROR; + } + + return B_OK; +} + + +status_t +DVBCard::SetTuningParameter(const dvb_tuning_parameters_t& param) +{ + if (fDev < 0) + return B_NO_INIT; + + printf("DVBCard::SetTuningParameter:\n"); +/* + printf("frequency %Ld\n", param.frequency); + printf("inversion %d\n", param.inversion); + printf("bandwidth %d\n", param.bandwidth); + printf("modulation %d\n", param.modulation); + printf("hierarchy %d\n", param.hierarchy); + printf("code_rate_hp %d\n", param.code_rate_hp); + printf("code_rate_lp %d\n", param.code_rate_lp); + printf("transmission_mode %d\n", param.transmission_mode); + printf("guard_interval %d\n", param.guard_interval); + printf("symbolrate %d\n", param.symbolrate); + printf("polarity %d\n", param.polarity); + printf("agc_inversion %d\n", param.agc_inversion); +*/ + params = param;// XXX temporary! + +// if (do_ioctl(fDev, DVB_SET_TUNING_PARAMETERS, const_cast(¶m)) < 0) { +// if (do_ioctl(fDev, DVB_SET_TUNING_PARAMETERS, (void *)(¶m)) < 0) { + if (ioctl(fDev, DVB_SET_TUNING_PARAMETERS, (void *)(¶m)) < 0) { + printf("DVB_SET_TUNING_PARAMETERS failed with error %s\n", strerror(errno)); + return errno; + } + + dvb_status_t status; + + bigtime_t start = system_time(); + bool has_lock = false; + bool has_signal = false; + bool has_carrier = false; + do { + if (do_ioctl(fDev, DVB_GET_STATUS, &status) < 0) { + printf("DVB_GET_STATUS failed with error %s\n", strerror(errno)); + return errno; + } + if (!has_signal && status & DVB_STATUS_SIGNAL) { + has_signal = true; + printf("got signal after %.6f\n", (system_time() - start) / 1e6); + } + if (!has_carrier && status & DVB_STATUS_CARRIER) { + has_carrier = true; + printf("got carrier after %.6f\n", (system_time() - start) / 1e6); + } + if (!has_lock && status & DVB_STATUS_LOCK) { + has_lock = true; + printf("got lock after %.6f\n", (system_time() - start) / 1e6); + } + + if ((status & (DVB_STATUS_SIGNAL|DVB_STATUS_CARRIER|DVB_STATUS_LOCK)) == (DVB_STATUS_SIGNAL|DVB_STATUS_CARRIER|DVB_STATUS_LOCK)) + break; + snooze(25000); + } while ((system_time() - start) < 5000000); + + + if ((status & (DVB_STATUS_SIGNAL|DVB_STATUS_CARRIER|DVB_STATUS_LOCK)) != (DVB_STATUS_SIGNAL|DVB_STATUS_CARRIER|DVB_STATUS_LOCK)) { + printf("DVB tuning failed! need these status flags: DVB_STATUS_SIGNAL, DVB_STATUS_CARRIER, DVB_STATUS_LOCK\n"); + return B_ERROR; + } + + return B_OK; +} + + +status_t +DVBCard::GetTuningParameter(dvb_tuning_parameters_t *param) +{ + // XXX get from CARD + *param = params; + return B_OK; +} + + +status_t +DVBCard::GetSignalInfo(uint32 *ss, uint32 *ber, uint32 *snr) +{ + if (do_ioctl(fDev, DVB_GET_SS, ss) < 0) { + printf("DVB_GET_SS failed with error %s\n", strerror(errno)); + return errno; + } + if (do_ioctl(fDev, DVB_GET_BER, ber) < 0) { + printf("DVB_GET_BER failed with error %s\n", strerror(errno)); + return errno; + } + if (do_ioctl(fDev, DVB_GET_SNR, snr) < 0) { + printf("DVB_GET_SNR failed with error %s\n", strerror(errno)); + return errno; + } + + printf("ss %08lx, ber %08lx, snr %08lx\n", *ss, *ber, *snr); + printf("ss %lu%%, ber %lu%%, snr %lu%%\n", *ss / (0xffffffff / 100), *ber / (0xffffffff / 100), *snr / (0xffffffff / 100)); + return B_OK; +} + + +status_t +DVBCard::CaptureStart() +{ + printf("DVBCard::CaptureStart\n"); + + if (fCaptureActive) { + printf("CaptureStart already called, doing nothing\n"); + return B_OK; + } + + if (do_ioctl(fDev, DVB_START_CAPTURE, 0) < 0) { + printf("DVB_START_CAPTURE failed with error %s\n", strerror(errno)); + return errno; + } + + fCaptureActive = true; + return B_OK; +} + + +status_t +DVBCard::CaptureStop() +{ + printf("DVBCard::CaptureStop\n"); + + if (!fCaptureActive) { + printf("CaptureStop already called, doing nothing\n"); + return B_OK; + } + + if (do_ioctl(fDev, DVB_STOP_CAPTURE, 0) < 0) { + printf("DVB_STOP_CAPTURE failed with error %s\n", strerror(errno)); + return errno; + } + + fCaptureActive = false; + return B_OK; +} + + +status_t +DVBCard::Capture(void **data, size_t *size, bigtime_t *end_time) +{ + dvb_capture_t cap; + + if (ioctl(fDev, DVB_CAPTURE, &cap) < 0) + return errno; + + *data = cap.data; + *size = cap.size; + *end_time = cap.end_time; + + return B_OK; +} + + +int +DVBCard::do_ioctl(int fDev, ulong op, void *arg) +{ + int res = 0; // silence stupid compiler warning + int i; + for (i = 0; i < 20; i++) { + res = ioctl(fDev, op, arg); + if (res >= 0) + break; + } + if (i != 0) printf("ioctl %lx repeated %d times\n", op, i); + return res; +} Added: haiku/trunk/src/add-ons/media/media-add-ons/dvb/DVBCard.h =================================================================== --- haiku/trunk/src/add-ons/media/media-add-ons/dvb/DVBCard.h 2007-04-15 17:34:52 UTC (rev 20706) +++ haiku/trunk/src/add-ons/media/media-add-ons/dvb/DVBCard.h 2007-04-15 18:42:03 UTC (rev 20707) @@ -0,0 +1,66 @@ +/* + * Copyright (c) 2004-2007 Marcus Overhagen + * + * Permission is hereby granted, free of charge, to any person + * obtaining a copy of this software and associated documentation + * files (the "Software"), to deal in the Software without restriction, + * including without limitation the rights to use, copy, modify, + * merge, publish, distribute, sublicense, and/or sell copies of + * the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be + * included in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES + * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT + * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, + * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + */ + +#ifndef __DVB_CARD_H +#define __DVB_CARD_H + +#include "../drivers/cx23882/dvb.h" + +class DVBCard +{ +public: + DVBCard(const char *path); + ~DVBCard(); + + status_t InitCheck(); + + status_t GetCardType(dvb_type_t *type); + status_t GetCardInfo(char *name, int max_name_len, char *info, int max_info_len); + status_t GetSignalInfo(uint32 *ss, uint32 *ber, uint32 *snr); + + status_t SetTuningParameter(const dvb_tuning_parameters_t& param); + status_t GetTuningParameter(dvb_tuning_parameters_t *param); + + status_t CaptureStart(); + status_t CaptureStop(); + status_t Capture(void **data, size_t *size, bigtime_t *end_time); + +private: + + int do_ioctl(int fDev, ulong op, void *arg); + + status_t fInitStatus; + int fDev; + + int64 fFreqMin; + int64 fFreqMax; + int64 fFreqStep; + + bool fCaptureActive; + + dvb_tuning_parameters_t params; // XXX temporary cache +}; + + +#endif Added: haiku/trunk/src/add-ons/media/media-add-ons/dvb/DVBMediaAddon.cpp =================================================================== --- haiku/trunk/src/add-ons/media/media-add-ons/dvb/DVBMediaAddon.cpp 2007-04-15 17:34:52 UTC (rev 20706) +++ haiku/trunk/src/add-ons/media/media-add-ons/dvb/DVBMediaAddon.cpp 2007-04-15 18:42:03 UTC (rev 20707) @@ -0,0 +1,277 @@ +/* + * Copyright (c) 2004-2007 Marcus Overhagen + * + * Permission is hereby granted, free of charge, to any person + * obtaining a copy of this software and associated documentation + * files (the "Software"), to deal in the Software without restriction, + * including without limitation the rights to use, copy, modify, + * merge, publish, distribute, sublicense, and/or sell copies of + * the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be + * included in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES + * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT + * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, + * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + */ + +#include "DVBMediaAddon.h" +#include "DVBCard.h" +#include "DVBMediaNode.h" +#include "config.h" + +#include +#include +#include +#include +#include +#include +#include + +struct device_info +{ + DVBCard * card; + char name[200]; + char info[200]; + media_format formats[5]; + flavor_info flavor; + bool active; // workaround for zeta +}; + + +extern "C" BMediaAddOn * +make_media_addon(image_id id) +{ + return new DVBMediaAddon(id); +} + + +DVBMediaAddon::DVBMediaAddon(image_id id) + : BMediaAddOn(id) +{ + ScanFolder("/dev/dvb"); +} + + +DVBMediaAddon::~DVBMediaAddon() +{ + FreeDeviceList(); +} + + +status_t +DVBMediaAddon::InitCheck(const char ** out_failure_text) +{ + if (!fDeviceList.CountItems()) { + *out_failure_text = "No supported device found"; + return B_ERROR; + } + return B_OK; +} + + +int32 +DVBMediaAddon::CountFlavors() +{ + return fDeviceList.CountItems(); +} + + +status_t +DVBMediaAddon::GetFlavorAt(int32 n, const flavor_info ** out_info) +{ + device_info *dev = (device_info *)fDeviceList.ItemAt(n); + if (!dev) + return B_ERROR; + *out_info = &dev->flavor; + return B_OK; +} + + +BMediaNode * +DVBMediaAddon::InstantiateNodeFor(const flavor_info * info, BMessage * config, status_t * out_error) +{ + printf("DVB: DVBMediaAddon::InstantiateNodeFor\n"); + + device_info *dev = (device_info *)fDeviceList.ItemAt(info->internal_id); + if (!dev || dev->flavor.internal_id != info->internal_id) { + *out_error = B_ERROR; + return NULL; + } + *out_error = B_OK; + + // workaround for Zeta + if (dev->active) { + printf("DVB: max instances violation!!!\n"); + *out_error = B_ERROR; + return NULL; + } else { + dev->active = true; + } + + return new DVBMediaNode(this, dev->name, dev->flavor.internal_id, dev->card, &dev->active); +} + + +bool +DVBMediaAddon::WantsAutoStart() +{ +#if BUILD_FOR_HAIKU + printf("DVB: DVBMediaAddon::WantsAutoStart - NO\n"); + return false; +#else + printf("DVB: DVBMediaAddon::WantsAutoStart - YES\n"); + return true; +#endif +} + + +status_t +DVBMediaAddon::AutoStart(int index, BMediaNode **outNode, int32 *outInternalID, bool *outHasMore) +{ + printf("DVB: DVBMediaAddon::AutoStart, index %d\n", index); + +#if BUILD_FOR_HAIKU + return B_ERROR; +#else + + device_info *dev = (device_info *)fDeviceList.ItemAt(index); + if (!dev) { + printf("DVB: DVBMediaAddon::AutoStart, bad index\n"); + return B_BAD_INDEX; + } + + *outHasMore = fDeviceList.ItemAt(index + 1) ? true : false; + + // workaround for Zeta + if (dev->active) { + printf("DVB: max instances violation!!!\n"); + *outInternalID = -1; + *outNode = NULL; + return B_MEDIA_ADDON_FAILED; + } + + dev->active = true; + + *outInternalID = dev->flavor.internal_id; + *outNode = new DVBMediaNode(this, dev->name, dev->flavor.internal_id, dev->card, &dev->active); + + printf("DVB: DVBMediaAddon::AutoStart, success\n"); + + return B_OK; +#endif +} + + +void +DVBMediaAddon::ScanFolder(const char *path) +{ + BDirectory dir(path); + if (dir.InitCheck() != B_OK) + return; + + BEntry ent; + + while (dir.GetNextEntry(&ent) == B_OK) { + BPath path(&ent); + if (ent.IsDirectory()) { + ScanFolder(path.Path()); + } else { + DVBCard *card = new DVBCard(path.Path()); + if (card->InitCheck() == B_OK) + AddDevice(card, path.Path()); + else + delete card; + } + } +} + + +void +DVBMediaAddon::AddDevice(DVBCard *card, const char *path) +{ + dvb_type_t type; + char name[250]; + char info[1000]; + const char *dvbtype; + const char *dvbnumber; + + // get card name, info and type + if (B_OK != card->GetCardType(&type)) { + printf("DVBMediaAddon::AddDevice: getting DVB card type failed\n"); + return; + } + if (B_OK != card->GetCardInfo(name, sizeof(name), info, sizeof(info))) { + printf("DVBMediaAddon::AddDevice: getting DVB card info failed\n"); + return; + } + + // get type + switch (type) { + case DVB_TYPE_DVB_C: dvbtype = "C"; break; + case DVB_TYPE_DVB_H: dvbtype = "H"; break; + case DVB_TYPE_DVB_S: dvbtype = "S"; break; + case DVB_TYPE_DVB_T: dvbtype = "T"; break; + default: + printf("DVBMediaAddon::AddDevice: unsupported DVB type %d\n", type); + return; + } + + // get interface number + const char *p = strrchr(path, '/'); + dvbnumber = p ? p + 1 : ""; + + // create device_info + device_info *dev = new device_info; + fDeviceList.AddItem(dev); + + dev->card = card; + + dev->active = false; // workaround for Zeta + + // setup name and info, it's important that name starts with "DVB" +// snprintf(dev->name, sizeof(dev->name), "DVB-%s %s (%s)", dvbtype, dvbnumber, name); +// strlcpy(dev->info, info, sizeof(dev->info)); + sprintf(dev->name, "DVB-%s %s %s", dvbtype, name, dvbnumber); + strcpy(dev->info, info); + + // setup supported formats (the lazy way) + memset(dev->formats, 0, sizeof(dev->formats)); + dev->formats[0].type = B_MEDIA_RAW_VIDEO; + dev->formats[1].type = B_MEDIA_RAW_AUDIO; + dev->formats[2].type = B_MEDIA_ENCODED_VIDEO; + dev->formats[3].type = B_MEDIA_ENCODED_AUDIO; + dev->formats[4].type = B_MEDIA_MULTISTREAM; + + // setup flavor info + dev->flavor.name = dev->name; + dev->flavor.info = dev->info; + dev->flavor.kinds = B_BUFFER_PRODUCER | B_CONTROLLABLE | B_PHYSICAL_INPUT; + dev->flavor.flavor_flags = B_FLAVOR_IS_GLOBAL; + dev->flavor.internal_id = fDeviceList.CountItems() - 1; + dev->flavor.possible_count = 1; + dev->flavor.in_format_count = 0; + dev->flavor.in_format_flags = 0; + dev->flavor.in_formats = 0; + dev->flavor.out_format_count = 5; + dev->flavor.out_format_flags = 0; + dev->flavor.out_formats = dev->formats; +} + + +void +DVBMediaAddon::FreeDeviceList() +{ + device_info *dev; + while ((dev = (device_info *)fDeviceList.RemoveItem((int32)0))) { + delete dev->card; + delete dev; + } +} Added: haiku/trunk/src/add-ons/media/media-add-ons/dvb/DVBMediaAddon.h =================================================================== --- haiku/trunk/src/add-ons/media/media-add-ons/dvb/DVBMediaAddon.h 2007-04-15 17:34:52 UTC (rev 20706) +++ haiku/trunk/src/add-ons/media/media-add-ons/dvb/DVBMediaAddon.h 2007-04-15 18:42:03 UTC (rev 20707) @@ -0,0 +1,59 @@ +/* + * Copyright (c) 2004-2007 Marcus Overhagen + * + * Permission is hereby granted, free of charge, to any person + * obtaining a copy of this software and associated documentation + * files (the "Software"), to deal in the Software without restriction, + * including without limitation the rights to use, copy, modify, + * merge, publish, distribute, sublicense, and/or sell copies of + * the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be + * included in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES + * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT + * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, + * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + */ + +#ifndef _DVB_MEDIA_ADDON_H_ +#define _DVB_MEDIA_ADDON_H_ + +#include + +class DVBCard; + +class DVBMediaAddon : public BMediaAddOn +{ +public: + DVBMediaAddon(image_id id); + ~DVBMediaAddon(); + + status_t InitCheck(const char **out_failure_text); + + int32 CountFlavors(); + + status_t GetFlavorAt(int32 n, const flavor_info **out_info); + + BMediaNode *InstantiateNodeFor(const flavor_info *info, BMessage *config, status_t *out_error); + + bool WantsAutoStart(); + status_t AutoStart(int index, BMediaNode **outNode, int32 *outInternalID, bool *outHasMore); + +protected: + void ScanFolder(const char *path); + + void AddDevice(DVBCard *card, const char *path); + void FreeDeviceList(); + +protected: + BList fDeviceList; +}; + +#endif Added: haiku/trunk/src/add-ons/media/media-add-ons/dvb/DVBMediaNode.cpp =================================================================== --- haiku/trunk/src/add-ons/media/media-add-ons/dvb/DVBMediaNode.cpp 2007-04-15 17:34:52 UTC (rev 20706) +++ haiku/trunk/src/add-ons/media/media-add-ons/dvb/DVBMediaNode.cpp 2007-04-15 18:42:03 UTC (rev 20707) @@ -0,0 +1,2701 @@ +/* + * Copyright (c) 2004-2007 Marcus Overhagen + * + * Permission is hereby granted, free of charge, to any person + * obtaining a copy of this software and associated documentation + * files (the "Software"), to deal in the Software without restriction, + * including without limitation the rights to use, copy, modify, + * merge, publish, distribute, sublicense, and/or sell copies of + * the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be + * included in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES + * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT + * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, + * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + */ + +#include +#include +#include +#include +#include +#include +#include +#include + +#include +#include +#include +#include +#include +#include +#include +#include + +#include +#include +#include + +#include "DefaultDecoder.h" +#include "Support.h" +#include "HeaderFormat.h" +#include "packet.h" +#include "packet_queue.h" +#include "pes_extract.h" +#include "media_header_ex.h" +#include "config.h" + +//#define DUMP_VIDEO +//#define DUMP_AUDIO +//#define DUMP_RAW_AUDIO + + +#include "DVBMediaNode.h" + +#define ENABLE_TRACE +//#define ENABLE_TRACE_TIMING + +#undef TRACE + +#ifdef ENABLE_TRACE + #define TRACE printf +#else + #define TRACE(a...) +#endif + +#ifdef ENABLE_TRACE_TIMING + #define TRACE_TIMING printf +#else + #define TRACE_TIMING(a...) +#endif + +#define RETURN_IF_ERROR(expr) { status_t e = (expr); if (e != B_OK) return e; } + +#define ID_RAW_VIDEO 0 +#define ID_RAW_AUDIO 1 +#define ID_ENC_VIDEO 2 +#define ID_ENC_AUDIO 3 +#define ID_TS 4 + +// Timeouts for requesting buffers, if the system is busy, +// the output buffer queue is full, requesting a buffer will +// timeout, and we need to drop the current data +#define VIDEO_BUFFER_REQUEST_TIMEOUT 20000 +#define AUDIO_BUFFER_REQUEST_TIMEOUT 10000 + +// DVB data arrives early and with a timestamp, this is used to validate +// that the timestamp is correct and we don't get stuck +#define VIDEO_MAX_EARLY 3000000 // up to 3 seconds too early +#define VIDEO_MAX_LATE 50000 // no more than 50 ms too late +#define AUDIO_MAX_EARLY 3000000 // up to 3 seconds too early +#define AUDIO_MAX_LATE 50000 // no more than 50 ms too late + +#define PROCESSING_LATENCY 1500 // assumed latency for sending the buffer + +#define STOP_CAPTURE_WHILE_TUNING 1 + +#define MPEG2_VIDEO_DECODER_PATH "/boot/home/config/add-ons/media/dvb/video_decoder_addon" +#define MPEG2_AUDIO_DECODER_PATH "/boot/home/config/add-ons/media/dvb/audio_decoder_addon" +#define AC3_AUDIO_DECODER_PATH "/boot/home/config/add-ons/media/dvb/ac3_decoder_addon" +#define DEINTERLACE_FILTER_PATH "/boot/home/config/add-ons/media/dvb/deinterlace_filter_addon" + + +#define M_REFRESH_PARAMETER_WEB (BTimedEventQueue::B_USER_EVENT + 1) + + +DVBMediaNode::DVBMediaNode( + BMediaAddOn *addon, const char *name, + int32 internal_id, DVBCard *card, bool *active) // bool *active is a workaround for Zeta + : BMediaNode(name) + , BMediaEventLooper() + , BBufferProducer(B_MEDIA_RAW_VIDEO) + , BControllable() + , fStopDisabled(false) + , fOutputEnabledRawVideo(false) + , fOutputEnabledRawAudio(false) + , fOutputEnabledEncVideo(false) + , fOutputEnabledEncAudio(false) + , fOutputEnabledTS(false) + , fCardDataQueue(new PacketQueue(6)) + , fRawVideoQueue(new PacketQueue(56)) + , fRawAudioQueue(new PacketQueue(56)) + , fEncVideoQueue(new PacketQueue(56)) + , fEncAudioQueue(new PacketQueue(56)) + , fMpegTsQueue(new PacketQueue(16)) + , fCard(card) + , fCaptureThreadsActive(false) + , fThreadIdCardReader(-1) + , fThreadIdMpegDemux(-1) + , fThreadIdRawAudio(-1) + , fThreadIdRawVideo(-1) + , fThreadIdEncAudio(-1) + , fThreadIdEncVideo(-1) + , fThreadIdMpegTS(-1) + , fTerminateThreads(false) + , fDemux(new TSDemux(fRawVideoQueue, fRawAudioQueue, fEncVideoQueue, fEncAudioQueue, fMpegTsQueue)) + , fBufferGroupRawVideo(0) + , fBufferGroupRawAudio(0) + , fInterfaceType(DVB_TYPE_UNKNOWN) + , fAudioPid(-1) + , fVideoPid(-1) + , fPcrPid(-1) + , fTuningSuccess(false) + , fCaptureActive(false) + , fVideoDelaySem(create_sem(0, "video delay sem")) + , fAudioDelaySem(create_sem(0, "audio delay sem")) + , fSelectedState(-1) + , fSelectedRegion(-1) + , fSelectedChannel(-1) + , fSelectedAudio(-1) + , fStateList(new StringList) + , fRegionList(new StringList) + , fChannelList(new StringList) + , fAudioList(new StringList) + , fVideoDecoder(0) + , fAudioDecoder(0) + , fCurrentVideoPacket(0) + , fCurrentAudioPacket(0) + , fMpeg2VideoDecoderImage(-1) + , fMpeg2AudioDecoderImage(-1) + , fAC3DecoderImage(-1) + , fDeinterlaceFilterImage(-1) + , instantiate_mpeg2_video_decoder(NULL) + , instantiate_mpeg2_audio_decoder(NULL) + , instantiate_ac3_audio_decoder(NULL) + , instantiate_deinterlace_filter(NULL) + , fActive(active) +{ + TRACE("DVBMediaNode::DVBMediaNode\n"); + + AddNodeKind(B_PHYSICAL_INPUT); + + fInternalID = internal_id; + fAddOn = addon; + + fInitStatus = B_OK; + + LoadAddons(); + + InitDefaultFormats(); + + // in the beginning, the required formats are the same as the defaults + fRequiredFormatRawVideo = fDefaultFormatRawVideo; + fRequiredFormatRawAudio = fDefaultFormatRawAudio; + fRequiredFormatEncVideo = fDefaultFormatEncVideo; + fRequiredFormatEncAudio = fDefaultFormatEncAudio; + fRequiredFormatTS = fDefaultFormatTS; + + // start the BMediaEventLooper control loop running + Run(); + + TRACE("current RunMode = %d\n", RunMode()); + +#ifdef DUMP_VIDEO + fVideoFile = open("/boot/home/dvb-video.mpg", O_RDWR | O_CREAT | O_TRUNC); +#endif +#ifdef DUMP_AUDIO + fAudioFile = open("/boot/home/dvb-audio.mpg", O_RDWR | O_CREAT | O_TRUNC); +#endif +#ifdef DUMP_RAW_AUDIO + fRawAudioFile = open("/boot/home/dvb-audio.raw", O_RDWR | O_CREAT | O_TRUNC); +#endif +} + + +DVBMediaNode::~DVBMediaNode() +{ + TRACE("DVBMediaNode::~DVBMediaNode\n"); + + StopCapture(); + + delete_sem(fVideoDelaySem); + delete_sem(fAudioDelaySem); + + // fCard is owned by the media addon + delete fCardDataQueue; + delete fRawVideoQueue; + delete fRawAudioQueue; + delete fEncVideoQueue; + delete fEncAudioQueue; + delete fMpegTsQueue; + + delete fDemux; + +printf("deleting video buffer group...\n"); + delete fBufferGroupRawVideo; +printf("deleting video buffer group done\n"); + +printf("deleting audio buffer group...\n"); + // deleting the audio buffer group does hang on Zeta neo, + // but works on Haiku and seems to work on Zeta 1.0 with updated media_server + delete fBufferGroupRawAudio; +printf("deleting audio buffer group done\n"); + + delete fStateList; + delete fRegionList; + delete fChannelList; + delete fAudioList; + + UnloadAddons(); + +#ifdef DUMP_VIDEO + close(fVideoFile); +#endif +#ifdef DUMP_AUDIO + close(fAudioFile); +#endif +#ifdef DUMP_RAW_AUDIO + close(fRawAudioFile); +#endif + + *fActive = false; // workaround for zeta +} + + +image_id +DVBMediaNode::LoadAddon(const char *path, const char *name, void **ptr) +{ + image_id id = load_add_on(path); + if (id <= 0) { + *ptr = NULL; + printf("loading addon '%s' failed\n", path); + return -1; + } + status_t s = get_image_symbol(id, name, B_SYMBOL_TYPE_TEXT, ptr); + if (s < B_OK) { + unload_add_on(id); + *ptr = NULL; + printf("locating function '%s' in addon '%s' failed\n", name, path); + return -1; [... truncated: 4298 lines follow ...] From marcusoverhagen at mail.berlios.de Sun Apr 15 20:43:39 2007 From: marcusoverhagen at mail.berlios.de (marcusoverhagen at BerliOS) Date: Sun, 15 Apr 2007 20:43:39 +0200 Subject: [Haiku-commits] r20708 - haiku/trunk/src/apps Message-ID: <200704151843.l3FIhd6p025650@sheep.berlios.de> Author: marcusoverhagen Date: 2007-04-15 20:43:38 +0200 (Sun, 15 Apr 2007) New Revision: 20708 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20708&view=rev Added: haiku/trunk/src/apps/tv/ Log: directory for TV app From bonefish at cs.tu-berlin.de Sun Apr 15 20:53:14 2007 From: bonefish at cs.tu-berlin.de (Ingo Weinhold) Date: Sun, 15 Apr 2007 20:53:14 +0200 Subject: [Haiku-commits] r20688 - haiku/trunk/src/add-ons/tracker/filetype In-Reply-To: <20070415110636.358.1@stippis.nameserver> References: <200704142322.l3ENMpQL006101@sheep.berlios.de> <20070415035345.4747.3@cs.tu-berlin.de> <20070415110636.358.1@stippis.nameserver> Message-ID: <20070415205314.1003.2@cs.tu-berlin.de> On 2007-04-15 at 11:06:36 [+0200], Stephan Assmus wrote: > > On 2007-04-15 at 03:53:45 [+0200], Ingo Weinhold > wrote: > > > > On 2007-04-15 at 01:22:51 [+0200], stippi at BerliOS > > > > wrote: > > > Author: stippi > > > Date: 2007-04-15 01:22:51 +0200 (Sun, 15 Apr 2007) > > > New Revision: 20688 > > > ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20688&view=rev > > > > > > Modified: > > > haiku/trunk/src/add-ons/tracker/filetype/FileType.rdef > > > haiku/trunk/src/add-ons/tracker/filetype/Jamfile > > > Log: > > > * added same vector icon as FileTypes preflet, but somehow the > > > resources are not added for the "Addon" target type? Ingo? > > > > Works fine here (tested under Linux). What exactly goes wrong on your > > machine? > > Hm. I just don't see the icon. That's all. Since I can't reproduce the problem -- I can see the nice new icon under Haiku -- can you please investigate the problem a bit. Apparently the attribute is not there. Is the resource? If not, what happens when touching the rdef file and rerunning "jam -q FileType-F"? CU, Ingo From marcusoverhagen at mail.berlios.de Sun Apr 15 20:58:06 2007 From: marcusoverhagen at mail.berlios.de (marcusoverhagen at BerliOS) Date: Sun, 15 Apr 2007 20:58:06 +0200 Subject: [Haiku-commits] r20709 - haiku/trunk/src/apps/tv Message-ID: <200704151858.l3FIw6Yu027841@sheep.berlios.de> Author: marcusoverhagen Date: 2007-04-15 20:58:05 +0200 (Sun, 15 Apr 2007) New Revision: 20709 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20709&view=rev Added: haiku/trunk/src/apps/tv/Controller.cpp haiku/trunk/src/apps/tv/Controller.h haiku/trunk/src/apps/tv/ConvertBitmap.cpp haiku/trunk/src/apps/tv/ConvertBitmap.h haiku/trunk/src/apps/tv/DeviceRoster.cpp haiku/trunk/src/apps/tv/DeviceRoster.h haiku/trunk/src/apps/tv/MainApp.cpp haiku/trunk/src/apps/tv/MainApp.h haiku/trunk/src/apps/tv/MainWin.cpp haiku/trunk/src/apps/tv/MainWin.h haiku/trunk/src/apps/tv/VideoNode.cpp haiku/trunk/src/apps/tv/VideoNode.h haiku/trunk/src/apps/tv/VideoView.cpp haiku/trunk/src/apps/tv/VideoView.h haiku/trunk/src/apps/tv/config.h Log: The DVB TV application, can probably be used as a generic TV application, or even merged with MediaPlayer and CDPlayer later. Added: haiku/trunk/src/apps/tv/Controller.cpp =================================================================== --- haiku/trunk/src/apps/tv/Controller.cpp 2007-04-15 18:43:38 UTC (rev 20708) +++ haiku/trunk/src/apps/tv/Controller.cpp 2007-04-15 18:58:05 UTC (rev 20709) @@ -0,0 +1,494 @@ +/* + * Copyright (c) 2004-2007 Marcus Overhagen + * + * Permission is hereby granted, free of charge, to any person + * obtaining a copy of this software and associated documentation + * files (the "Software"), to deal in the Software without restriction, + * including without limitation the rights to use, copy, modify, + * merge, publish, distribute, sublicense, and/or sell copies of + * the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be + * included in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES + * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT + * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, + * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + */ + +#include +#include +#include +#include +#include + +#include "Controller.h" +#include "DeviceRoster.h" +#include "VideoView.h" +#include "VideoNode.h" + +extern bool gOverlayDisabled; + +status_t MediaRoster_Disconnect(const media_output &output, const media_input &input); + + + +media_node dvb_node; +media_node audio_mixer_node; +media_node video_window_node; +media_node time_node; + +media_input audio_input; +media_output audio_output; +media_input video_input; +media_output video_output; + +BMediaRoster *gMediaRoster; + +void +HandleError(const char *text, status_t err) +{ + if (err != B_OK) { + printf("%s. error 0x%08x (%s)\n",text, (int)err, strerror(err)); + fflush(NULL); + exit(1); + } +} + + +Controller::Controller() + : fCurrentInterface(-1) + , fCurrentChannel(-1) + , fVideoView(NULL) + , fVideoNode(NULL) + , fWeb(NULL) + , fChannelParam(NULL) + , fConnected(false) + , fInput() + , fOutput() +{ + gMediaRoster = BMediaRoster::Roster(); +} + + +Controller::~Controller() +{ + delete fWeb; +} + + +void +Controller::SetVideoView(VideoView *view) +{ + fVideoView = view; +} + + +void +Controller::SetVideoNode(VideoNode *node) +{ + fVideoNode = node; +} + + +void +Controller::DisconnectInterface() +{ + DisconnectNodes(); + fCurrentInterface = -1; + fCurrentChannel = -1; + delete fWeb; + fWeb = 0; + fChannelParam = 0; +} + + +status_t +Controller::ConnectInterface(int i) +{ + if (i < 0) { + printf("Controller::ConnectInterface: wrong index\n"); + return B_ERROR; + } + if (fCurrentInterface != -1) { + printf("Controller::ConnectInterface: already connected\n"); + return B_ERROR; + } + + BParameterWeb *web; + status_t err; + + err = gDeviceRoster->MediaRoster()->GetParameterWebFor(gDeviceRoster->DeviceNode(i), &web); + if (err != B_OK) { + printf("Controller::ConnectInterface: can't get parameter web\n"); + return B_ERROR; + } + + delete fWeb; + fWeb = web; + fCurrentInterface = i; + + // XXX we may need to monitor for parameter web changes + // and reassing fWeb and fChannelParam on demand. + + // find the channel control and assign it to fChannelParam + fChannelParam = NULL; + int count = fWeb->CountParameters(); + for (int i = 0; i < count; i++) { + BParameter *parameter = fWeb->ParameterAt(i); + + printf("parameter %d\n", i); + printf(" name '%s'\n", parameter->Name()); + printf(" kind '%s'\n", parameter->Kind()); + printf(" unit '%s'\n", parameter->Unit()); + printf(" flags 0x%08lx\n", parameter->Flags()); + + // XXX TODO: matching on Name is weak + if (strcmp(parameter->Name(), "Channel") == 0 || strcmp(parameter->Kind(), B_TUNER_CHANNEL) == 0) { + fChannelParam = dynamic_cast(parameter); + if (fChannelParam) + break; + } + } + if (!fChannelParam) { + printf("Controller::ConnectInterface: can't find channel parameter control\n"); + fCurrentChannel = -1; + } else { + if (fChannelParam->CountItems() == 0) { + fCurrentChannel = -1; + printf("Controller::ConnectInterface: channel control has 0 items\n"); + } else { + int32 index; + size_t size; + status_t err; + bigtime_t when; + size = sizeof(index); + err = fChannelParam->GetValue(&index, &size, &when); + if (err == B_OK && size == sizeof(index)) { + fCurrentChannel = index; + printf("Controller::ConnectInterface: selected channel is %d\n", fCurrentChannel); + } else { + fCurrentChannel = -1; + printf("Controller::ConnectInterface: can't get channel control value\n"); + } + } + } + + ConnectNodes(); + + return B_OK; +} + + +bool +Controller::IsInterfaceAvailable(int i) +{ + return gDeviceRoster->IsRawAudioOutputFree(i) && gDeviceRoster->IsRawVideoOutputFree(i); +} + + +int +Controller::CurrentInterface() +{ + return fCurrentInterface; +} + + +int +Controller::CurrentChannel() +{ + return fCurrentChannel; +} + + +status_t +Controller::SelectChannel(int i) +{ + if (!fChannelParam) + return B_ERROR; + + int32 index; + status_t err; + index = i; + err = fChannelParam->SetValue(&index, sizeof(index), 0); + if (err != B_OK) { + printf("Controller::SelectChannel %d failed\n", i); + return err; + } + + fCurrentChannel = i; + return B_OK; +} + + +int +Controller::ChannelCount() +{ + if (fCurrentInterface == -1) + return 0; + + if (!fChannelParam) + return 0; + + return fChannelParam->CountItems(); +} + + +const char * +Controller::ChannelName(int i) +{ + if (fCurrentInterface == -1) + return NULL; + + if (!fChannelParam) + return NULL; + + return fChannelParam->ItemNameAt(i); +} + + +void +Controller::VolumeUp() +{ +} + + +void +Controller::VolumeDown() +{ +} + + +status_t +Controller::ConnectNodes() +{ + status_t err; + +// dvb_node = gDeviceRoster->DeviceNode(fCurrentInterface); + + err = gMediaRoster->GetNodeFor(gDeviceRoster->DeviceNode(fCurrentInterface).node, &dvb_node); + HandleError("GetNodeFor failed", err); + + video_window_node = fVideoNode->Node(); + + err = gMediaRoster->GetAudioMixer(&audio_mixer_node); + HandleError("GetAudioMixer failed", err); + + media_input input; + media_output output; + media_format fmt; + int32 count; + + // Connect audio + + err = gMediaRoster->GetFreeOutputsFor(dvb_node, &output, 1, &count, B_MEDIA_RAW_AUDIO); + HandleError("Can't find free audio output", err); + if (count < 1) + HandleError("No free audio output", -1); + + err = gMediaRoster->GetFreeInputsFor(audio_mixer_node, &input, 1, &count, B_MEDIA_RAW_AUDIO); + HandleError("Can't find free audio input", err); + if (count < 1) + HandleError("No free audio input", -1); + + memset(&fmt, 0, sizeof(fmt)); + err = gMediaRoster->Connect(output.source, input.destination, &fmt, &audio_output, &audio_input); + HandleError("Can't connect audio", err); + + // Connect video + + err = gMediaRoster->GetFreeOutputsFor(dvb_node, &output, 1, &count, B_MEDIA_RAW_VIDEO); + HandleError("Can't find free video output", err); + if (count < 1) + HandleError("No free video output", -1); + + err = gMediaRoster->GetFreeInputsFor(video_window_node, &input, 1, &count, B_MEDIA_RAW_VIDEO); + HandleError("Can't find free video input", err); + if (count < 1) + HandleError("No free video input", -1); + + color_space cspaces_overlay[] = { B_YCbCr422, B_RGB32, B_NO_COLOR_SPACE }; + color_space cspaces_bitmap[] = { B_RGB32, B_NO_COLOR_SPACE }; + + if (gOverlayDisabled) { + err = B_ERROR; + } else { + fVideoNode->SetOverlayEnabled(true); + for (int i = 0; cspaces_overlay[i] != B_NO_COLOR_SPACE; i++) { + printf("trying connect with colorspace 0x%08x\n", cspaces_overlay[i]); + memset(&fmt, 0, sizeof(fmt)); + fmt.type = B_MEDIA_RAW_VIDEO; + fmt.u.raw_video.display.format = cspaces_overlay[i]; + err = gMediaRoster->Connect(output.source, input.destination, &fmt, &video_output, &video_input); + if (err == B_OK) + break; + } + } + if (err) { + fVideoNode->SetOverlayEnabled(false); + for (int i = 0; cspaces_bitmap[i] != B_NO_COLOR_SPACE; i++) { + printf("trying connect with colorspace 0x%08x\n", cspaces_bitmap[i]); + memset(&fmt, 0, sizeof(fmt)); + fmt.type = B_MEDIA_RAW_VIDEO; + fmt.u.raw_video.display.format = cspaces_bitmap[i]; + err = gMediaRoster->Connect(output.source, input.destination, &fmt, &video_output, &video_input); + if (err == B_OK) + break; + } + } + HandleError("Can't connect video", err); + + // set time sources + + err = gMediaRoster->GetTimeSource(&time_node); + HandleError("Can't get time source", err); + + BTimeSource *ts = gMediaRoster->MakeTimeSourceFor(time_node); + + err = gMediaRoster->SetTimeSourceFor(dvb_node.node, time_node.node); + HandleError("Can't set dvb time source", err); + + err = gMediaRoster->SetTimeSourceFor(audio_mixer_node.node, time_node.node); + HandleError("Can't set audio mixer time source", err); + + err = gMediaRoster->SetTimeSourceFor(video_window_node.node, time_node.node); + HandleError("Can't set video window time source", err); + + // Add a delay of (2 video frames) to the buffers send by the DVB node, + // because as a capture device in B_RECORDING run mode it's supposed to + // deliver buffers that were captured in the past (and does so). + // It is important that the audio buffer size used by the connection with + // the DVB node is smaller than this, optimum is the same length as one + // video frame (40 ms). However, this is not yet guaranteed. + err = gMediaRoster->SetProducerRunModeDelay(dvb_node, 80000); + HandleError("Can't set DVB producer delay", err); + + bigtime_t start_time = ts->Now() + 50000; + + ts->Release(); + + // start nodes + + err = gMediaRoster->StartNode(dvb_node, start_time); + HandleError("Can't start dvb node", err); + + err = gMediaRoster->StartNode(audio_mixer_node, start_time); + HandleError("Can't start audio mixer node", err); + + err = gMediaRoster->StartNode(video_window_node, start_time); + HandleError("Can't start video window node", err); + + printf("running...\n"); + + fConnected = true; + + return B_OK; +} + + +status_t +Controller::DisconnectNodes() +{ + printf("stopping...\n"); + + if (!fConnected) + return B_OK; + + status_t err; + + // stop nodes + + err = gMediaRoster->StopNode(dvb_node, 0, true); + HandleError("Can't stop dvb node", err); + + err = gMediaRoster->StopNode(audio_mixer_node, 0, true); + HandleError("Can't stop audio mixer node", err); + + err = gMediaRoster->StopNode(video_window_node, 0, true); + HandleError("Can't stop video window node", err); + + // disconnect nodes + + err = MediaRoster_Disconnect(video_output, video_input); + HandleError("Can't disconnect video", err); + + err = MediaRoster_Disconnect(audio_output, audio_input); + HandleError("Can't disconnect audio", err); + + // disable overlay, or erase image + + fVideoView->RemoveVideoDisplay(); + + // release other nodes + + err = gMediaRoster->ReleaseNode(audio_mixer_node); + HandleError("Can't release audio mixer node", err); + +// err = gMediaRoster->ReleaseNode(video_window_node); +// HandleError("Can't release video window node", err); + +// err = gMediaRoster->ReleaseNode(time_node); +// HandleError("Can't release time source node", err); + + // release dvb + + err = gMediaRoster->ReleaseNode(dvb_node); + HandleError("Can't release DVB node", err); + + fConnected = false; + + return B_OK; +} + + +status_t +MediaRoster_Disconnect(const media_output &output, const media_input &input) +{ + if (output.node.node <= 0) { + printf("MediaRoster_Disconnect: output.node.node %d invalid\n", + (int)output.node.node); + return B_MEDIA_BAD_NODE; + } + if (input.node.node <= 0) { + printf("MediaRoster_Disconnect: input.node.node %d invalid\n", + (int)input.node.node); + return B_MEDIA_BAD_NODE; + } + if (!(output.node.kind & B_BUFFER_PRODUCER)) { + printf("MediaRoster_Disconnect: output.node.kind 0x%x is no B_BUFFER_PRODUCER\n", + (int)output.node.kind); + return B_MEDIA_BAD_NODE; + } + if (!(input.node.kind & B_BUFFER_CONSUMER)) { + printf("MediaRoster_Disconnect: input.node.kind 0x%x is no B_BUFFER_PRODUCER\n", + (int)input.node.kind); + return B_MEDIA_BAD_NODE; + } + if (input.source.port != output.source.port) { + printf("MediaRoster_Disconnect: input.source.port %d doesn't match output.source.port %d\n", + (int)input.source.port, (int)output.source.port); + return B_MEDIA_BAD_NODE; + } + if (input.source.id != output.source.id) { + printf("MediaRoster_Disconnect: input.source.id %d doesn't match output.source.id %d\n", + (int)input.source.id, (int)output.source.id); + return B_MEDIA_BAD_NODE; + } + if (input.destination.port != output.destination.port) { + printf("MediaRoster_Disconnect: input.destination.port %d doesn't match output.destination.port %d\n", + (int)input.destination.port, (int)output.destination.port); + return B_MEDIA_BAD_NODE; + } + if (input.destination.id != output.destination.id) { + printf("MediaRoster_Disconnect: input.destination.id %d doesn't match output.destination.id %d\n", + (int)input.destination.id, (int)output.destination.id); + return B_MEDIA_BAD_NODE; + } + return BMediaRoster::Roster()->Disconnect(output.node.node, output.source, input.node.node, input.destination); +} Added: haiku/trunk/src/apps/tv/Controller.h =================================================================== --- haiku/trunk/src/apps/tv/Controller.h 2007-04-15 18:43:38 UTC (rev 20708) +++ haiku/trunk/src/apps/tv/Controller.h 2007-04-15 18:58:05 UTC (rev 20709) @@ -0,0 +1,75 @@ +/* + * Copyright (c) 2004-2007 Marcus Overhagen + * + * Permission is hereby granted, free of charge, to any person + * obtaining a copy of this software and associated documentation + * files (the "Software"), to deal in the Software without restriction, + * including without limitation the rights to use, copy, modify, + * merge, publish, distribute, sublicense, and/or sell copies of + * the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be + * included in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES + * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT + * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, + * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + */ + +#ifndef __CONTROLLER_H +#define __CONTROLLER_H + +#include +#include +#include + +class VideoView; +class VideoNode; + +class Controller +{ +public: + Controller(); + virtual ~Controller(); + + void SetVideoView(VideoView *view); + void SetVideoNode(VideoNode *node); + + void DisconnectInterface(); + status_t ConnectInterface(int i); + + bool IsInterfaceAvailable(int i); + int CurrentInterface(); + + int ChannelCount(); + int CurrentChannel(); + status_t SelectChannel(int i); + const char * ChannelName(int i); + + void VolumeUp(); + void VolumeDown(); + +private: + status_t ConnectNodes(); + status_t DisconnectNodes(); + +private: + int fCurrentInterface; + int fCurrentChannel; + VideoView * fVideoView; + VideoNode * fVideoNode; + BParameterWeb * fWeb; + BDiscreteParameter * fChannelParam; + bool fConnected; + media_input fInput; + media_output fOutput; +}; + + +#endif Added: haiku/trunk/src/apps/tv/ConvertBitmap.cpp =================================================================== --- haiku/trunk/src/apps/tv/ConvertBitmap.cpp 2007-04-15 18:43:38 UTC (rev 20708) +++ haiku/trunk/src/apps/tv/ConvertBitmap.cpp 2007-04-15 18:58:05 UTC (rev 20709) @@ -0,0 +1,56 @@ +/* + * Copyright (c) 2004-2007 Marcus Overhagen + * + * Permission is hereby granted, free of charge, to any person + * obtaining a copy of this software and associated documentation + * files (the "Software"), to deal in the Software without restriction, + * including without limitation the rights to use, copy, modify, + * merge, publish, distribute, sublicense, and/or sell copies of + * the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be + * included in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES + * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT + * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, + * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + */ + +#include +#include +#include +#include + +#include "ConvertBitmap.h" + +status_t ConvertBitmap_YCbCr422_to_RGB32(BBitmap *dst, const BBitmap *src); + +status_t +ConvertBitmap(BBitmap *dst, const BBitmap *src) +{ + if (dst->Bounds() != src->Bounds()) + return B_BAD_VALUE; + + if (dst->ColorSpace() == src->ColorSpace() && dst->BytesPerRow() == src->BytesPerRow() ) { + memcpy(dst->Bits(), src->Bits(), src->BitsLength()); + return B_OK; + } + + if (src->ColorSpace() == B_YCbCr422 && dst->ColorSpace() == B_RGB32) + return ConvertBitmap_YCbCr422_to_RGB32(dst, src); + + return B_ERROR; +} + + +status_t +ConvertBitmap_YCbCr422_to_RGB32(BBitmap *dst, const BBitmap *src) +{ + return B_ERROR; +} Added: haiku/trunk/src/apps/tv/ConvertBitmap.h =================================================================== --- haiku/trunk/src/apps/tv/ConvertBitmap.h 2007-04-15 18:43:38 UTC (rev 20708) +++ haiku/trunk/src/apps/tv/ConvertBitmap.h 2007-04-15 18:58:05 UTC (rev 20709) @@ -0,0 +1,30 @@ +/* + * Copyright (c) 2004-2007 Marcus Overhagen + * + * Permission is hereby granted, free of charge, to any person + * obtaining a copy of this software and associated documentation + * files (the "Software"), to deal in the Software without restriction, + * including without limitation the rights to use, copy, modify, + * merge, publish, distribute, sublicense, and/or sell copies of + * the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be + * included in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES + * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT + * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, + * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + */ + +#ifndef __CONVERT_BITMAP_H +#define __CONVERT_BITMAP_H + +status_t ConvertBitmap(BBitmap *dst, const BBitmap *src); + +#endif Added: haiku/trunk/src/apps/tv/DeviceRoster.cpp =================================================================== --- haiku/trunk/src/apps/tv/DeviceRoster.cpp 2007-04-15 18:43:38 UTC (rev 20708) +++ haiku/trunk/src/apps/tv/DeviceRoster.cpp 2007-04-15 18:58:05 UTC (rev 20709) @@ -0,0 +1,144 @@ +/* + * Copyright (c) 2004-2007 Marcus Overhagen + * + * Permission is hereby granted, free of charge, to any person + * obtaining a copy of this software and associated documentation + * files (the "Software"), to deal in the Software without restriction, + * including without limitation the rights to use, copy, modify, + * merge, publish, distribute, sublicense, and/or sell copies of + * the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be + * included in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES + * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT + * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, + * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + */ + +#include "DeviceRoster.h" + +#include +#include +#include + + +DeviceRoster *gDeviceRoster; + + + +DeviceRoster::DeviceRoster() +{ + live_node_info info[MAX_DEVICE_COUNT]; + int32 info_count = MAX_DEVICE_COUNT; + status_t err; + err = MediaRoster()->GetLiveNodes(info, &info_count, NULL, NULL, "DVB*", B_BUFFER_PRODUCER | B_PHYSICAL_INPUT); + if (err != B_OK || info_count < 1) { + printf("Can't find live DVB node. Found %ld nodes, error %08lx (%s)\n", info_count, err, strerror(err)); + fDeviceCount = 0; + } else { + fDeviceCount = info_count; + for (int i = 0; i < fDeviceCount; i++) { + fDeviceInfo[i].node = info[i].node; + strcpy(fDeviceInfo[i].name, info[i].name); + } + } +} + + +DeviceRoster::~DeviceRoster() +{ +} + + +int +DeviceRoster::DeviceCount() +{ + return fDeviceCount; +} + + +const char * +DeviceRoster::DeviceName(int i) +{ + ASSERT(i >= 0 && i < fDeviceCount); + return fDeviceInfo[i].name; +} + + +media_node +DeviceRoster::DeviceNode(int i) +{ + ASSERT(i >= 0 && i < fDeviceCount); + return fDeviceInfo[i].node; +} + + +bool +DeviceRoster::IsRawAudioOutputFree(int i) +{ + ASSERT(i >= 0 && i < fDeviceCount); + + media_output output; + int32 count; + status_t err; + + err = MediaRoster()->GetFreeOutputsFor(fDeviceInfo[i].node, &output, 1, &count, B_MEDIA_RAW_AUDIO); + return (err == B_OK) && (count == 1); +} + + +bool +DeviceRoster::IsEncAudioOutputFree(int i) +{ + ASSERT(i >= 0 && i < fDeviceCount); + + media_output output; + int32 count; + status_t err; + + err = MediaRoster()->GetFreeOutputsFor(fDeviceInfo[i].node, &output, 1, &count, B_MEDIA_ENCODED_AUDIO); + return (err == B_OK) && (count == 1); +} + + +bool +DeviceRoster::IsRawVideoOutputFree(int i) +{ + ASSERT(i >= 0 && i < fDeviceCount); + + media_output output; + int32 count; + status_t err; + + err = MediaRoster()->GetFreeOutputsFor(fDeviceInfo[i].node, &output, 1, &count, B_MEDIA_RAW_VIDEO); + return (err == B_OK) && (count == 1); +} + + +bool +DeviceRoster::IsEncVideoOutputFree(int i) +{ + ASSERT(i >= 0 && i < fDeviceCount); + + media_output output; + int32 count; + status_t err; + + err = MediaRoster()->GetFreeOutputsFor(fDeviceInfo[i].node, &output, 1, &count, B_MEDIA_ENCODED_VIDEO); + return (err == B_OK) && (count == 1); +} + + +BMediaRoster * +DeviceRoster::MediaRoster() +{ + return BMediaRoster::Roster(); +} + Added: haiku/trunk/src/apps/tv/DeviceRoster.h =================================================================== --- haiku/trunk/src/apps/tv/DeviceRoster.h 2007-04-15 18:43:38 UTC (rev 20708) +++ haiku/trunk/src/apps/tv/DeviceRoster.h 2007-04-15 18:58:05 UTC (rev 20709) @@ -0,0 +1,66 @@ +/* + * Copyright (c) 2004-2007 Marcus Overhagen + * + * Permission is hereby granted, free of charge, to any person + * obtaining a copy of this software and associated documentation + * files (the "Software"), to deal in the Software without restriction, + * including without limitation the rights to use, copy, modify, + * merge, publish, distribute, sublicense, and/or sell copies of + * the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be + * included in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES + * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT + * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, + * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + */ + +#ifndef __DEVICE_ROSTER_H +#define __DEVICE_ROSTER_H + +#include + +class DeviceRoster +{ +public: + DeviceRoster(); + ~DeviceRoster(); + + int DeviceCount(); + + const char * DeviceName(int i); + media_node DeviceNode(int i); + + bool IsRawAudioOutputFree(int i); + bool IsEncAudioOutputFree(int i); + bool IsRawVideoOutputFree(int i); + bool IsEncVideoOutputFree(int i); + +public: + BMediaRoster* MediaRoster(); + +private: + enum { MAX_DEVICE_COUNT = 8 }; + + class device_info + { + public: + media_node node; + char name[B_MEDIA_NAME_LENGTH]; + }; + +private: + device_info fDeviceInfo[MAX_DEVICE_COUNT]; + int fDeviceCount; +}; + +extern DeviceRoster *gDeviceRoster; + +#endif Added: haiku/trunk/src/apps/tv/MainApp.cpp =================================================================== --- haiku/trunk/src/apps/tv/MainApp.cpp 2007-04-15 18:43:38 UTC (rev 20708) +++ haiku/trunk/src/apps/tv/MainApp.cpp 2007-04-15 18:58:05 UTC (rev 20709) @@ -0,0 +1,86 @@ +/* + * Copyright (c) 2004-2007 Marcus Overhagen + * + * Permission is hereby granted, free of charge, to any person + * obtaining a copy of this software and associated documentation + * files (the "Software"), to deal in the Software without restriction, + * including without limitation the rights to use, copy, modify, + * merge, publish, distribute, sublicense, and/or sell copies of + * the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be + * included in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES + * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT + * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, + * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + */ + +#include +#include +#include +#include +#include +#include + +#include "MainApp.h" +#include "config.h" +#include "DeviceRoster.h" + +MainApp *gMainApp; + +bool gOverlayDisabled = false; + +MainApp::MainApp() + : BApplication(APP_SIG) +{ + InitPrefs(); + + gDeviceRoster = new DeviceRoster; + + fMainWindow = NewWindow(); +} + + +MainApp::~MainApp() +{ + delete gDeviceRoster; +} + + +status_t +MainApp::InitPrefs() +{ + return B_OK; +} + + +BWindow * +MainApp::NewWindow() +{ + static int i = 0; + BRect rect(200, 200, 750, 300); + rect.OffsetBy(i * 25, i * 25); + i = (i + 1) % 15; + BWindow *win = new MainWin(rect); + win->Show(); + return win; +} + + +int +main(int argc, const char *argv[]) +{ + if (argc > 1) + gOverlayDisabled = true; + gMainApp = new MainApp; + gMainApp->Run(); + delete gMainApp; + return 0; +} Added: haiku/trunk/src/apps/tv/MainApp.h =================================================================== --- haiku/trunk/src/apps/tv/MainApp.h 2007-04-15 18:43:38 UTC (rev 20708) +++ haiku/trunk/src/apps/tv/MainApp.h 2007-04-15 18:58:05 UTC (rev 20709) @@ -0,0 +1,45 @@ +/* + * Copyright (c) 2004-2007 Marcus Overhagen [... truncated: 2441 lines follow ...] From marcusoverhagen at mail.berlios.de Sun Apr 15 21:00:34 2007 From: marcusoverhagen at mail.berlios.de (marcusoverhagen at BerliOS) Date: Sun, 15 Apr 2007 21:00:34 +0200 Subject: [Haiku-commits] r20710 - in haiku/trunk/data/settings/media: . dvb dvb/dvb-s channels dvb/dvb-s channels/Deutschland dvb/dvb-t channels dvb/dvb-t channels/Deutschland Message-ID: <200704151900.l3FJ0YQq028994@sheep.berlios.de> Author: marcusoverhagen Date: 2007-04-15 21:00:26 +0200 (Sun, 15 Apr 2007) New Revision: 20710 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20710&view=rev Added: haiku/trunk/data/settings/media/dvb/ haiku/trunk/data/settings/media/dvb/dvb-s channels/ haiku/trunk/data/settings/media/dvb/dvb-s channels/Deutschland/ haiku/trunk/data/settings/media/dvb/dvb-s channels/Deutschland/Astra 19 East + Hotbird 13 East + Pay TV haiku/trunk/data/settings/media/dvb/dvb-s channels/Deutschland/Astra 19 East FTA haiku/trunk/data/settings/media/dvb/dvb-s channels/Deutschland/Astra 19 East, inkl. ORF und Canal Digtaal NL haiku/trunk/data/settings/media/dvb/dvb-s channels/Deutschland/Astra 19+13+5 East +1+30 West + PayTV haiku/trunk/data/settings/media/dvb/dvb-s channels/Deutschland/Astra 19+13+5 East +1West + PayTV haiku/trunk/data/settings/media/dvb/dvb-t channels/ haiku/trunk/data/settings/media/dvb/dvb-t channels/Deutschland/ haiku/trunk/data/settings/media/dvb/dvb-t channels/Deutschland/Berlin-Brandenburg haiku/trunk/data/settings/media/dvb/dvb-t channels/Deutschland/Mitteldeutschland - Leipzig haiku/trunk/data/settings/media/dvb/dvb-t channels/Deutschland/NRW - Koeln, Bonn haiku/trunk/data/settings/media/dvb/dvb-t channels/Deutschland/NRW - Ruhrgebiet, Duesseldorf haiku/trunk/data/settings/media/dvb/dvb-t channels/Deutschland/Norddeutschland - Braunschweig haiku/trunk/data/settings/media/dvb/dvb-t channels/Deutschland/Norddeutschland - Bremen haiku/trunk/data/settings/media/dvb/dvb-t channels/Deutschland/Norddeutschland - Bremen, Bremerhaven, Oldenburg haiku/trunk/data/settings/media/dvb/dvb-t channels/Deutschland/Norddeutschland - Hamburg haiku/trunk/data/settings/media/dvb/dvb-t channels/Deutschland/Norddeutschland - Hannover haiku/trunk/data/settings/media/dvb/dvb-t channels/Deutschland/Norddeutschland - Kiel haiku/trunk/data/settings/media/dvb/dvb-t channels/Deutschland/Rhein-Main-Gebiet - Frankfurt a.M. haiku/trunk/data/settings/media/dvb/dvb-t channels/Deutschland/Rhein-Main-Gebiet - Mainz haiku/trunk/data/settings/media/dvb/dvb-t channels/Deutschland/Sueddeutschland - Muenchen Log: channel settings for DVB Added: haiku/trunk/data/settings/media/dvb/dvb-s channels/Deutschland/Astra 19 East + Hotbird 13 East + Pay TV =================================================================== --- haiku/trunk/data/settings/media/dvb/dvb-s channels/Deutschland/Astra 19 East + Hotbird 13 East + Pay TV 2007-04-15 18:58:05 UTC (rev 20709) +++ haiku/trunk/data/settings/media/dvb/dvb-s channels/Deutschland/Astra 19 East + Hotbird 13 East + Pay TV 2007-04-15 19:00:26 UTC (rev 20710) @@ -0,0 +1,1505 @@ +:->Astra19?East +Das Erste:11837:H:S19.2E:27500:101:102:104:0:28106:1:1101:0 +ZDF:11954:H:S19.2E:27500:110:120:0:0:28006:1:1079:0 +WDR K?ln:11837:H:S19.2E:27500:601:602:604:0:28111:1:1101:0 +Fashion TV:10992:V:S13E:27500:259:515:0:0:3:1:1:0 +SAT.1:12480:V:S19.2E:27500:1791:1792:0:0:46:133:33:0 +EinsMuXx:12109:H:S19.2E:27500:301:302:404:0:28203:1:1073:0 +ProSieben:12480:V:S19.2E:27500:255:256:32:0:898:133:33:0 +RTL2:12188:H:S19.2E:27500:166:128:68:0:12020:1:1089:0 +RTL Television:12188:H:S19.2E:27500:163:104:105:0:12003:1:1089:0 +KABEL1:12480:V:S19.2E:27500:511:512:33:0:899:133:33:0 +VOX:12188:H:S19.2E:27500:167:136:71:0:12060:1:1089:0 +Eurosport:11954:H:S19.2E:27500:410:420:0:0:28009:1:1079:0 +DSF:12480:V:S19.2E:27500:1023:1024:0:0:900:133:33:0 +Bayerisches FS:11837:H:S19.2E:27500:201:202:204:0:28107:1:1101:0 +hessen fernsehen:11837:H:S19.2E:27500:301:302:304:0:28108:1:1101:0 +S?dwest BW:11837:H:S19.2E:27500:801:802:804:0:28113:1:1101:0 +BR-alpha:11837:H:S19.2E:27500:701:702:704:0:28112:1:1101:0 +arte:11837:H:S19.2E:27500:401:402:404:0:28109:1:1101:0 +3sat:11954:H:S19.2E:27500:210:220:0:0:28007:1:1079:0 +Phoenix:11837:H:S19.2E:27500:901:902:904:0:28114:1:1101:0 +TW1:12663:H:S19.2E:22000:1010:1011:1013:0:13101:1:1115:0 +Travel:11778:V:S19.2E:27500:163:92:0:0:28003:1:1068:0 +CANAL CANARIAS:10979:V:S19.2E:22000:164:96:0:0:30661:1:1034:0 +N24:12480:V:S19.2E:27500:2047:2048:36:0:47:133:33:0 +N-TV:12188:H:S19.2E:27500:169:73:80:0:12090:1:1089:0 +Bloomberg TV Germany:12552:V:S19.2E:22000:162:99:0:0:12160:1:1108:0 +CNBC Europe:11597:V:S19.2E:22000:307:308:43:0:10030:1:1026:0 +EuroNews:11954:H:S19.2E:27500:2221:2233:0:0:28015:1:1079:0 +Sky News Intl:11597:V:S19.2E:22000:305+131:306:0:0:28707:1:1026:0 +DW-TV:11597:V:S19.2E:22000:1000:1001:0:0:10020:1:1026:0 +CNN Int.:11778:V:S19.2E:27500:165:100:0:0:28522:1:1068:0 +Al Jazeera:11568:V:S19.2E:22000:55:56:0:0:9021:1:1024:0 +SFi:12399:H:S13E:27500:167:102:58:0:911:318:8500:0 +SKY TG 24:12713:V:S13E:27500:2579+2560:2580:2588:0:4362:64511:10000:0 +24ore.tv:12558:V:S13E:27500:6916:6917:0:0:9372:319:9200:0 +BBC World:12597:V:S13E:27500:163:92:41:0:8204:318:9400:0 +BBC WORLD:12285:V:S19.2E:27500:167:108:0:0:17027:1:1094:0 +BBC Prime:11131:V:S13E:5632:256+128:257:258:0:5001:318:3801:0 +EinsFestival:12109:H:S19.2E:27500:201:202:0:0:28202:1:1073:0 +EinsExtra:12109:H:S19.2E:27500:101:102:0:0:28201:1:1073:0 +EinsFestival:12109:H:S19.2E:27500:201:202:0:0:28202:1:1073:1 +MDR FERNSEHEN:12109:H:S19.2E:27500:401:402:404:0:28204:1:1073:0 +MDR SACHSEN:12109:H:S19.2E:27500:401:402:404:0:28228:1:1073:0 +MDR S-ANHALT:12109:H:S19.2E:27500:401:402:404:0:28229:1:1073:0 +MDR THRINGEN:12109:H:S19.2E:27500:401:402:404:0:28230:1:1073:0 +rbb Berlin:12109:H:S19.2E:27500:601:602:604:0:28206:1:1073:0 +rbb Brandenburg:12109:H:S19.2E:27500:501:502:504:0:28205:1:8191:0 +NDR FS MV:12109:H:S19.2E:27500:2401:2402:2404:0:28224:1:1073:0 +NDR FS HH:12109:H:S19.2E:27500:2401:2402:2404:0:28225:1:1073:0 +NDR FS NDS:12109:H:S19.2E:27500:2401:2402:2404:0:28226:1:1073:0 +NDR FS SH:12109:H:S19.2E:27500:2401:2402:2404:0:28227:1:1073:0 +ARD-MHP-TEST-6:12109:H:S19.2E:27500:101:102:0:0:28222:1:1073:0 +WDR D?sseldorf:12422:H:S19.2E:27500:101:102:104:0:28308:1:1201:0 +WDR Essen:12422:H:S19.2E:27500:101:102:104:0:28309:1:1201:0 +WDR Dortmund:12422:H:S19.2E:27500:101:102:104:0:28307:1:1201:0 +WDR Bielefeld:12422:H:S19.2E:27500:101:102:104:0:28306:1:1201:0 +WDR Siegen:12422:H:S19.2E:27500:101:102:104:0:28311:1:1201:0 +WDR Wuppertal:12422:H:S19.2E:27500:101:102:104:0:28312:1:1201:0 +WDR M?nster:12422:H:S19.2E:27500:101:102:104:0:28310:1:1201:0 +WDR Aachen:12422:H:S19.2E:27500:101:102:104:0:28305:1:1201:0 +S?DWEST RP:12109:H:S19.2E:27500:3101:3102:3104:0:28231:1:1073:0 +SR Fernsehen Suedwest:11837:H:S19.2E:27500:501:502:504:0:28110:1:1101:0 +ZDFdokukanal:11954:H:S19.2E:27500:660:670:130:0:28014:1:1079:0 +ZDFinfokanal:11954:H:S19.2E:27500:610:620:130:0:28011:1:1079:0 +ZDFtheaterkanal:11954:H:S19.2E:27500:1110:1120:130:0:28016:1:1079:0 +KiKa:11954:H:S19.2E:27500:310:320:330:0:28008:1:1079:0 +iFoxKids:12148:H:S19.2E:27500:3839:3840:0:0:765:133:7:0 +Bahn TV:12633:H:S19.2E:22000:201:301:0:0:12600:1:1113:0 +XXP:12633:H:S19.2E:22000:203:303:503:0:12602:1:1113:0 +rhein main tv:12633:H:S19.2E:22000:208:308:508:0:12614:1:1113:0 +BVN:12574:H:S19.2E:22000:515+8190:96:36:0:5025:53:1109:0 +RTL TELE Letzebuerg:12552:V:S19.2E:22000:168:144:74:0:3994:1:1108:0 +Super RTL:12188:H:S19.2E:27500:165:120:65:0:12040:1:1089:0 +RTL Shop:12188:H:S19.2E:27500:168:137:70:0:12080:1:1089:0 +GOD Channel:12148:H:S19.2E:27500:767:768:0:0:774:133:7:0 +RNFplus:12148:H:S19.2E:27500:1104:1105:0:0:768:133:7:0 +TV.BERLIN:12148:H:S19.2E:27500:511:512:0:0:772:133:7:0 +ONTV Regional:12148:H:S19.2E:27500:2303:2304:0:0:514:133:8191:0 +Franken SAT:12148:H:S19.2E:27500:3583:3584:0:0:775:133:7:0 +LokalSAT:12148:H:S19.2E:27500:1279:1280:0:0:767:133:7:0 +rhein main tv:12632:H:S19.2E:22000:208:308:508:0:12614:1:1113:1 +TV TRAVEL SHOP:12148:H:S19.2E:27500:1023:1024:37:0:769:133:7:0 +Sonnenklar TV:12480:V:S19.2E:27500:2303:2304:0:0:32:133:33:0 +TELE 5:12480:V:S19.2E:27500:1535:1536:38:0:51:133:33:0 +NEUN LIVE Television:12480:V:S19.2E:27500:767:768:35:0:897:133:33:0 +HSE24:12480:V:S19.2E:27500:1279:1280:37:0:40:133:33:0 +AstroTV:12480:V:S19.2E:27500:2559:2560:0:0:661:133:33:0 +Bibel TV:10832:H:S19.2E:22000:32:33:0:0:61900:1:1057:0 +TV TRWAM:10832:H:S19.2E:22000:70:71:54:0:61911:1:1057:0 +TV SHOP:10832:H:S19.2E:22000:37:38:0:0:61992:1:1057:0 +24.CZ:10832:H:S19.2E:22000:41:40:0:0:61993:1:1057:0 +ESA alt:10832:H:S19.2E:22000:55:56:0:0:61950:1:1057:0 +ESA:12552:V:S19.2E:22000:305:306:0:0:3995:1:1108:0 +QVC Deutschland:12552:V:S19.2E:22000:165:166:167:0:12100:1:1108:0 +RTM MAROC:11597:V:S19.2E:22000:63:62:0:0:10002:1:1026:0 +2M Maroc:11568:V:S19.2E:22000:139:140:0:0:9030:1:1024:0 +ESC1 - EGYPT:11568:V:S19.2E:22000:163:104:0:0:9014:1:1024:0 +RAI 1:11568:V:S19.2E:22000:289:290:0:0:9015:1:1024:0 +RTPI:11568:V:S19.2E:22000:161:301:302:0:9017:1:1024:0 +CANAL ALGERIE:11568:V:S19.2E:22000:168:138:0:0:9011:1:1024:0 +TV7:11568:V:S19.2E:22000:166:128:0:0:9018:1:1024:0 +Club Teleachat:12610:V:S19.2E:22000:53:54:0:0:12270:1:1112:0 +Screenpeaks promo:12460:H:S19.2E:27500:1535:1536:0:0:63:133:5:0 +wellenlaenge.tv:12460:H:S19.2E:27500:767:768:0:0:61:133:5:0 +Avinos-Wein-Shop:12460:H:S19.2E:27500:511:512:0:0:60:133:5:0 +ACTIVI:12460:H:S19.2E:27500:1279:1280:0:0:62:133:5:0 +Amio.tv:12460:H:S19.2E:27500:1535:1536:0:0:63:133:5:1 +tv.gusto:12460:H:S19.2E:27500:3071:3072:0:0:659:133:5:0 +1-2-3.tv:12460:H:S19.2E:27500:2815:2816:32:0:662:133:5:0 +K-TV:12633:H:S19.2E:22000:202:302:0:0:12601:1:1113:0 +LifeStyle-TV:12633:H:S19.2E:22000:204:304:0:0:12603:1:1113:0 +K1010:12633:H:S19.2E:22000:1041:1042:0:0:12616:1:1113:0 +Spielekanal TV:12633:H:S19.2E:22000:1053:1054:1055:0:12618:1:1113:0 +Quiz-des-Tages:12633:H:S19.2E:22000:1044:1045:0:0:12619:1:1113:0 +Traumpartner TV:12188:H:S19.2E:27500:170:144:81:0:12095:1:1089:0 +:->Music +MTV Central:11739:V:S19.2E:27500:3031:3032:0:0:28653:1:1066:0 +MTV2 Pop Channel:12226:H:S19.2E:27500:513+8190:661:577:0:28640:1:1091:0 +GoTV:12663:H:S19.2E:22000:1020:1021:0:0:13102:1:1115:0 +VIVA:12670:V:S19.2E:22000:309:310:311:0:12732:1:1116:0 +VIVA PLUS:12552:V:S19.2E:22000:171:172:173:0:12120:1:1108:0 +VIVA polska:11604:H:S13E:27500:190:191:0:0:611:318:15500:0 +102.5 HIT Ch:11623:V:S13E:27500:224:244:0:0:10704:318:15600:0 +DANCE TV:12303:V:S13E:27500:1237:1238:0:0:3221:318:8000:0 +Music Box Italia:12207:H:S13E:27500:4097+4102:4098:0:0:16:1:1:0 +4fun.TV:10719:V:S13E:27500:163:92:0:0:4404:318:11000:0 +Ocko TV:10832:H:S19.2E:22000:161:162:163:0:61990:1:1057:0 +'ZIK / XXL:12285:V:S19.2E:27500:164:96:0:0:17024:1:1094:0 +T.TV:10832:H:S19.2E:22000:61:62:0:0:61920:1:1057:0 +Playlist Italia:12673:V:S13E:27500:340:341:343:0:4210:318:9800:0 +S24 TV:12303:V:S13E:27500:1234:1235:0:0:3231:318:8000:0 +ITALIAN MUSIC:12303:V:S13E:27500:1232:1233:0:0:3222:318:8000:0 +COUNTDOWN:12303:V:S13E:27500:235:236:0:0:3212:318:8000:0 +MAGIC:12303:V:S13E:27500:245:246:0:0:3211:318:8000:0 +123LIVESAT/69XTV:11623:V:S13E:27500:230:250:297:0:10710:318:15600:0 +GAY.TV:12111:V:S13E:27500:351:352:360:0:721:318:7000:0 +DAN MUSIC:12692:H:S13E:27500:175:140:0:0:525:318:9900:0 +PMC:11747:H:S13E:27500:67:0:0:0:9508:318:5103:0 +NOJOOM TV:11747:H:S13E:27500:76:109:0:0:9511:318:5103:0 +Radio Italia tv:11387:H:S13E:27500:526+134:790:0:0:15:272:900:0 +TMF:12574:H:S19.2E:22000:516+8190:88:34:0:5015:53:1109:0 +TRACE TV:12012:V:S19.2E:27500:166:104:0:0:8807:1:1080:0 +VH1 Classic:11739:V:S19.2E:27500:3071:3072:0:0:28657:1:1066:0 +VH1 European:11739:V:S19.2E:27500:3061:3062:0:0:28656:1:1066:0 +MTV Base:11739:V:S19.2E:27500:3051:3052:0:0:28655:1:1066:0 +MTV 2 Europe:11739:V:S19.2E:27500:3091:3092:0:0:28659:1:1066:0 +MTV F:11739:V:S19.2E:27500:3021:3022:3024:0:28652:1:1066:0 +MTV Hits:11739:V:S19.2E:27500:3041:3042:0:0:28654:1:1066:0 +MTV ESP:11739:V:S19.2E:27500:3011:3012:3014:0:28651:1:1066:0 +VH1:11739:V:S19.2E:27500:3061:3062:0:0:28656:1:1066:1 +MTV France:11242:V:S13E:27500:168:112:56:0:9:318:200:0 +MATCH TV:11895:V:S19.2E:27500:165:100:0:0:8355:1:1074:0 +MCM:11895:V:S19.2E:27500:161:84:0:0:8352:1:1074:0 +MCM POP:11895:V:S19.2E:27500:164:96:0:0:8354:1:1074:0 +MCM TOP:11895:V:S19.2E:27500:162:88:0:0:8365:1:1074:0 +MCM Europe:12245:H:S13E:27500:122:132:0:0:102:318:7700:0 +RFM-TV:11681:H:S13E:27500:168:112:0:0:209:318:15900:0 +T?l? M?lody:11034:V:S13E:27500:520:530:0:0:1705:176:12600:0 +Fun TV:10796:V:S13E:27500:420:430:0:0:1404:176:11400:0 +M6 Music:10796:V:S13E:27500:1020:1030:0:0:1410:176:11400:0 +:->HotBird 13?East +NBC Giga:11054:H:S13E:27500:550:551:553:0:8008:318:12700:0 +TERRA NOVA:12692:H:S13E:27500:161:84:35:0:502:318:9900:0 +Fashion TV:10992:V:S13E:27500:259:515:0:0:3:1:1:1 +Tv Moda:12673:V:S13E:27500:220:221:0:0:4203:318:9800:0 +SKY Meteo24:12713:V:S13E:27500:2561+2560:2562:0:0:4321:64511:10000:0 +Meteo Express:10909:V:S13E:27500:5820:5830:0:0:5800:176:12000:0 +GAME NETWORK:12673:V:S13E:27500:291:292:0:0:4213:318:9800:0 +DCTV-german:12265:V:S13E:27500:1160:1123:0:0:14:318:101:0 +EbS:12476:H:S13E:27500:101:201:0:0:10601:318:8900:0 +tv.nrw:11604:H:S13E:27500:111:112:114:0:603:318:15500:0 +ARD "Das Erste":11604:H:S13E:27500:172:173:174:0:606:318:15500:0 +ZDF:11054:H:S13E:27500:570:571:572:0:8011:318:12700:0 +RTL Television:11054:H:S13E:27500:160:80:32:0:8001:318:12700:0 +VOX CH:11054:H:S13E:27500:500:501:502:0:8002:318:12700:0 +Super RTL A:11604:H:S13E:27500:180:181:182:0:610:318:15500:0 +Super RTL CH:11604:H:S13E:27500:180:181:182:0:610:318:15500:1 +RTL 2 CH:11604:H:S13E:27500:175:176:177:0:609:318:15500:0 +BVN-TV 1-7|00:12303:V:S13E:27500:209:210:0:0:3209:318:8000:0 +EURONEWS GER:12597:V:S13E:27500:2221:2233:0:0:8211:318:9400:0 +DW-TV:11604:H:S13E:27500:1000:1001:0:0:607:318:15500:0 +BBC World:12597:V:S13E:27500:163:92:41:0:8204:318:9400:1 +Bloomberg English TV:11642:H:S13E:27500:1560:1520:0:0:5:318:15700:0 +Bloomberg German TV:11642:H:S13E:27500:1460:1420:0:0:4:318:15700:0 +Bloomberg European TV:11642:H:S13E:27500:1360:1320:0:0:3:318:15700:0 +PROMO:12188:V:S13E:27500:517+2305:655:0:0:1001:56:7400:0 +TV PIREAS:12188:V:S13E:27500:515+130:653:579:0:1010:56:7400:0 +RTS SAT:12188:V:S13E:27500:519+131:657:0:0:1022:56:7400:0 +TV MAGIC:12188:V:S13E:27500:512+132:650:0:0:1024:56:7400:0 +EXTRA 3 CHANNEL:12188:V:S13E:27500:3713+137:768:0:0:1101:56:7400:0 +ERT SAT:12188:V:S13E:27500:514+2306:652:578:0:1102:56:7400:0 +HOLIDAYS IN GR CHANNEL:12188:V:S13E:27500:516+135:654:0:0:1106:56:7400:0 +TELEASTY:12188:V:S13E:27500:513+133:651:0:0:1108:56:7400:0 +MKTV:12188:V:S13E:27500:518+136:656:0:0:1208:56:7400:0 +902:12284:H:S13E:27500:513+131:660:0:0:3904:318:7900:0 +Kurdsat:10853:H:S13E:27500:308+2501:256:0:0:8602:318:11700:0 +Kurdistan TV:11137:H:S13E:27500:3526:3646:0:0:7326:318:13100:0 +TRT INT:10957:H:S13E:4340:308+8190:256:273:0:1:65535:1:0 +Nile News:12539:H:S13E:27500:1185+1184:1186:0:0:8983:318:9100:0 +Nile TV International:12539:H:S13E:27500:1181+1180:1182:0:0:8982:318:9100:0 +Sports test:12539:H:S13E:27500:1192+1193:1194:0:0:8991:318:9100:0 +ANN:12597:V:S13E:27500:161:84:0:0:8202:318:9400:0 +GCNE:12597:V:S13E:27500:167:108:0:0:8208:318:9400:0 +EuroNews:12597:V:S13E:27500:2221:2231:768:0:8211:318:9400:1 +Al Arabiya:12597:V:S13E:27500:160+8190:80:8190:0:8201:318:9400:0 +BBC World:12597:V:S13E:27500:163:92:41:0:8204:318:9400:2 +Sharjah:12654:H:S13E:27500:1160:1120:0:0:1:702:9700:0 +Qatar:12654:H:S13E:27500:1260:1220:0:0:2:702:9700:0 +Saudi 1:12654:H:S13E:27500:1360:1320:0:0:3:702:9700:0 +Kuwait:12654:H:S13E:27500:1460:1420:0:0:4:702:9700:0 +Libya:12654:H:S13E:27500:1560:1520:0:0:5:702:9700:0 +Sudan:12654:H:S13E:27500:1660:1620:0:0:6:702:9700:0 +Oman:12654:H:S13E:27500:1760:1720:0:0:7:702:9700:0 +ESC:12654:H:S13E:27500:1860:1820:0:0:8:702:9700:0 +Iraq:12654:H:S13E:27500:1960:1920:0:0:9:702:9700:0 +Al manar:12654:H:S13E:27500:1060:1020:0:0:10:702:9700:0 +DUBAI TV.:11747:H:S13E:27500:4130:4131:0:0:9501:318:5103:0 +EDTV SPORTS:11747:H:S13E:27500:4386:4388:0:0:9502:318:5103:0 +EDTV_BUSINESS:11747:H:S13E:27500:4642:4643:0:0:9503:318:5103:0 +SHARQIYA:11747:H:S13E:27500:77:113:0:0:9510:318:5103:0 +INFINITY:11747:H:S13E:27500:121:122:0:0:9512:318:5103:0 +AL JAZEERA:12111:V:S13E:27500:270:271:0:0:708:318:7000:0 +AL-ALAM:12437:H:S13E:27500:165:90:0:0:7915:602:8700:0 +IRIB2 ENG:12437:H:S13E:27500:161:83:0:0:7904:318:8700:0 +IRIB2 PER:12437:H:S13E:27500:161:82:0:0:7903:318:8700:0 +IRIB1 ENG:12437:H:S13E:27500:160:81:0:0:7902:318:8700:0 +IRIB1 PER:12437:H:S13E:27500:160:80:0:0:7901:318:8700:0 +IRINN:12437:H:S13E:27500:164:88:0:0:7905:318:8700:0 +SAHAR1:12437:H:S13E:27500:162:84:0:0:7910:318:8700:0 +SAHAR2:12437:H:S13E:27500:163:86:0:0:7911:318:8700:0 +FEED:12437:H:S13E:27500:308+8190:256:8190:0:7943:318:8700:0 +Jordan TV:12380:V:S13E:27500:3029:3039:0:0:3009:318:8400:0 +Abu Dhabi TV:12380:V:S13E:27500:3024:3034:0:0:3004:318:8400:0 +Syria Satellite Channel:12380:V:S13E:27500:3022:3032:0:0:3002:318:8400:0 +SAT 7:12380:V:S13E:27500:3023+128:3033:0:0:3003:318:8400:0 +CANAL ALGERIE:11585:V:S13E:27500:1381:1382:0:0:13508:318:15400:0 +IQRAA:12015:H:S13E:27500:520+136:730:0:0:474:318:6500:0 +MA3:12015:H:S13E:27500:522+138:750:0:0:478:318:6500:0 +2M MAROC:12476:H:S13E:27500:601:602:0:0:10607:318:8900:0 +SYRIAN TV:12379:V:S13E:27500:3022:3032:0:0:3002:318:8400:1 +DunaTV:12149:V:S13E:27500:96:97:98:0:7201:318:7200:0 +TV7 Tunis:12149:V:S13E:27500:112:113:114:0:7202:318:7200:0 +Khabar TV:12149:V:S13E:27500:160:161:0:0:7220:318:7200:0 +TizianaSat:12149:V:S13E:27500:208:209:0:0:7223:318:7200:0 +LIDER TV AZE:12149:V:S13E:27500:192+191:193:0:0:7222:318:7200:0 +Canal Algerie:12149:V:S13E:27500:224:225:0:0:7224:318:7200:0 +A3:12149:V:S13E:27500:240:241:0:0:7225:318:7200:0 +Bulgaria TV:12539:H:S13E:27500:4612:4613:0:0:8827:318:9100:0 +FEED:12437:H:S13E:27500:308+8190:256:8190:0:7943:602:8700:0 +Miracle TV:11642:H:S13E:27500:1860:1820:0:0:8:318:8191:0 +Channel Nine:11642:H:S13E:27500:1960:1920:0:0:9:318:8191:0 +Arirang TV:11178:H:S13E:27500:215:216:0:0:4909:318:13300:0 +TCT WORLD:11178:H:S13E:27500:205:206:0:0:4902:318:13300:0 +TCT:12207:H:S13E:27500:3585+3590:3586:0:0:114:1:1:0 +Promo:12169:H:S13E:27500:521+8190:740:0:0:361:318:7300:0 +????:12169:H:S13E:27500:517+8190:700:581:0:384:318:7300:0 +God TV:11034:V:S13E:27500:220:230:0:0:1702:176:12600:0 +OASI.TV:12303:V:S13E:27500:248:247:0:0:8320:318:8000:0 +TV Centrum:11515:H:S13E:27500:169:116:0:0:5110:318:1500:0 +Bloomberg/S?damerika:11223:H:S13E:27500:4144:4145:0:0:13303:318:100:0 +Berb?re T?l?vision:11034:V:S13E:27500:1120:1130:0:0:1711:176:12600:0 +TEST 1:12303:V:S13E:27500:205:206:0:0:3207:318:8000:0 +AL HAYAT:11200:V:S13E:27500:413:414:0:0:4733:318:13400:0 +Ch 3 Arabic IBA TV:12207:H:S13E:27500:1057:1058:0:0:49:1:1:0 +OPENET.TV:12558:V:S13E:27500:6660:6661:0:0:9302:319:9200:0 +ASB:12380:V:S13E:27500:3240:3540:0:0:3090:318:8400:0 +Tamil 02HI:10723:H:S13E:29900:1021:1221:0:0:4621:318:11100:0 +OU ch 8:10723:H:S13E:29900:1008:1308:0:0:4620:318:11100:0 +EWTN:10723:H:S13E:29900:1001:1201:0:0:4601:318:11100:0 +E-TV Tech C.:12673:V:S13E:27500:360:361:0:0:4214:318:9800:0 +Emi.Li TV:12673:V:S13E:27500:310:311:0:0:4208:318:9800:0 +Telemarket:12673:V:S13E:27500:350:351:0:0:4211:318:9800:0 +Ceramicanda:12111:V:S13E:27500:260:261:0:0:707:318:7000:0 +HB CHANNEL:12111:V:S13E:27500:200:201:0:0:701:318:7000:0 +NTD TV:11585:V:S13E:27500:1331:1332:0:0:13503:318:15400:0 +MAHARISHI:11585:V:S13E:27500:1341:1342:0:0:13504:318:15400:0 +BET NAHRAIN:11585:V:S13E:27500:1351:1352:0:0:13505:318:15400:0 +ICC:11585:V:S13E:27500:1471:1472:0:0:13517:318:15400:0 +ROJ TV:11585:V:S13E:27500:1321:1322:0:0:13502:318:15400:0 +EWTN:11585:V:S13E:27500:1441:1442:0:0:13514:318:15400:0 +PODROZE TV:11585:V:S13E:27500:1461:1462:0:0:13516:318:15400:0 +DAYSTAR:11585:V:S13E:27500:1311:1312:0:0:13501:318:15400:0 +TAPESH:11585:V:S13E:27500:1401:1402:0:0:13510:318:15400:0 +JAAM E JAM:11585:V:S13E:27500:1411:1412:0:0:13511:318:15400:0 +IPN:11585:V:S13E:27500:1421:1422:0:0:13512:318:15400:0 +IRAN:11585:V:S13E:27500:1431:1432:0:0:13513:318:15400:0 +ITC:11585:V:S13E:27500:1451:1452:0:0:13515:318:15400:0 +PEN TV:11585:V:S13E:27500:1361:1362:0:0:13506:318:15400:0 +OMID E IRAN:11585:V:S13E:27500:1391:1392:0:0:13509:318:15400:0 +Majadahonda TV:11585:V:S13E:27500:1381:1382:0:0:13508:318:15400:1 +NAPOLI SERVICE:12303:V:S13E:27500:500:515:0:0:3216:318:8000:0 +C5 DTT:11387:H:S13E:27500:513+129:660:577:0:11:272:900:0 +I1 DTT:11387:H:S13E:27500:512+128:650:576:0:12:272:900:0 +LCI Dfree:11387:H:S13E:27500:514+130:670:0:0:13:272:900:0 +R4 DTT:11387:H:S13E:27500:531+133:840:595:0:20:272:900:0 +Prima:11387:H:S13E:27500:516+132:690:0:0:19:272:900:0 +Hellas TV:11179:H:S13E:27500:215:216:0:0:4909:318:13300:1 +NTD TV:11585:V:S13E:27500:1331:1332:0:0:13503:318:15400:1 +MI-TV:10853:H:S13E:27500:2950:2951:0:0:8605:318:11700:0 +HB CH.2:11179:H:S13E:27500:200:201:0:0:4901:318:13300:0 +Test:11096:H:S13E:27500:38+8190:41:0:0:3701:318:12900:0 +Islah-TV:12245:H:S13E:27500:129:139:0:0:109:318:7700:0 +TV_SRI:11221:H:S13E:27500:4240:4241:0:0:13301:318:100:0 +LoveWorld:11221:H:S13E:27500:4208:4209:0:0:13302:318:100:0 +PROG_3:11221:H:S13E:27500:4224:4225:0:0:13303:318:100:1 +PROG_4:11221:H:S13E:27500:4176:4177:0:0:13304:318:100:0 +PROG_5:11221:H:S13E:27500:4192:4193:0:0:13305:318:100:0 +WorldnetEurope:12226:V:S13E:27500:4260:4220:0:0:1:1:101:0 +Imagine Sat:10992:V:S13E:27500:257:513:0:0:1:1:1:0 +Red Light Ultra:10992:V:S13E:27500:260:516:0:0:4:1:1:0 +MTC:10992:V:S13E:27500:261:517:0:0:5:1:1:0 +Occasional:10992:V:S13E:27500:280:536:0:0:18:1:1:0 +RR FEED:10992:V:S13E:27500:1282:1289:1288:0:81:1:1:0 +Hope Channel:12577:H:S13E:27500:1207:1317:0:0:8107:318:9300:0 +TELESUD:12577:H:S13E:27500:1204:1304:0:0:8104:318:9300:0 +RTPi:10723:H:S13E:29900:1003:1203:1103:0:4603:318:11100:0 +DIYAR-ARABESQUE:10723:H:S13E:29900:1010:1210:0:0:4623:318:11100:0 +:->Italia 13?East +RAI1:11766:V:S13E:27500:512:650:576:0:3401:318:5200:0 +RAI2:11766:V:S13E:27500:513:651:577:0:3402:318:5200:0 +RAI3:11766:V:S13E:27500:514:652:578:0:3403:318:5200:0 +Retequattro:11919:V:S13E:27500:514+130:670:578:0:3:272:6000:0 +Canale 5:11919:V:S13E:27500:513+129:660:577:0:2:272:6000:0 +Italia 1:11919:V:S13E:27500:512+128:650:576:0:1:272:6000:0 +Test - Mediaset:11919:V:S13E:27500:515+131:680:0:0:4:272:6000:0 +RaiNettunoSat1:11804:V:S13E:27500:519:657:0:0:3308:318:5400:0 +RaiNettunoSat2:11804:V:S13E:27500:513:651:0:0:3306:318:5400:0 +Telepace:11804:V:S13E:27500:515:653:0:0:3304:318:5400:0 +Camera Deputati:11804:V:S13E:27500:517:655:0:0:3302:318:5400:0 +SAT2000:11804:V:S13E:27500:518:656:582:0:3309:318:5400:0 +RaiNotizie24:11804:V:S13E:27500:516:654:0:0:3301:318:5400:0 +RaiUtile:11804:V:S13E:27500:521:659:0:0:3303:318:5400:0 +RaiSportSat:11804:V:S13E:27500:512:650:0:0:3305:318:5400:0 +RaiDoc:11804:V:S13E:27500:522:663:0:0:3310:318:5400:0 +Rai Edu1:11804:V:S13E:27500:514:652:0:0:3307:318:5400:0 +RaiEdu2:11766:V:S13E:27500:518:656:0:0:3406:318:5200:0 +RaiMed:11766:V:S13E:27500:515:653:0:0:3404:318:5200:0 +Senato:11766:V:S13E:27500:8190:92:0:0:3408:318:5200:0 +Euro-News:12596:V:S13E:27500:2221:2234:0:0:8211:318:9400:2 +24ore.tv:12558:V:S13E:27500:6916:6917:6930:0:9372:319:9200:1 +EURO MEDITERRANEO:12303:V:S13E:27500:248:247:0:0:8320:318:8000:1 +NAPOLI INT.:12303:V:S13E:27500:240:241:0:0:3210:318:8000:0 +Napoli Network:12673:V:S13E:27500:220:221:0:0:4203:318:9800:1 +Studio Europa:12673:V:S13E:27500:230:231:0:0:4204:318:9800:0 +TeleMarket:12673:V:S13E:27500:350:351:0:0:4211:318:9800:1 +MEDIOLANUM:12539:H:S13E:27500:1131:1132:0:0:8987:318:9100:0 +HSE:11900:H:S13E:27500:163:92:0:0:11408:64511:5900:0 +Sport Promo:11842:V:S13E:27500:2432:2433:0:0:3565:64511:5600:0 +TizianaSat:12149:V:S13E:27500:208:209:0:0:7223:318:7200:1 +Made In Italy 70:12111:V:S13E:27500:250:251:0:0:706:318:7000:0 +MediterraneoSat:12111:V:S13E:27500:320:321:0:0:718:318:7000:0 +MediterranSat2:11304:H:S13E:27500:512:768:0:0:8408:318:500:0 +DEFENCE TV:11304:H:S13E:27500:400:401:0:0:8407:318:500:0 +Roma Uno:11137:H:S13E:27500:3523:3643:0:0:7323:318:13100:0 +TBNE:11137:H:S13E:27500:3527:3647:0:0:7327:318:13100:0 +RTB:11137:H:S13E:27500:3530:3650:0:0:7330:318:13100:0 +starMarket:11137:H:S13E:27500:3531:3651:0:0:7331:318:13100:0 +Videolook:11137:H:S13E:27500:3525:3645:0:0:7325:318:13100:0 +Telegenova:11137:H:S13E:27500:3529:3649:0:0:7329:318:13100:0 +CartomanziaLOTTO:11623:V:S13E:27500:222:242:0:0:10702:318:15600:0 +Telegenova:11623:V:S13E:27500:228:248:0:0:10708:318:15600:0 +Mediatel:10949:V:S13E:27500:5001:5011:0:0:7401:318:12200:0 +SET:12520:V:S13E:27500:501:502:0:0:8309:318:9000:0 +SARDEGNA UNO:12520:V:S13E:27500:503:504:0:0:8310:318:9000:0 +PUGLIA CHANNEL:12520:V:S13E:27500:515:516:0:0:8318:318:9000:0 +Tele A:10853:H:S13E:27500:34+33:32:0:0:8604:318:11700:0 +CALABRIA CH.:11200:V:S13E:27500:382:383:0:0:4716:318:13400:0 +ContoTV:11200:V:S13E:27500:386:387:448:0:4718:318:13400:0 +ODEON SAT:11200:V:S13E:27500:424+427:425:0:0:4720:318:13400:0 +TAXI channel:11200:V:S13E:27500:416:417:0:0:4721:318:13400:0 +TLC SAT:11200:V:S13E:27500:421:422:0:0:4725:318:13400:0 +STARSAT:11200:V:S13E:27500:397:398:0:0:4726:318:13400:0 +NOELLO SILVER:11200:V:S13E:27500:378:376:0:0:4728:318:13400:0 +NOELLO GOLD:11200:V:S13E:27500:392:393:0:0:4729:318:13400:0 +PLAY TV ITALIA:11200:V:S13E:27500:394:395:0:0:4730:318:13400:0 +PEOPLE TV-RETE7:11200:V:S13E:27500:400:401:0:0:4731:318:13400:0 +ROMA SAT:11200:V:S13E:27500:405:406:0:0:4732:318:13400:0 +Olisat / Telefe:11200:V:S13E:27500:413:414:0:0:4733:318:13400:1 +Spectrum:11179:H:S13E:27500:215:216:0:0:4909:318:13300:2 +Nostradamus:11179:H:S13E:27500:220:221:0:0:4905:318:13300:0 +Napoli Nova:11179:H:S13E:27500:225:226:0:0:4906:318:13300:0 +:->zwez.com +Telegenova:11623:V:S13E:27500:228:248:0:0:10708:318:15600:1 +eurotic TV:10853:H:S13E:27500:2982:2983:0:0:8620:318:11700:0 +Diva Futura:11179:H:S13E:27500:205:206:0:0:4902:318:13300:1 +Multivision 1:11662:V:S13E:27500:120:130:140:0:1301:176:15800:0 +Multivision 2:11662:V:S13E:27500:220:230:240:0:1302:176:15800:0 +Multivision 3:11662:V:S13E:27500:320:330:340:0:1303:176:15800:0 +ZIK / XXL:11681:H:S13E:27500:164:96:0:0:205:318:15900:0 +Playboy Polsat:12322:H:S13E:27500:545:546:0:0:7340:113:8100:0 +TV6:12610:V:S19.2E:22000:100:101:4201:0:12301:1:1112:0 +Telesierra:12092:H:S13E:27500:4160:4161:4162:0:8704:318:6900:0 +Xstream:12476:H:S13E:27500:551:552:0:0:10602:318:8900:0 +Videosexy TV:11623:V:S13E:27500:221:241:0:0:10701:318:15600:0 +ITALIA CLUB:11623:V:S13E:27500:226:246:0:0:10706:318:15600:0 +Sexysat 1:11623:V:S13E:27500:231+8190:251:0:0:10711:318:15600:0 +Sexysat 2:12245:H:S13E:27500:128+8190:138:0:0:108:318:7700:0 +BLU LINE TV:12303:V:S13E:27500:242:243:0:0:3219:318:8000:0 +Erotic TV:12089:H:S13E:27495:1160:1120:0:0:8729:318:6900:0 +Italiasat/Luxuria:12089:H:S13E:27495:4520:4521:0:0:8706:318:6900:0 +DPTV:12089:H:S13E:27495:4690:4691:0:0:8733:318:6900:0 +ATV+:12692:H:S19.2E:22000:506:507:509:0:13012:1:1117:0 +DSF:12480:V:S19.2E:27500:1023:1024:0:0:900:133:33:1 +NEUN LIVE Television:12480:V:S19.2E:27500:767:768:35:0:897:133:33:1 +TV.BERLIN:12148:H:S19.2E:27500:511:512:0:0:772:133:7:1 +tv.nrw:11604:H:S13E:27500:111:112:114:0:603:318:15500:1 +CANAL CLUB:11623:V:S13E:27500:225:245:0:0:10705:318:15600:0 +Mediatel:10949:V:S13E:27500:5001:5011:0:0:7401:318:12200:1 +Polonia 1:11513:H:S13E:27500:162:88:0:0:5103:318:1500:0 +TV POLONIA:11513:H:S13E:27500:160:80:500:0:5101:318:1500:0 +Tele5:11513:H:S13E:27500:161:84:0:0:5102:318:1500:0 +ITV:11513:H:S13E:27500:168:112:502:0:5109:318:1500:0 +RAZE TV:10832:H:S19.2E:22000:308:256:273:0:61963:1:1057:0 +INXTC TV:10853:H:S13E:27500:2984:2985:0:0:8621:318:11700:0 +XPLUS TV:10853:H:S13E:27500:2986:2987:0:0:8622:318:11700:0 +Spice Platinum:10853:H:S13E:27500:2901:2911:0:0:8603:318:11700:0 +XDreamTV:12207:H:S13E:27500:2321:2323:0:0:9:1:1:0 +X4U-TV:12207:H:S13E:27500:1141:1142:0:0:131:1:1:0 +Don't Panic:12089:H:S13E:27500:4690:4691:0:0:8733:318:6900:1 +Sex-View:12089:H:S13E:27500:4630:4631:0:0:8731:318:6900:0 +Sex View Plus:12089:H:S13E:27500:4660:4661:0:0:8755:318:6900:0 +Sex.tv:12089:H:S13E:27495:4600:4601:0:0:8728:318:6900:0 +Sex Gay.tv:12089:H:S13E:27495:4720:4721:0:0:8761:318:6900:0 +Extasi:12089:H:S13E:27495:4432:4433:0:0:8720:318:6900:0 +247Sex:12089:H:S13E:27495:4368:4369:0:0:8711:318:6900:0 +Satisfaction SCT:12089:H:S13E:27495:4192:4193:0:0:8727:318:6900:0 +full-X1:12577:H:S13E:27500:3038:3009:0:0:8111:318:9300:0 +full-X2:12577:H:S13E:27500:6045:6010:0:0:8112:318:9300:0 +full-X2 M:12577:H:S13E:27500:6045:6010:0:0:8115:318:9300:0 +FULLX 2:11507:V:S19.2E:22000:6045:6010:0:0:7001:1:1020:0 +FULLX 2M:11507:V:S19.2E:22000:6045:6010:0:0:7002:1:1020:0 +Free-X TV:10832:H:S19.2E:22000:160+57:80:0:0:61980:1:1057:0 +Red Light Ultra:10992:V:S13E:27500:260:516:0:0:4:4688:9472:0 +Red Light Italia:10992:V:S13E:27500:263:519:0:0:8:4688:9472:0 +Free-X TV:12207:H:S13E:27500:2321+2326:2322:0:0:134:1:1:0 +FREE-XTV 2:12207:H:S13E:27500:4609+4614:4610:0:0:130:1:1:0 +XDream TV:12207:H:S13E:27500:1141+1146:1142:0:0:131:1:1:1 +Red Light TV+:12207:H:S13E:27500:5021+4358:5034:0:0:132:1:1:0 +:->SCPC 13?East +ARTE GERMAN:11060:V:S13E:6510:98:99:105:0:1:177:176:0 +ARTE FRENCH:11060:V:S13E:6510:4450:4451:4457:0:2:177:176:0 +HB Feed:11143:V:S13E:5500:1000:1001:0:0:607:318:13201:0 +WorldNet Europe:12482:V:S13E:8296:4260:4220:0:0:1:1:1:1 +WORLDNET:12482:V:S13E:8296:4560:4520:0:0:4:1:1:1 +APTN JERUSALEM:12581:H:S13E:5631:308+8190:256:0:0:1:0:0:0 +RAI INTERNATIONAL:11464:V:S13E:4400:512+8190:650:0:0:1:65535:1:1 +RAI International:11380:V:S13E:4400:33:36:44:0:2:1:1:0 +DW-TV Amerika:11143:V:S13E:5500:101:102:0:0:5310:318:13201:0 +CCS Test:11205:H:S13E:4000:4130:4131:0:0:1:318:7000:0 +Ch-3 Arabic IBA TV:12220:H:S13E:6160:1057:1058:0:0:2:4369:1:0 +R R FEED 1:12211:H:S13E:6161:4194:4195:0:0:1:177:176:1 +ARIRANG TV:12220:H:S13E:6161:33:34:0:0:1:4369:1:0 +ATN BANGLA:12220:H:S13E:6161:1057:1058:0:0:2:4369:1:1 +BK TV:12220:H:S13E:6161:3105:3106:0:0:4:4369:1:0 +R.R FEED:12220:H:S13E:6158:1057:1058:0:0:2:4369:8191:0 +:->Hotbird Radio 13?East +EDTV RADIO 2:11747:H:S13E:27500:1+4099:4099:0:0:9524:318:5103:0 +ARABIC/5 RADIO:12437:H:S13E:27500:1+165:91:0:0:7932:318:8700:0 +INT1/2:12437:H:S13E:27500:1+162:85:0:0:7930:318:8700:0 +INT4/INT3:12437:H:S13E:27500:1+163:87:0:0:7931:318:8700:0 +IRIB1/QURAN:12437:H:S13E:27500:1+164:89:0:0:7925:318:8700:0 +Radio A1:10723:H:S13E:29900:1+129:1235:0:0:4635:318:11100:0 +RDPi Radio:10723:H:S13E:29900:1+129:1230:0:0:4630:318:11100:0 +NPR:10723:H:S13E:29900:1+1208:1208:0:0:4614:318:11100:0 +:->SRG SSR 13?East +SFi:12399:H:S13E:27500:167:102:58:0:911:318:8500:1 +SF1:12399:H:S13E:27500:160:80:32:0:901:318:8500:0 +SF2:12399:H:S13E:27500:163:92:41:0:907:318:8500:0 +TSR1:12399:H:S13E:27500:161:84:35:0:902:318:8500:0 +TSR2:12399:H:S13E:27500:164:96:44:0:908:318:8500:0 +TSI1:12399:H:S13E:27500:162:88:38:0:903:318:8500:0 +TSI2:12399:H:S13E:27500:166:100:50:0:909:318:8500:0 +ProSieben Schweiz:12051:V:S19.2E:27500:289:290:33:0:20001:1:1082:0 +Kabel 1 Schweiz:12051:V:S19.2E:27500:162:163:165:0:20003:1:1082:0 +SAT.1-CH:12148:H:S19.2E:27500:255:256:34:0:48:133:7:0 +:->French +TV 5 - FBS:11137:H:S13E:27500:3521:3641:3601:0:7321:318:13100:0 +TV 5 Europe:11137:H:S13E:27500:3522:3642:3602:0:7322:318:13100:0 +Euro-News:12595:V:S13E:27500:2221:2231:768:0:8211:318:9400:3 +Liberty TV:12577:H:S13E:27500:1209:1309:0:0:8109:318:9300:0 +TV 8 Mont Blanc:11304:H:S13E:27500:3011:3012:0:0:8401:318:500:0 +TFJ:11034:V:S13E:27500:1020:1030:0:0:1710:176:12600:0 +Beur TV:11034:V:S13E:27500:420:430:0:0:1704:176:12600:0 +Euronews france:11034:V:S13E:27500:920:930:0:0:1709:176:12600:0 +DEMAIN:11034:V:S13E:27500:420:430:0:0:1704:176:12600:1 +DEMAIN:11509:V:S19.2E:22000:704:724:0:0:7004:1:1020:0 +Chamber TV:12551:V:S19.2E:22000:55:56:0:0:12180:1:1108:0 +ARTE:11568:V:S19.2E:22000:167:136:0:0:9019:1:1024:0 +TV 5:11568:V:S19.2E:22000:164:112:0:0:9012:1:1024:0 +TV5 Europe:12610:V:S19.2E:22000:45:46:47:0:12240:1:1112:0 +Liberty TV.com:12610:V:S19.2E:22000:941:943:0:0:12199:1:1112:0 +M6 Boutique:12610:V:S19.2E:22000:53:54:0:0:12270:1:1112:1 +RTBF SAT:12610:V:S19.2E:22000:48:49:0:0:3982:1:1112:0 +FRANCE 5:12207:V:S19.2E:27500:160:80:32:0:8501:1:1090:0 +LCP:12207:V:S19.2E:27500:165:100:0:0:8506:1:1090:0 +MOSA 4:12324:V:S19.2E:27500:166:1961:0:0:8614:1:1096:0 +MOSA 3:12324:V:S19.2E:27500:164:1941:0:0:8605:1:1096:0 +MOSA 2:12324:V:S19.2E:27500:163:1921:0:0:8604:1:1096:0 +MOSAIQUE:12324:V:S19.2E:27500:162:1906:0:0:8603:1:1096:0 +MOSAIQUE:12324:V:S19.2E:27500:168:0:0:0:8608:1:1096:0 +KTO:11895:V:S19.2E:27500:163:92:0:0:8353:1:1074:0 +:->Canal Satellite19?East +TRACE TV:12012:V:S19.2E:27500:166:104:0:0:8807:1:1080:1 +MATCH TV:11895:V:S19.2E:27500:165:100:0:0:8355:1:1074:1 +MCM POP:11895:V:S19.2E:27500:164:96:0:0:8354:1:1074:1 +MCM:11895:V:S19.2E:27500:161:84:0:0:8352:1:1074:1 +MCM TOP:11895:V:S19.2E:27500:162:88:0:0:8365:1:1074:1 +NBA+:11895:V:S19.2E:27500:160:80:0:0:8362:1:1074:0 +GOURMET TV:11895:V:S19.2E:27500:170:120:0:0:8359:1:1074:0 +C CINEMA AUTEUR:11895:V:S19.2E:27500:166:104:50:0:8351:1:1074:0 +C CINEMA INFO:11895:V:S19.2E:27500:167:108:0:0:8356:1:1074:0 +DISNEY CHANNEL+1:12640:V:S19.2E:22000:165:100:47:0:8906:1:1114:0 +PLAYHOUSE DISNEY:12640:V:S19.2E:22000:166:104:0:0:8907:1:1114:0 +TOON DISNEY:12640:V:S19.2E:22000:167:108:0:0:8908:1:1114:0 +CINE POLAR:12640:V:S19.2E:22000:161:84:0:0:8902:1:1114:0 +MOTORS TV:12640:V:S19.2E:22000:169:116:0:0:8910:1:1114:0 +BBC WORLD:12285:V:S19.2E:27500:167:108:0:0:17027:1:1094:1 +CINE FX:12285:V:S19.2E:27500:174:136:41:0:17034:1:1094:0 +CANAL CLUB:12324:V:S19.2E:27500:160:80:0:0:8612:1:1096:0 +PINK TV:12581:V:S19.2E:22000:169:116:0:0:9309:1:1110:0 +:->ABsat2000 13?East +AB SAT PROMO:12692:H:S13E:27500:169:116:41:0:510:318:9900:0 +PASSIONS:12692:H:S13E:27500:160:80:41:0:501:318:9900:0 +CINE BOX:12692:H:S13E:27500:164:96:0:0:505:318:9900:0 +CINE POLAR:12692:H:S13E:27500:165:100:0:0:506:318:9900:0 +CINE FX:12692:H:S13E:27500:166:104:0:0:507:318:9900:0 +CINE COMIC:12692:H:S13E:27500:167:108:0:0:508:318:9900:0 +AB 1:11681:H:S13E:27500:160:80:0:0:201:318:15900:0 +ANIMAUX:11681:H:S13E:27500:162:88:0:0:203:318:15900:0 +CHASSE & PECHE:11681:H:S13E:27500:163:92:0:0:204:318:15900:0 +ZIK / XXL:11681:H:S13E:27500:164:96:0:0:205:318:15900:1 +MUSIQUE CLASSIQUE:11681:H:S13E:27500:165:100:0:0:206:318:15900:0 +ESCALES:11681:H:S13E:27500:166:104:0:0:207:318:15900:0 +FIT/ toute L'HISTOIRE:11681:H:S13E:27500:167:108:0:0:208:318:15900:0 +RFM-TV:11681:H:S13E:27500:168:112:0:0:209:318:15900:1 +ACTION:11681:H:S13E:27500:169:116:0:0:210:318:15900:0 +MANGAS:11681:H:S13E:27500:170:120:0:0:211:318:15900:0 +ENCYCLOPEDIA:11681:H:S13E:27500:171:124:0:0:212:318:15900:0 +RTL9:11681:H:S13E:27500:172:128:0:0:200:318:15900:0 +AB Moteurs:11681:H:S13E:27500:161:84:35:0:202:318:15900:0 +:->TPS 13?East +GOURMET TV:12245:H:S13E:27500:126:136:0:0:106:318:7700:0 +MCM Europe:12245:H:S13E:27500:122:132:0:0:102:318:7700:1 +MEZZO:12245:H:S13E:27500:125:135:0:0:105:318:7700:0 +CFI PECO PRO:12245:H:S13E:27500:121+131:131:0:0:101:318:7700:0 +FRANCE 2:10834:V:S13E:27500:320:330:0:0:1103:176:11600:0 +FRANCE 3:10834:V:S13E:27500:520:530:0:0:1105:176:11600:0 +FRANCE 5:10834:V:S13E:27500:220:230:0:0:1102:176:11600:0 +ARTE:10834:V:S13E:27500:720:730:0:0:1107:176:11600:0 +Eureka!:10796:V:S13E:27500:220:230:0:0:1402:176:11400:0 +Serie Club:10796:V:S13E:27500:320:330:0:0:1403:176:11400:0 +Fun TV:10796:V:S13E:27500:420:430:0:0:1404:176:11400:1 +Teva:10796:V:S13E:27500:520:530:0:0:1405:176:11400:0 +Teletoon:10796:V:S13E:27500:620:630:0:0:1406:176:11400:0 +Festival:10796:V:S13E:27500:720:730:0:0:1407:176:11400:0 +M6 Music:10796:V:S13E:27500:1020:1030:0:0:1410:176:11400:1 +M6 Boutique La Chane:10796:V:S13E:27500:1120:1130:0:0:1411:176:11400:0 +TF1:10909:V:S13E:27500:420:430:440:0:1604:176:12000:0 +TF6:10909:V:S13E:27500:720:730:0:0:1607:176:12000:0 +M6:10909:V:S13E:27500:120:130:140:0:1601:176:12000:0 +HISTOIRE:10909:V:S13E:27500:320:330:0:0:1603:176:12000:0 +Odyssee:10909:V:S13E:27500:620:630:0:0:1606:176:12000:0 +PARIS PREMIERE:10834:V:S13E:27500:620:630:0:0:1106:176:11600:0 +LCI:10834:V:S13E:27500:120:130:0:0:1101:176:11600:0 +I TELE:10834:V:S13E:27500:820:830:0:0:1108:176:11600:0 +PIWI:10796:V:S13E:27500:820:830:0:0:1408:176:11400:0 +TFOU:10909:V:S13E:27500:520:530:0:0:1605:176:12000:0 +RFO SAT:10909:V:S13E:27500:820:830:0:0:1608:176:12000:0 +Teletoon+1:10909:V:S13E:27500:920:930:0:0:1609:176:12000:0 +KTO:11034:V:S13E:27500:120:130:0:0:1701:176:12600:0 +STAR ACADEMY:10871:V:S13E:27500:120:130:0:0:1501:176:11800:0 +RTM:10871:V:S13E:27500:220:230:0:0:1502:176:11800:0 +SIC:10871:V:S13E:27500:520:530:0:0:1505:176:11800:0 +BBC PRIME:10871:V:S13E:27500:620:630:0:0:1506:176:11800:0 +TV BREIZH:10871:V:S13E:27500:720:730:0:0:1507:176:11800:0 +LA CHAINE PARLEMENTAIRE:10871:V:S13E:27500:1020:1030:0:0:1510:176:11800:0 +TPS Cinestar:10756:V:S13E:27500:120:130:140:0:1201:176:11200:0 +TPS Homecinema:10756:V:S13E:27500:220:230:240:0:1202:176:11200:0 +TPS Cinetoile:10756:V:S13E:27500:320:330:340:0:1203:176:11200:0 +TPS Cineculte:10756:V:S13E:27500:520:530:540:0:1205:176:11200:0 +TPS Cinextreme:10756:V:S13E:27500:620:630:640:0:1206:176:11200:0 +TPS Cinefamily:10756:V:S13E:27500:720:730:740:0:1207:176:11200:0 +TPS star:10756:V:S13E:27500:420:430:440:0:1204:176:11200:0 +Multivision 1:11662:V:S13E:27500:120:130:140:0:1301:176:15800:1 +Multivision 2:11662:V:S13E:27500:220:230:240:0:1302:176:15800:1 +Multivision 3:11662:V:S13E:27500:320:330:340:0:1303:176:15800:1 +Multivision 4:11662:V:S13E:27500:420:430:440:0:1304:176:15800:0 +Multivision 5:11662:V:S13E:27500:520:530:540:0:1305:176:15800:0 +Multivision 6:11662:V:S13E:27500:620:630:640:0:1306:176:15800:0 +Multivision 7:11662:V:S13E:27500:720:730:0:0:1307:176:15800:0 +Multivision NOOS:11662:V:S13E:27500:920:930:0:0:1319:176:15800:0 +Boomerang:11034:V:S13E:27500:320:330:0:0:1703:176:12600:0 +Berb?re T?l?vision:11034:V:S13E:27500:1120:1130:0:0:1711:176:12600:1 +PINK TV:11034:V:S13E:27500:1220:1230:0:0:1712:176:12600:0 +:->Serb/Monten13?East +PINK PLUS:12577:H:S13E:27500:512+8190:640:576:0:8101:318:9300:0 +PINK EXTRA:12577:H:S13E:27500:513+8190:641:0:0:8102:318:9300:0 +RTS SAT:12188:V:S13E:27500:519+131:657:0:0:1022:56:7400:1 +BK TV:12207:H:S13E:27500:3105+3110:3106:0:0:65:1:1:0 +RTV MONTENEGRO:12380:V:S13E:27500:3026:3036:0:0:3006:318:8400:0 +BALKANIA TV:12187:V:S13E:27500:3969+129:3970:0:0:1005:56:7400:0 +:->HRT/SLO/Asia 13?East +HRT-TV1:12520:V:S13E:27500:100:101:0:0:8301:318:9000:0 +HRT-TV2:12520:V:S13E:27500:103:104:0:0:8302:318:9000:0 +HRT PLUS:12520:V:S13E:27500:105:106:102:0:8303:318:9000:0 +SLO-TV1:12303:V:S13E:27500:200:201:202:0:3201:318:8191:0 +SLO-TV2:12303:V:S13E:27500:203:204:202:0:3202:318:8191:0 +CCTV4:12169:H:S13E:27500:516+8190:690:0:0:355:318:7300:0 +CCTV9:11034:V:S13E:27500:620:630:0:0:1706:176:12600:0 +MTA INTL:10723:H:S13E:29900:1004:1204:0:0:4604:318:11100:0 +VTV 4:12207:H:S13E:27500:2817:2818:0:0:50:1:1:0 +Asianet:12207:H:S13E:27500:1537:1538:0:0:34:1:1:0 +Kairali Europe:12207:H:S13E:27500:33:34:0:0:33:1:1:0 +TV 5 Global:12207:H:S13E:27500:1281:1282:0:0:81:1:1:1 +IndiaVision:12207:H:S13E:27500:514+513:515:0:0:20:1:1:0 +PEN TV:11585:V:S13E:27500:1361:1362:0:0:13506:318:15400:1 +BET-NAHRAIN:11585:V:S13E:27500:1351:1352:0:0:13505:318:15400:1 +MAHARISHI:11585:V:S13E:27500:1341:1342:0:0:13504:318:15400:1 +NTDTV:11585:V:S13E:27500:1331:1332:0:0:13503:318:15400:2 +DAYSTAR:11585:V:S13E:27500:1311:1312:0:0:13501:318:15400:1 +ROJ TV:11585:V:S13E:27500:1321+8190:1322:0:0:13502:318:15400:1 +JSTV 1:12597:V:S13E:27500:2000:2001:0:0:8213:318:9400:0 +Tele Lumiere:10949:V:S13E:27500:5101:5111:0:0:7402:318:12200:0 +Islah TV:10949:V:S13E:27500:5301:5311:0:0:7404:318:12200:0 +Adjara TV:10949:V:S13E:27500:5401:5411:0:0:7405:318:12200:0 +Sun KTV:10949:V:S13E:27500:5901:5911:0:0:7450:318:12200:0 +ANB:10949:V:S13E:27500:6101+2306:6111:0:0:7452:318:12200:0 +Sun TV +442083356780:10949:V:S13E:27500:6401:6411:0:0:7455:318:12200:0 +Al Mustakillah:10949:V:S13E:27500:6501+2307:6511:0:0:7456:318:12200:0 +Cartoon Network:10949:V:S13E:27500:6601+2308:6611:6621:0:7457:318:12200:0 +Dharma TV:10949:V:S13E:27500:6801:6811:0:0:7459:318:12200:0 +Prime TV:10949:V:S13E:27500:7001+2305:7011:0:0:7461:318:12200:0 +Urdu Europe:11727:V:S13E:27500:2611+2610:2612:0:0:13701:318:5000:0 +Bangla Europe:11727:V:S13E:27500:2621+2620:2622:0:0:13702:318:5000:0 +Tamil Europe:11727:V:S13E:27500:2631+2630:2632:0:0:13703:318:5000:0 +Hindi Europe:11727:V:S13E:27500:2641+2640:2642:0:0:13704:318:5000:0 +Locale:11727:V:S13E:27500:2711+2710:2712:0:0:13710:318:5000:0 +Zagros:11727:V:S13E:27500:2721+2720:2722:0:0:13720:318:5000:0 +:->Russia 13?East +CNL:12207:H:S13E:27500:3329:3330:0:0:51:1:1:0 +CH 1 RUS-ORTi:12597:V:S13E:27500:167:108:0:0:8208:318:9400:1 +ARM 1:12111:V:S13E:27500:240:241:0:0:705:318:7000:0 +Euro-News:12596:V:S13E:27500:2221:2237:768:0:8211:318:9400:4 +AJARA TV:12245:H:S13E:27500:127:137:0:0:107:318:8191:0 +RTR-Planet:11034:V:S13E:27500:820:830:0:0:1708:176:12600:0 +Suroyo TV:11938:H:S13E:27500:46:71:0:0:7420:318:61:0 +TV+:11938:H:S13E:27500:164:86:0:0:7201:318:61:0 +TV ROMANIA:11623:V:S13E:27500:227:247:0:0:10707:318:15600:0 +:->Spain +CCVALENCIANA:10817:V:S19.2E:22000:169:116:0:0:29954:1:1056:0 +TVC INT.:11686:V:S19.2E:22000:161:84:35:0:30201:1:1032:0 +ANDALUC?A TV:11686:V:S19.2E:22000:162:88:38:0:30202:1:1032:0 +EUSKADI TV:11686:V:S19.2E:22000:163:92:0:0:30203:1:1032:0 +TM SAT/LAOTRA:11686:V:S19.2E:22000:164:96:44:0:30204:1:1032:0 +TV GALICIA:11686:V:S19.2E:22000:167:108:53:0:30222:1:1032:0 +CANAL CANARIAS:10979:V:S19.2E:22000:164:96:0:0:30661:1:1034:1 +Euro-News:12595:V:S13E:27500:2221:2235:768:0:8211:318:9400:5 +LIBRE - CARTA:11785:H:S13E:27500:3577:3578:3580:0:3504:318:6983:0 +TVE INTER. ASIA:11785:H:S13E:27500:3553:3554:3556:0:3503:318:6215:0 +TVE INTERNACIONAL:11785:H:S13E:27500:3521:3522:3525:0:3501:318:65351:0 +CANAL 24 HORAS:11785:H:S13E:27500:3569:3570:3573:0:3502:318:5300:0 +Olisat VV Cont:11304:H:S13E:27500:1060:1020:0:0:8402:318:500:0 +Olisat TV CHILE:11304:H:S13E:27500:310:256:0:0:8403:318:500:0 +Olisat TV Colombia:11304:H:S13E:27500:513:514:0:0:8404:318:500:0 +Olisat Cubavision:11304:H:S13E:27500:101:201:0:0:8406:318:500:0 +Olisat servhisp:11304:H:S13E:27500:1037:1038:0:0:8405:318:500:0 +:->Polsat 13?East +Polsat:12322:H:S13E:27500:289:290:0:0:7303:113:8100:0 +Polsat 2:12322:H:S13E:27500:321:322:0:0:7305:113:8100:0 +TV 4:12322:H:S13E:27500:305:306:0:0:7304:113:8100:0 +Discovery:12322:H:S13E:27500:341:342:0:0:7315:113:8100:0 +Animal Planet:12322:H:S13E:27500:344:345:0:0:7316:113:8100:0 +AXN:12322:H:S13E:27500:353:356:0:0:7318:113:8100:0 +CNN Int.:12322:H:S13E:27500:848:849:0:0:7319:113:8100:0 +Playboy:12322:H:S13E:27500:545:546:0:0:7340:113:8100:1 +KINO POLSKA:12322:H:S13E:27500:2307:2305:0:0:7342:113:8100:0 +Fox Kids:12322:H:S13E:27500:337:338:0:0:7349:113:8100:0 +Zdrowie i Uroda test:12322:H:S13E:27500:801:802:0:0:7371:113:8100:0 +test2:12322:H:S13E:27500:806:807:0:0:7372:113:8100:0 +Cartoon Net./TCM:12360:H:S13E:27500:257:258:0:0:10501:113:8300:0 +Reality TV:12360:H:S13E:27500:535:536:0:0:10514:113:8300:0 +Club:12360:H:S13E:27500:369:370:0:0:10508:113:8300:0 +Europa Europa:12360:H:S13E:27500:353:354:356:0:10507:113:8300:0 +Science:12360:H:S13E:27500:544:545:0:0:10521:113:8300:0 +Civilisation:12360:H:S13E:27500:561:562:0:0:10522:113:8300:0 +Travel:12360:H:S13E:27500:566:567:568:0:10520:113:8300:0 +Polsat Sport:12360:H:S13E:27500:532:533:0:0:10513:113:8300:0 +Zdrowie i Uroda:12360:H:S13E:27500:868:869:0:0:10515:113:8300:0 +Info/Teleuniwersytet:12360:H:S13E:27500:513:514:0:0:10512:113:8300:0 +TVN Siedem:12322:H:S13E:27500:801:802:0:0:7371:113:8100:1 +TVN:12322:H:S13E:27500:806:807:0:0:7372:113:8100:1 +TVN:11408:V:S13E:27500:512+128:650:0:0:4311:318:1:0 +TVN 24:11408:V:S13E:27500:513+129:660:0:0:4312:318:1:0 +TVN Siedem:11408:V:S13E:27500:514+130:670:0:0:4313:318:1:0 +TVN METEO:11408:V:S13E:27500:519+134:720:0:0:4318:318:1:0 +TVN TURBO:11408:V:S13E:27500:520+135:730:0:0:4319:318:1:0 +TVN ST Test:11408:V:S13E:27500:521+136:740:0:0:4320:318:1:0 +:->Polen FTA 13?East +PilotTV:12360:H:S13E:27500:401:402:0:0:10517:113:8191:0 +Polonia 1:11513:H:S13E:27500:162:88:0:0:5103:318:1500:1 +TV POLONIA:11513:H:S13E:27500:160:80:500:0:5101:318:1500:1 +Tele5:11513:H:S13E:27500:161:84:0:0:5102:318:1500:1 +ITV:11513:H:S13E:27500:168:112:502:0:5109:318:1500:1 +MANGO 24:11408:V:S13E:27500:517+133:700:0:0:4316:318:1:0 +TV Puls:12322:H:S13E:27500:273:274:0:0:7320:113:8100:0 +:->Astra Mosaik19?E +ASTRA Satmode EU 1:12246:V:S19.2E:27500:802:803:0:0:3210:1:1:0 +ASTRA Satmode EU 2:12246:V:S19.2E:27500:818:819:0:0:3211:1:1:0 +ASTRA-Mosaic 6:12552:V:S19.2E:22000:190:191:0:0:3983:1:1108:0 +ASTRA-Mosaic 5:12552:V:S19.2E:22000:163:164:0:0:3984:1:1108:0 +ASTRA-Mosaic 4:12552:V:S19.2E:22000:185:170:0:0:3985:1:1108:0 +ASTRA-Mosaic 3:12552:V:S19.2E:22000:182:169:0:0:3986:1:1108:0 +ASTRA-Mosaic 2:12552:V:S19.2E:22000:179:120:0:0:3987:1:1108:0 +ASTRA-Mosaic:12552:V:S19.2E:22000:175:176:0:0:3988:1:1108:0 +Astra Vision:12552:V:S19.2E:22000:168:144:74:0:3997:1:1108:0 +ASTRA MHP MOSAIC:12552:V:S19.2E:22000:175:164:0:0:3980:1:1108:0 +Wishline:12610:V:S19.2E:22000:214:215:0:0:12320:1:1112:0 +Astra:10832:H:S19.2E:22000:55:56:0:0:61950:1:1057:1 +Euro1080:12168:V:S19.2E:27500:308:256:0:0:21100:1:1088:0 +Pioneer HDTV:12441:V:S19.2E:27500:133+80:134:0:0:29700:1:1102:0 +test_1016:11436:V:S19.2E:22000:214:215:0:0:123:1:1016:0 +Test T:12640:H:S19.2E:22000:204:304:0:0:12603:1:1113:1 +UNIVERSAL MOBILE:12363:V:S19.2E:27500:1+956:956:0:0:9121:1:1098:0 +:->Canal Digitaal 19,2?E +NED1:12515:H:S19.2E:22000:517+8190:88:34:0:4011:53:1105:0 +NED2:12515:H:S19.2E:22000:518+8190:92:35:0:4012:53:1105:0 +NED3:12515:H:S19.2E:22000:519+8190:96:36:0:4013:53:1105:0 +RTL4:12344:H:S19.2E:27500:512+8190:80:32:0:2004:53:1097:0 +RTL5:12344:H:S19.2E:27500:513+8190:92:33:0:2005:53:1097:0 +NET5:12574:H:S19.2E:22000:513+8190:100:37:0:5004:53:1109:0 +SBS6:12574:H:S19.2E:22000:514+8190:80:32:0:5005:53:1109:0 +Yorin:12574:H:S19.2E:22000:512+8190:84:33:0:5010:53:1109:0 +TMF:12574:H:S19.2E:22000:516+8190:88:34:0:5015:53:1109:1 +Veronica/FoxKids:12574:H:S19.2E:22000:518+8190:92:38:0:5020:53:1109:0 +BVN:12574:H:S19.2E:22000:515+8190:96:36:0:5025:53:1109:1 +RTBF SAT:12610:V:S19.2E:22000:48:49:0:0:3982:1:1112:1 +MEZZO:11817:V:S19.2E:27500:166:104:0:0:8007:1:1070:0 +EURONEWS:11817:V:S19.2E:27500:163:92:0:0:8004:1:1070:0 +Eurosport:12344:H:S19.2E:27500:517+8190:112:36:0:2025:53:1097:0 +Hallmark:12344:H:S19.2E:27500:519+8190:108:0:0:2035:53:1097:0 +BBC Prime:12344:H:S19.2E:27500:518+8190:116:37:0:2030:53:1097:0 +Animal Planet:12344:H:S19.2E:27500:514+8190:96:35:0:2020:53:1097:0 +NGC:12344:H:S19.2E:27500:516+8190:84:0:0:2010:53:1097:0 +Discovery:12344:H:S19.2E:27500:515+8190:88:34:0:2015:53:1097:0 +Nickelodeon NL:11739:V:S19.2E:27500:3081:3082:3084:0:28658:1:1066:0 +Cartoon / TCM:12515:H:S19.2E:22000:523+8190:116:39:0:4015:53:1105:0 +SPICE PLATINUM:12515:H:S19.2E:22000:515+8190:87:0:0:4009:53:1105:0 +C+16/9:12515:H:S19.2E:22000:514+8190:104:0:0:4007:53:1105:0 +C+ Rood:12515:H:S19.2E:22000:512+8190:80:0:0:4005:53:1105:0 +C+ Blauw:12515:H:S19.2E:22000:513+8190:84:0:0:4006:53:1105:0 +:->ORF 19,2?East +ORF 2 E:12692:H:S19.2E:22000:170:171:505:0:13014:1:1117:0 +ORF 1:12692:H:S19.2E:22000:160:161:165:0:13001:1:1117:0 +ORF 2:12692:H:S19.2E:22000:500:501:505:0:13002:1:1117:0 +ORF2 Wien:12692:H:S19.2E:22000:510:511:505:0:13003:1:1117:0 +ORF2 Nieder?sterreich:12692:H:S19.2E:22000:500:501:505:0:13004:1:1117:0 +ORF2 Burgenland:12692:H:S19.2E:22000:530:531:505:0:13005:1:1117:0 +ORF2 Ober?sterreich:12692:H:S19.2E:22000:540:541:505:0:13006:1:1117:0 +ORF2 Salzburg:12692:H:S19.2E:22000:550:551:505:0:13007:1:1117:0 +ORF2 Tirol:12692:H:S19.2E:22000:560:561:505:0:13008:1:1117:0 +ORF2 Vorarlberg:12692:H:S19.2E:22000:570:571:505:0:13009:1:1117:0 +ORF2 Steiermark:12692:H:S19.2E:22000:580:581:505:0:13010:1:1117:0 +ORF2 K?rnten:12692:H:S19.2E:22000:590:591:505:0:13011:1:1117:0 +TW1:12692:H:S19.2E:22000:166:167:168:0:13013:1:1117:0 +ATV+:12692:H:S19.2E:22000:506:507:509:0:13012:1:1117:1 +PREMIERE Austria:12148:H:S19.2E:27500:2559:2560:35:0:53:133:7:0 +BLUE MOVIE Austria:12148:H:S19.2E:27500:592:593:0:0:52:133:7:0 +RTL Austria:12226:H:S19.2E:27500:201:202:203:0:28800:1:1091:0 +RTL2 Austria:12226:H:S19.2E:27500:401:402:0:0:28810:1:1091:0 +VOX Austria:12226:H:S19.2E:27500:301:302:303:0:28805:1:1091:0 +Super RTL A:12226:H:S19.2E:27500:501:502:503:0:28815:1:1091:0 +ProSieben Austria:12051:V:S19.2E:27500:161:84:36:0:20002:1:1082:0 +SAT.1 A:12051:V:S19.2E:27500:800:801:802:0:20005:1:1082:0 +Kabel 1 Austria:12051:V:S19.2E:27500:166:167:169:0:20004:1:1082:0 +:->Formel 1 19,2?East +F1 Portal:11720:H:S19.2E:27500:255:256:0:0:17:133:3:0 +Supersignal:11720:H:S19.2E:27500:2047:2048:0:0:240:0:0:0 +Cockpitkanal:11720:H:S19.2E:27500:2303:2304:0:0:241:0:0:0 +Boxengasse:11720:H:S19.2E:27500:2559:2560:0:0:242:0:0:0 +Highlights:11720:H:S19.2E:27500:2815:2816:0:0:243:0:0:0 +Interaktiv:11720:H:S19.2E:27500:3071:3072:0:0:244:0:0:0 +F1 Portal2:12032:H:S19.2E:27500:3839:3840:0:0:27:133:4:0 +:->Premiere Direkt 19,2?E +Direkt Portal:12032:H:S19.2E:27500:2815:2816:2819:0:18:133:4:0 +Direkt 01:11720:H:S19.2E:27500:2047:2048:0:0:240:133:3:0 +Direkt 02:11720:H:S19.2E:27500:2303:2304:0:0:241:133:3:0 +Direkt 03:11720:H:S19.2E:27500:2559:2560:0:0:242:133:3:0 +Direkt 04:11720:H:S19.2E:27500:2815:2816:0:0:243:133:3:0 +Direkt 05:11720:H:S19.2E:27500:3071:3072:0:0:244:133:3:0 +Direkt 06:11720:H:S19.2E:27500:3327:3328:0:0:245:133:3:0 +Direkt 07:12032:H:S19.2E:27500:3071:3072:0:0:208:133:4:0 +Direkt 08:12032:H:S19.2E:27500:3327:3328:0:0:209:133:4:0 +Direkt 09:12032:H:S19.2E:27500:2303:2304:0:0:210:133:4:0 +Direkt 10:11758:H:S19.2E:27500:511:512:0:0:211:133:17:0 +Direkt 11:12070:H:S19.2E:27500:511:512:0:0:212:0:0:0 +Erotik1:12070:H:S19.2E:27500:255:256:0:0:777:0:0:0 +Erotik2:12070:H:S19.2E:27500:1535:1536:0:0:778:133:1:0 +Erotik3:12070:H:S19.2E:27500:1791:1792:0:0:779:133:1:0 +Erotik4:12070:H:S19.2E:27500:3583:3584:0:0:780:133:1:0 +PREMIERE EROTIK:12032:H:S19.2E:27500:1279:1280:0:0:513:133:4:0 +BEATE-UHSE.TV:12070:H:S19.2E:27500:1023:1024:0:0:21:133:1:0 +BIG BROTHER:12070:H:S19.2E:27500:2559:2560:32:0:50:133:1:0 +DPC_DVB:12148:H:S19.2E:27500:2815:2816:0:0:660:133:7:0 +DPC.TV 3:12480:V:S19.2E:27500:2559:2560:0:0:661:133:33:1 +DPC.TV1:12460:H:S19.2E:27500:1023:1024:0:0:663:133:5:0 +:->Horses +EQUIDIA PRO P1:12379:V:S13E:27500:321:0:0:0:3052:318:8400:0 +EQUIDIA PRO:12379:V:S13E:27500:3321:3331:0:0:3051:318:8400:0 +Casino Channel:10949:V:S13E:27500:6701+2305:6711:0:0:7458:318:12200:0 +Raze TV:10832:H:S19.2E:22000:308:256:0:0:61963:1:1057:1 +:->Bundesliga 19?East +Konferenz:11720:H:S19.2E:27500:255:256:0:0:17:133:3:1 +Spiel 1:11720:H:S19.2E:27500:2047:2048:0:0:240:0:0:1 +Spiel 2:11720:H:S19.2E:27500:2303:2304:0:0:241:0:0:1 +Spiel 3:11720:H:S19.2E:27500:2559:2560:0:0:242:0:0:1 +Spiel 4:11720:H:S19.2E:27500:2815:2816:0:0:243:0:0:1 +Spiel 5:11720:H:S19.2E:27500:3071:3072:0:0:244:0:0:1 +Spiel 6:11720:H:S19.2E:27500:3327:3328:0:0:245:133:3:1 +Spiel 7:12032:H:S19.2E:27500:3071:3072:0:0:208:0:0:0 +Spiel 8:12032:H:S19.2E:27500:3327:3328:0:0:209:0:0:0 +Spiel 9:12032:H:S19.2E:27500:2303:2304:0:0:210:133:4:1 +Test:11758:H:S19.2E:27500:1791:0:0:0:213:1:17:0 +:->TPS Sport 13?East +EUROSPORT TPS:10909:V:S13E:27500:220:230:0:0:1602:176:12000:0 +Multivision 8:10909:V:S13E:27500:220:230:240:0:1602:176:12000:1 +ENGLISH PREMIER LEAGUE:10834:V:S13E:27500:420:430:0:0:1104:176:11600:0 +EUROSPORTNEWS:12558:V:S13E:27500:2825:2823:2831:0:9365:319:9200:0 +Infosport:10796:V:S13E:27500:120:130:0:0:1401:176:11400:0 +SIC:10871:V:S13E:27500:520:530:0:0:1505:176:11800:1 +EQUIDIA:10871:V:S13E:27500:320:330:0:0:1503:176:11800:0 +ESPN CLASSIC SPORT:10871:V:S13E:27500:420:430:0:0:1504:176:11800:0 +:->Sport +Sport Italia - Si Dfree:11387:H:S13E:27500:515+131:680:0:0:14:272:900:0 +Prima:11387:H:S13E:27500:516+132:690:0:0:19:272:900:1 +DSF:12480:V:S19.2E:27500:1023:1024:0:0:900:133:33:2 +Eurosport:11954:H:S19.2E:27500:410:420:430:0:28009:1:1079:1 +NBA+:11895:V:S19.2E:27500:160:80:0:0:8362:1:1074:1 +Polsat Sport:12360:H:S13E:27500:532:533:0:0:10513:113:8300:1 +MOTORS TV:12640:V:S19.2E:22000:169:116:0:0:8910:1:1114:1 +RTL5:12344:H:S19.2E:27500:513+8190:92:33:0:2005:53:1097:1 +RTS SAT:12187:V:S13E:27500:519+131:657:0:0:1022:56:7400:2 +JAAM E JAM:11585:V:S13E:27500:1411:1412:0:0:13511:318:15400:1 +Jame-Jam 2:12437:H:S13E:27500:161:83:0:0:7904:318:8700:1 +TRT INT:10957:H:S13E:4340:308+8190:256:273:0:1:65535:1:2 +RTV MONTENEGRO:12380:V:S13E:27500:3026:3036:0:0:3006:318:8400:1 +TVE INTERNACIONAL:11785:H:S13E:27500:3521:3522:3525:0:1:4369:5300:0 +Italia 1:11919:V:S13E:27500:512+128:650:0:0:1:272:6000:1 +TF1:10911:V:S13E:27500:420:430:440:0:1604:176:12000:1 +RTPI:11568:V:S19.2E:22000:161:301:302:0:9017:1:1024:1 +CANAL ALGERIE:11568:V:S19.2E:22000:168:138:0:0:9011:1:1024:1 +TV7:11568:V:S19.2E:22000:166:128:0:0:9018:1:1024:1 +Dubai Sports EU:11747:H:S13E:27500:4386:4388:0:0:9502:318:5103:1 +EDTV Sports:11747:H:S13E:27500:4386:4387:0:0:9502:318:5103:2 +Sailing Channel:11200:V:S13E:27500:370:371:0:0:4708:318:13400:0 +TW 1:12692:H:S19.2E:22000:166:167:0:0:13013:1:1117:1 +NED2:12515:H:S19.2E:22000:518+8190:92:35:0:4012:53:1105:1 +FRANCE 3:10834:V:S13E:27500:520:530:0:0:1105:176:11600:1 +Infosport:10796:V:S13E:27500:120:130:0:0:1401:176:11400:1 +SLO-TV2:12303:V:S13E:27500:203:204:202:0:3202:318:8191:1 +TSI2:12399:H:S13E:27500:166:100:50:0:909:318:8500:1 +CH 3 Arabic IBA TV:12207:H:S13E:27500:1057+1062:1058:0:0:49:1:1:1 +RaiSportSat:11804:V:S13E:27500:512:650:0:0:3305:318:5400:1 +RAI2:11766:V:S13E:27500:513:651:577:0:3402:318:5200:1 +RAI3:11766:V:S13E:27500:514:652:578:0:3403:318:5200:1 +:->Premiere 19?East +Sport 1:11720:H:S19.2E:27500:255:256:0:0:17:133:3:2 +Sport 2:12032:H:S19.2E:27500:3839:3840:0:0:27:133:4:1 +PREMIERE 1:11798:H:S19.2E:27500:511:512:32:0:10:133:2:0 +PREMIERE 2:11798:H:S19.2E:27500:1791:1792:32:0:11:133:2:0 +PREMIERE 3:11798:H:S19.2E:27500:2303:2304:0:0:43:133:2:0 +PREMIERE 4:11798:H:S19.2E:27500:767:768:0:0:9:133:2:0 +PREMIERE 5:11798:H:S19.2E:27500:1279:1280:32:0:29:133:2:0 +PREMIERE 6:11798:H:S19.2E:27500:1535:1536:32:0:41:133:2:0 +PREMIERE 7:11798:H:S19.2E:27500:1023:1024:32:0:20:133:2:0 +PREMIERE START:11798:H:S19.2E:27500:255:256:32:0:8:133:2:0 +DISNEY CHANNEL:11758:H:S19.2E:27500:2559:2560:0:0:34:133:17:0 +GOLDSTAR TV:12070:H:S19.2E:27500:3839:3840:0:0:518:133:1:0 +HEIMATKANAL:12070:H:S19.2E:27500:1279:1280:32:0:22:133:1:0 +CLASSICA:12070:H:S19.2E:27500:767:768:0:0:15:133:1:0 +JUNIOR:11758:H:S19.2E:27500:255:256:0:0:19:133:17:0 +FOX KIDS:11758:H:S19.2E:27500:1279:1280:0:0:28:133:17:0 +PREMIERE KRIMI:12032:H:S19.2E:27500:1535:1536:0:0:23:133:4:0 +PREMIERE SERIE:12032:H:S19.2E:27500:1023:1024:0:0:16:133:4:0 +PREMIERE NOSTALGIE:12032:H:S19.2E:27500:2559:2560:0:0:516:133:4:0 +ANIMAL PLANET:11758:H:S19.2E:27500:2815:2816:0:0:12:133:17:0 +HIT24:11758:H:S19.2E:27500:3071:3072:0:0:168:133:17:0 +13 TH STREET:11758:H:S19.2E:27500:2303:2304:0:0:42:133:17:0 +MGM:11758:H:S19.2E:27500:767:768:0:0:515:133:17:0 +SCI FI:11758:H:S19.2E:27500:2047:2048:0:0:36:133:17:0 +DISCOVERY CHANNEL:11758:H:S19.2E:27500:1023:1024:0:0:14:133:17:0 +:-> Fav +ORF 1:12692:H:S19.2E:22000:160:161:165:0:13001:1:1117:1 +ORF 2:12692:H:S19.2E:22000:500:501:505:0:13002:1:1117:1 +ATV+:12692:H:S19.2E:22000:506:507:509:0:13012:1:1117:2 +SFi:12399:H:S13E:27500:167:102:58:0:911:318:8500:2 +SF1:12399:H:S13E:27500:160:80:32:0:901:318:8500:1 +SF2:12399:H:S13E:27500:163:92:41:0:907:318:8500:1 +TSI2:12399:H:S13E:27500:166:100:50:0:909:318:8500:2 +CLEAR TV:12610:V:S19.2E:22000:191:192:193:0:12300:1:1112:0 +tv.gusto:12460:H:S19.2E:27500:3071:3072:0:0:659:133:5:1 +TERRA NOVA:12285:V:S19.2E:27500:173:132:35:0:17033:1:1094:0 +XXP Spiegel TV:12633:H:S19.2E:22000:203:303:503:0:12602:1:1113:1 +ZDFdokukanal:11954:H:S19.2E:27500:660:670:130:0:28014:1:1079:1 +ZDFinfokanal:11954:H:S19.2E:27500:610:620:130:0:28011:1:1079:1 +N24:12480:V:S19.2E:27500:2047:2048:36:0:47:133:33:1 +arte:11837:H:S19.2E:27500:401:402:0:0:28109:1:1101:1 +3sat:11954:H:S19.2E:27500:210:220:0:0:28007:1:1079:1 +Phoenix:11837:H:S19.2E:27500:901:902:0:0:28114:1:1101:1 +EinsFestival:12109:H:S19.2E:27500:201:202:0:0:28202:1:1073:2 +EinsExtra:12109:H:S19.2E:27500:101:102:0:0:28201:1:1073:1 +:->Astra19,2?East Radio +Radio FG:12207:V:S19.2E:27500:1+236:243:0:0:8510:1:1090:0 +sunshine live:12149:H:S19.2E:27500:1+336:336:0:0:169:133:7:0 +Inselradio/Mallorca:12633:H:S19.2E:22000:1+702:702:0:0:12651:1:1113:0 +ANTENNE BAYERN:12149:H:S19.2E:27500:0+352:352:0:0:170:133:7:0 +OE3:12663:H:S19.2E:22000:1+433:433:0:0:13133:1:1115:0 +OE2 Tirol:12663:H:S19.2E:22000:1+428:428:0:0:13128:1:1115:0 +FM4:12663:H:S19.2E:22000:1+434:434:0:0:13134:1:1115:0 +YOU FM:11837:H:S19.2E:27500:1+3501:3501:0:0:28125:1:1101:0 +Sky Rock:12207:V:S19.2E:27500:1+236:239:0:0:8510:1:1090:1 +NRJ:12207:V:S19.2E:27500:1+236:236:0:0:8510:1:1090:2 +RTL RADIO:12344:H:S19.2E:27500:1+8190:104:0:0:2051:53:1097:0 +MDR JUMP:12109:H:S19.2E:27500:1+1001:1001:0:0:28210:1:1073:0 +SPUTNIK:12109:H:S19.2E:27500:1+1201:1201:0:0:28212:1:1073:0 +Fritz:12109:H:S19.2E:27500:1+901:901:0:0:28209:1:1073:0 +HIT RADIO FFH:12633:H:S19.2E:22000:1+1023:1024:0:0:12660:1:1113:0 +planet radio:12633:H:S19.2E:22000:1+1029:1030:0:0:12661:1:1113:0 +harmony fm:12633:H:S19.2E:22000:1+1035:1036:0:0:12662:1:1113:0 +Radio Maria:12633:H:S19.2E:22000:1+701:701:0:0:12650:1:1113:0 +ROCK ANTENNE:12149:H:S19.2E:27500:0+304:304:0:0:160:133:7:0 +ERF Radio:12149:H:S19.2E:27500:1+320:320:0:0:161:133:7:0 +NDR Kultur:12109:H:S19.2E:27500:1+701:701:2404:0:28207:1:1073:0 +MDR FIGARO:12109:H:S19.2E:27500:1+801:801:0:0:28208:1:1073:0 +MDR INFO:12109:H:S19.2E:27500:1+1101:1101:0:0:28211:1:1073:0 +RADIOmultikulti:12109:H:S19.2E:27500:1+1301:1301:0:0:28213:1:1073:0 +SWR2:12109:H:S19.2E:27500:1+1401:1401:0:0:28214:1:1073:0 +WDR 3:12109:H:S19.2E:27500:1+1501:1501:0:0:28215:1:1073:0 +WDR 5:12109:H:S19.2E:27500:1+1601:1601:0:0:28216:1:1073:0 +Bayern 4 Klassik:11837:H:S19.2E:27500:1+3001:3001:0:0:28120:1:1101:0 +B5 aktuell:11837:H:S19.2E:27500:1+3101:3101:0:0:28121:1:1101:0 +hr-skyline +:11837:H:S19.2E:27500:1+3201:3201:0:0:28122:1:1101:0 +hr2:11837:H:S19.2E:27500:1+3301:3301:0:0:28123:1:1101:0 +hr-klassik:11837:H:S19.2E:27500:1+3401:3401:0:0:28124:1:1101:0 +Bayern 1:11837:H:S19.2E:27500:1+3601:3601:0:0:28126:1:1101:0 +NDR Info:11837:H:S19.2E:27500:1+3701:3701:0:0:28127:1:1101:0 +NordwestRadio:11837:H:S19.2E:27500:1+3801:3801:0:0:28128:1:1101:0 +SR 1:11837:H:S19.2E:27500:1+3901:3901:0:0:28129:1:1101:0 +DLF-K?ln:11954:H:S19.2E:27500:1+810:810:0:0:28013:1:1079:0 +DLR-Berlin:11954:H:S19.2E:27500:1+710:710:0:0:28012:1:1079:0 +DW04:11597:V:S19.2E:22000:1+128:2040:128:0:10024:1:1026:0 +DW03:11597:V:S19.2E:22000:1+37:37:0:0:10023:1:1026:0 +DW01:11597:V:S19.2E:22000:1+128:2010:128:0:10021:1:1026:0 +domradio:12460:H:S19.2E:27500:1+368:368:0:0:171:133:5:0 +La Premi?re Sat:12610:V:S19.2E:22000:1:52:0:0:12342:1:1112:0 +CFN/RFC:12610:V:S19.2E:22000:1+51:51:0:0:12341:1:1112:0 +CFN/RFC:10832:H:S19.2E:22000:1+58:58:0:0:61994:1:1057:0 +Radio Maryja:10832:H:S19.2E:22000:1+73:73:0:0:61912:1:1057:0 +Radio Horeb:10832:H:S19.2E:22000:1+64:64:0:0:61960:1:1057:0 +RDC:10832:H:S19.2E:22000:1+67:67:0:0:61962:1:1057:0 +Jazz Radio Berlin:10832:H:S19.2E:22000:1+4384:4384:0:0:61965:1:1057:0 +Radio Neue Hoffnung:10832:H:S19.2E:22000:1+59:59:0:0:61995:1:1057:0 +Radio Caroline:10832:H:S19.2E:22000:1+4128:4128:0:0:61966:1:1057:0 +:->Les Radios 19,2?East +Contact FM:12207:V:S19.2E:27500:0+236:245:0:0:8510:1:1090:3 +Voltage:12207:V:S19.2E:27500:0+236:251:0:0:8510:1:1090:4 +Ado FM:12207:V:S19.2E:27500:0+236:253:0:0:8510:1:1090:5 +Couleur 3:12207:V:S19.2E:27500:0+169:1948:0:0:8511:1:1090:0 +Vibration:12207:V:S19.2E:27500:0+236:244:0:0:8510:1:1090:6 +Le Mouv:12207:V:S19.2E:27500:0+236:241:0:0:8510:1:1090:7 +Alouette:12207:V:S19.2E:27500:0+236:250:0:0:8510:1:1090:8 +Europe 2:12207:V:S19.2E:27500:0+236:237:0:0:8510:1:1090:9 +RTL 2:12207:V:S19.2E:27500:0+236:238:0:0:8510:1:1090:10 +Radio Nova:12207:V:S19.2E:27500:0+236:242:0:0:8510:1:1090:11 +Fun Radio:12207:V:S19.2E:27500:0+236:240:0:0:8510:1:1090:12 +RFM:12207:V:S19.2E:27500:0+236:248:0:0:8510:1:1090:13 +Montmartre FM:12207:V:S19.2E:27500:0+168:1915:0:0:8509:1:1090:0 +Hector:12207:V:S19.2E:27500:0+168:168:0:0:8509:1:1090:1 +Radio Nostalgie:12207:V:S19.2E:27500:0+236:246:0:0:8510:1:1090:14 +Cherie FM:12207:V:S19.2E:27500:0+236:249:0:0:8510:1:1090:15 +Oui FM:12207:V:S19.2E:27500:0+236:252:0:0:8510:1:1090:16 +Paris Jazz:12207:V:S19.2E:27500:0+236:254:0:0:8510:1:1090:17 +France Musique:12207:V:S19.2E:27500:0+168:1901:0:0:8509:1:1090:2 +France Inter Paris:12207:V:S19.2E:27500:0+168:1903:0:0:8509:1:1090:3 +France Info:12207:V:S19.2E:27500:0+168:1904:0:0:8509:1:1090:4 +France Inter:12207:V:S19.2E:27500:0+168:1905:0:0:8509:1:1090:5 +France Culture:12207:V:S19.2E:27500:0+168:1906:0:0:8509:1:1090:6 +Radio Bleue:12207:V:S19.2E:27500:0+168:1907:0:0:8509:1:1090:7 +Radio France Inter.:12207:V:S19.2E:27500:0+168:1908:0:0:8509:1:1090:8 +Radio Classique:12207:V:S19.2E:27500:0+168:1909:0:0:8509:1:1090:9 +RTL:12207:V:S19.2E:27500:0+168:1910:0:0:8509:1:1090:10 +Europe 1:12207:V:S19.2E:27500:0+168:1911:0:0:8509:1:1090:11 +Radio Monte Carlo:12207:V:S19.2E:27500:0+168:1912:0:0:8509:1:1090:12 +Rire et Chansons:12207:V:S19.2E:27500:0+168:1913:0:0:8509:1:1090:13 +Sud Radio:12207:V:S19.2E:27500:0+168:1914:0:0:8509:1:1090:14 [... truncated: 5609 lines follow ...] From korli at mail.berlios.de Sun Apr 15 22:40:13 2007 From: korli at mail.berlios.de (korli at BerliOS) Date: Sun, 15 Apr 2007 22:40:13 +0200 Subject: [Haiku-commits] r20711 - in haiku/trunk: headers/private/media src/kits/support src/servers/media Message-ID: <200704152040.l3FKeD42017182@sheep.berlios.de> Author: korli Date: 2007-04-15 22:40:12 +0200 (Sun, 15 Apr 2007) New Revision: 20711 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20711&view=rev Modified: haiku/trunk/headers/private/media/DataExchange.h haiku/trunk/src/kits/support/Beep.cpp haiku/trunk/src/kits/support/Jamfile haiku/trunk/src/servers/media/MMediaFilesManager.cpp haiku/trunk/src/servers/media/MMediaFilesManager.h haiku/trunk/src/servers/media/media_server.cpp Log: implemented add_system_beep_event() Modified: haiku/trunk/headers/private/media/DataExchange.h =================================================================== --- haiku/trunk/headers/private/media/DataExchange.h 2007-04-15 19:00:26 UTC (rev 20710) +++ haiku/trunk/headers/private/media/DataExchange.h 2007-04-15 20:40:12 UTC (rev 20711) @@ -74,6 +74,8 @@ MEDIA_SERVER_GET_FORMATS, MEDIA_SERVER_MAKE_FORMAT_FOR, + + MEDIA_SERVER_SYSTEM_BEEP_EVENT }; // Raw port based communication @@ -1012,4 +1014,10 @@ { }; + + +enum { + SYSTEM_BEEP_EVENT_INVOKE = 1, + SYSTEM_BEEP_EVENT_ADD +}; #endif // _DATA_EXCHANGE_H Modified: haiku/trunk/src/kits/support/Beep.cpp =================================================================== --- haiku/trunk/src/kits/support/Beep.cpp 2007-04-15 19:00:26 UTC (rev 20710) +++ haiku/trunk/src/kits/support/Beep.cpp 2007-04-15 20:40:12 UTC (rev 20711) @@ -7,13 +7,24 @@ #include #include +#include "DataExchange.h" + status_t system_beep(const char *eventName) { - printf("beep event \"%s\" requested.\n", eventName); - // ToDo: ask media server to beep around - return B_ERROR; + BMessenger messenger("application/x-vnd.Be.media-server"); + if (!messenger.IsValid()) + return B_ERROR; + BMessage msg(MEDIA_SERVER_SYSTEM_BEEP_EVENT), reply; + msg.AddInt32("action", SYSTEM_BEEP_EVENT_INVOKE); + msg.AddString("event", eventName); + + status_t err = messenger.SendMessage(&msg, &reply); + if ((err != B_OK) + || (reply.FindInt32("error", &err) != B_OK)) + err = B_BAD_REPLY; + return err; } @@ -27,7 +38,18 @@ status_t add_system_beep_event(const char *eventName, uint32 flags) { - // ToDo: ask media server to add beep event - return B_ERROR; + BMessenger messenger("application/x-vnd.Be.media-server"); + if (!messenger.IsValid()) + return B_ERROR; + BMessage msg(MEDIA_SERVER_SYSTEM_BEEP_EVENT), reply; + msg.AddInt32("action", SYSTEM_BEEP_EVENT_ADD); + msg.AddString("event", eventName); + msg.AddInt32("flags", flags); + + status_t err = messenger.SendMessage(&msg, &reply); + if ((err != B_OK) + || (reply.FindInt32("error", &err) != B_OK)) + err = B_BAD_REPLY; + return err; } Modified: haiku/trunk/src/kits/support/Jamfile =================================================================== --- haiku/trunk/src/kits/support/Jamfile 2007-04-15 19:00:26 UTC (rev 20710) +++ haiku/trunk/src/kits/support/Jamfile 2007-04-15 20:40:12 UTC (rev 20711) @@ -8,7 +8,7 @@ # # addr_t. #} -UsePrivateHeaders shared app ; +UsePrivateHeaders shared app media ; MergeObject support_kit.o : Archivable.cpp Modified: haiku/trunk/src/servers/media/MMediaFilesManager.cpp =================================================================== --- haiku/trunk/src/servers/media/MMediaFilesManager.cpp 2007-04-15 19:00:26 UTC (rev 20710) +++ haiku/trunk/src/servers/media/MMediaFilesManager.cpp 2007-04-15 20:40:12 UTC (rev 20711) @@ -4,6 +4,7 @@ */ #include #include +#include #include #include #include @@ -363,3 +364,37 @@ fRunner = NULL; } + +void +MMediaFilesManager::HandleSystemBeepEvent(BMessage *msg) +{ + int32 action, flags; + BString event; + status_t err = B_OK; + if ((msg->FindString("event", &event) != B_OK) + || (msg->FindInt32("action", &action) != B_OK)) { + err = B_BAD_VALUE; + } + + if (action == SYSTEM_BEEP_EVENT_ADD) { + if (msg->FindInt32("flags", &flags) != B_OK) + err = B_BAD_VALUE; + } + + if (err != B_OK) { + msg->SendReply(err); + return; + } + + switch (action) { + case SYSTEM_BEEP_EVENT_ADD: { + entry_ref ref; + SetRefFor(BMediaFiles::B_SOUNDS, event.String(), ref); + break; + } + case SYSTEM_BEEP_EVENT_INVOKE: { + // TODO play the sound + } + } +} + Modified: haiku/trunk/src/servers/media/MMediaFilesManager.h =================================================================== --- haiku/trunk/src/servers/media/MMediaFilesManager.h 2007-04-15 19:00:26 UTC (rev 20710) +++ haiku/trunk/src/servers/media/MMediaFilesManager.h 2007-04-15 20:40:12 UTC (rev 20711) @@ -51,6 +51,8 @@ void TimerMessage(); + void HandleSystemBeepEvent(BMessage *msg); + private: static int32 ReadPascalString(BFile &file, char **str); static int32 WritePascalString(BFile &file, const char *str); Modified: haiku/trunk/src/servers/media/media_server.cpp =================================================================== --- haiku/trunk/src/servers/media/media_server.cpp 2007-04-15 19:00:26 UTC (rev 20710) +++ haiku/trunk/src/servers/media/media_server.cpp 2007-04-15 20:40:12 UTC (rev 20711) @@ -802,7 +802,10 @@ case MEDIA_SERVER_MAKE_FORMAT_FOR: gFormatManager->MakeFormatFor(*msg); break; - + + case MEDIA_SERVER_SYSTEM_BEEP_EVENT: + gMMediaFilesManager->HandleSystemBeepEvent(msg); + break; default: inherited::MessageReceived(msg); printf("\nmedia_server: unknown message received:\n"); From hugosantos at mail.berlios.de Sun Apr 15 23:00:31 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Sun, 15 Apr 2007 23:00:31 +0200 Subject: [Haiku-commits] r20712 - in haiku/trunk: headers/private/net src/add-ons/kernel/network/datalink_protocols/arp Message-ID: <200704152100.l3FL0VoN019973@sheep.berlios.de> Author: hugosantos Date: 2007-04-15 23:00:12 +0200 (Sun, 15 Apr 2007) New Revision: 20712 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20712&view=rev Modified: haiku/trunk/headers/private/net/arp_control.h haiku/trunk/src/add-ons/kernel/network/datalink_protocols/arp/arp.cpp Log: ARP now queues packets while resolving a destination instead of blocking on send_data(). This fixes several issues: - TCP now behaves correctly when receiving new connections as its SYN/ACK is queued, or if lost correctly retransmitted when the peer resends a SYN. - The first ICMP Replies from an external on-link host pinging Haiku are no longer lost. - Reduced the number of ARP messages Haiku needs to generate until resolving an entry. Modified: haiku/trunk/headers/private/net/arp_control.h =================================================================== --- haiku/trunk/headers/private/net/arp_control.h 2007-04-15 20:40:12 UTC (rev 20711) +++ haiku/trunk/headers/private/net/arp_control.h 2007-04-15 21:00:12 UTC (rev 20712) @@ -16,6 +16,7 @@ #define ARP_FLAG_REJECT 0x02 #define ARP_FLAG_PERMANENT 0x04 #define ARP_FLAG_PUBLISH 0x08 +#define ARP_FLAG_VALID 0x10 // generic syscall interface Modified: haiku/trunk/src/add-ons/kernel/network/datalink_protocols/arp/arp.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/datalink_protocols/arp/arp.cpp 2007-04-15 20:40:12 UTC (rev 20711) +++ haiku/trunk/src/add-ons/kernel/network/datalink_protocols/arp/arp.cpp 2007-04-15 21:00:12 UTC (rev 20712) @@ -4,6 +4,7 @@ * * Authors: * Axel D?rfler, axeld at pinc-software.de + * Hugo Santos, hugosantos at gmail.com */ //! Ethernet Address Resolution Protocol, see RFC 826. @@ -18,6 +19,7 @@ #include #include +#include #include #include @@ -65,18 +67,28 @@ in_addr_t protocol_address; sockaddr_dl hardware_address; uint32 flags; - sem_id resolved_sem; net_buffer *request_buffer; net_timer timer; uint32 timer_state; bigtime_t timestamp; net_datalink_protocol *protocol; + typedef DoublyLinkedListCLink NetBufferLink; + typedef DoublyLinkedList BufferList; + + BufferList queue; + static int Compare(void *_entry, const void *_key); static uint32 Hash(void *_entry, const void *_key, uint32 range); static arp_entry *Lookup(in_addr_t protocolAddress); static arp_entry *Add(in_addr_t protocolAddress, sockaddr_dl *hardwareAddress, uint32 flags); + + ~arp_entry(); + + void ClearQueue(); + void MarkFailed(); + void MarkValid(); }; // see arp_control.h for flags @@ -109,9 +121,9 @@ arp_entry::Compare(void *_entry, const void *_key) { arp_entry *entry = (arp_entry *)_entry; - in_addr_t key = (in_addr_t)_key; + in_addr_t *key = (in_addr_t *)_key; - if (entry->protocol_address == key) + if (entry->protocol_address == *key) return 0; return 1; @@ -122,13 +134,13 @@ arp_entry::Hash(void *_entry, const void *_key, uint32 range) { arp_entry *entry = (arp_entry *)_entry; - in_addr_t key = (in_addr_t)_key; + const in_addr_t *key = (const in_addr_t *)_key; // TODO: check if this makes a good hash... -#define HASH(o) (((o >> 24) ^ (o >> 16) ^ (o >> 8) ^ o) % range) +#define HASH(o) ((((o) >> 24) ^ ((o) >> 16) ^ ((o) >> 8) ^ (o)) % range) #ifdef TRACE_ARP - in_addr_t a = entry ? entry->protocol_address : key; + in_addr_t a = entry ? entry->protocol_address : *key; dprintf("%ld.%ld.%ld.%ld: Hash: %lu\n", a >> 24, (a >> 16) & 0xff, (a >> 8) & 0xff, a & 0xff, HASH(a)); #endif @@ -136,7 +148,7 @@ if (entry != NULL) return HASH(entry->protocol_address); - return HASH(key); + return HASH(*key); #undef HASH } @@ -144,7 +156,7 @@ /*static*/ arp_entry * arp_entry::Lookup(in_addr_t address) { - return (arp_entry *)hash_lookup(sCache, (void *)address); + return (arp_entry *)hash_lookup(sCache, &address); } @@ -168,18 +180,9 @@ // this entry is already resolved entry->hardware_address = *hardwareAddress; entry->hardware_address.sdl_e_type = ETHER_TYPE_IP; - entry->resolved_sem = -1; } else { // this entry still needs to be resolved entry->hardware_address.sdl_alen = 0; - - char name[32]; - snprintf(name, sizeof(name), "arp %08lx", protocolAddress); - entry->resolved_sem = create_sem(0, name); - if (entry->resolved_sem < B_OK) { - delete entry; - return NULL; - } } if (entry->hardware_address.sdl_len != sizeof(sockaddr_dl)) { // explicitly set correct length in case our caller hasn't... @@ -195,6 +198,55 @@ } +arp_entry::~arp_entry() +{ + ClearQueue(); +} + + +void +arp_entry::ClearQueue() +{ + BufferList::Iterator iterator = queue.GetIterator(); + while (iterator.HasNext()) { + gBufferModule->free(iterator.Next()); + iterator.Remove(); + } +} + + +void +arp_entry::MarkFailed() +{ + TRACE(("ARP entry %p Marked as FAILED\n", this)); + + flags = (flags & ~ARP_FLAG_VALID) | ARP_FLAG_REJECT; + ClearQueue(); +} + + +void +arp_entry::MarkValid() +{ + TRACE(("ARP entry %p Marked as VALID, have %li packets queued.\n", this, + queue.Size())); + + flags = (flags & ~ARP_FLAG_REJECT) | ARP_FLAG_VALID; + + BufferList::Iterator iterator = queue.GetIterator(); + while (iterator.HasNext()) { + net_buffer *buffer = iterator.Next(); + iterator.Remove(); + + TRACE((" ARP Dequeing packet %p...\n", buffer)); + + memcpy(&buffer->destination, &hardware_address, + hardware_address.sdl_len); + protocol->next->module->send_data(protocol->next, buffer); + } +} + + // #pragma mark - @@ -237,12 +289,6 @@ return B_NO_MEMORY; } - // if someone was waiting for this ARP request to be resolved - if (entry->resolved_sem >= B_OK) { - delete_sem(entry->resolved_sem); - entry->resolved_sem = -1; - } - if (entry->request_buffer != NULL) { gBufferModule->free(entry->request_buffer); entry->request_buffer = NULL; @@ -254,6 +300,11 @@ sStackModule->set_timer(&entry->timer, ARP_STALE_TIMEOUT); } + if (entry->flags & ARP_FLAG_REJECT) + entry->MarkFailed(); + else + entry->MarkValid(); + if (_entry) *_entry = entry; @@ -424,7 +475,7 @@ // so that we won't try to request the same address again too soon. TRACE((" requesting ARP entry %p failed!\n", entry)); entry->timer_state = ARP_STATE_REMOVE_FAILED; - entry->flags |= ARP_FLAG_REJECT; + entry->MarkFailed(); sStackModule->set_timer(&entry->timer, ARP_REJECT_TIMEOUT); break; @@ -476,59 +527,13 @@ /*! - Checks if the ARP \a entry has already been resolved. If it wasn't yet, - and MSG_DONTWAIT is not set in \a flags, it will wait for the entry to - become resolved. - You need to have the sCacheLock held when calling this function - but - note that the lock may be interrupted (in which case entry is updated). -*/ -static status_t -arp_check_resolved(arp_entry **_entry, uint32 flags) -{ - arp_entry *entry = *_entry; - - if ((entry->flags & ARP_FLAG_REJECT) != 0) - return EHOSTUNREACH; - - if (entry->resolved_sem < B_OK) - return B_OK; - - // we need to wait for this entry to become resolved - - if ((flags & MSG_DONTWAIT) != 0) - return B_ERROR; - - // store information we cannot access anymore after having unlocked the cache - sem_id waitSem = entry->resolved_sem; - in_addr_t address = entry->protocol_address; - - benaphore_unlock(&sCacheLock); - - status_t status = acquire_sem_etc(waitSem, 1, B_RELATIVE_TIMEOUT, 5 * 1000000); - - benaphore_lock(&sCacheLock); - - if (status == B_TIMED_OUT) - return EHOSTUNREACH; - - // retrieve the entry again, as we reacquired the cache lock - entry = arp_entry::Lookup(address); - if (entry == NULL) - return B_ERROR; - - *_entry = entry; - return B_OK; -} - - -/*! Address resolver function: prepares and sends the ARP request necessary to retrieve the hardware address for \a address. You need to have the sCacheLock held when calling this function - but note that the lock will be interrupted here if everything goes well. */ static status_t -arp_resolve(net_datalink_protocol *protocol, in_addr_t address, arp_entry **_entry) +arp_start_resolve(net_datalink_protocol *protocol, in_addr_t address, arp_entry **_entry) { // create an unresolved ARP entry as a placeholder arp_entry *entry = arp_entry::Add(address, NULL, 0); @@ -590,26 +595,6 @@ sStackModule->set_timer(&entry->timer, 0); // start request timer - sem_id waitSem = entry->resolved_sem; - benaphore_unlock(&sCacheLock); - - status = acquire_sem_etc(waitSem, 1, B_RELATIVE_TIMEOUT, 5 * 1000000); - // wait for the entry to become resolved - - benaphore_lock(&sCacheLock); - - // retrieve the entry again, as we reacquired the cache lock - entry = arp_entry::Lookup(address); - if (entry == NULL) - return B_ERROR; - - if (status == B_TIMED_OUT) { - // we didn't get a response, mark ARP entry as non-existant - entry->flags = ARP_FLAG_REJECT; - // TODO: remove the ARP entry after some time - return EHOSTUNREACH; - } - *_entry = entry; return B_OK; } @@ -646,7 +631,7 @@ case ARP_GET_ENTRY: { arp_entry *entry = arp_entry::Lookup(control.address); - if (entry == NULL || entry->resolved_sem < B_OK) + if (entry == NULL || !(entry->flags & ARP_FLAG_VALID)) return B_ENTRY_NOT_FOUND; memcpy(control.ethernet_address, entry->hardware_address.sdl_data, @@ -683,7 +668,7 @@ case ARP_DELETE_ENTRY: { arp_entry *entry = arp_entry::Lookup(control.address); - if (entry == NULL || entry->resolved_sem < B_OK) + if (entry == NULL) return B_ENTRY_NOT_FOUND; if ((entry->flags & ARP_FLAG_LOCAL) != 0) return B_BAD_VALUE; @@ -832,25 +817,22 @@ entry = arp_entry::Lookup( ((struct sockaddr_in *)&buffer->destination)->sin_addr.s_addr); if (entry == NULL) { - // The ARP entry does not yet exist, if we're allowed to wait, - // we'll send an ARP request and try to change that. - if ((buffer->flags & MSG_DONTWAIT) != 0) { - // TODO: implement delaying packet send after ARP response! - return B_ERROR; - } - - status_t status = arp_resolve(protocol, + status_t status = arp_start_resolve(protocol, ((struct sockaddr_in *)&buffer->destination)->sin_addr.s_addr, &entry); if (status < B_OK) return status; - } else { - // The entry exists, but we have to check if it has already been - // resolved and is valid. - status_t status = arp_check_resolved(&entry, buffer->flags); - if (status < B_OK) - return status; } + if (entry->flags & ARP_FLAG_REJECT) + return EHOSTUNREACH; + else if (!(entry->flags & ARP_FLAG_VALID)) { + // entry is still being resolved. + TRACE(("ARP Queuing packet %p, entry still being resolved.\n", + buffer)); + entry->queue.Add(buffer); + return B_OK; + } + memcpy(&buffer->destination, &entry->hardware_address, entry->hardware_address.sdl_len); } @@ -896,7 +878,7 @@ } } - protocol->next->module->interface_down(protocol->next); + protocol->next->module->interface_down(protocol->next); } From hugosantos at mail.berlios.de Sun Apr 15 23:00:41 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Sun, 15 Apr 2007 23:00:41 +0200 Subject: [Haiku-commits] r20713 - haiku/trunk/src/bin/network/arp Message-ID: <200704152100.l3FL0foW020005@sheep.berlios.de> Author: hugosantos Date: 2007-04-15 23:00:32 +0200 (Sun, 15 Apr 2007) New Revision: 20713 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20713&view=rev Modified: haiku/trunk/src/bin/network/arp/arp.cpp Log: print the new 'active' flag in arp entries Modified: haiku/trunk/src/bin/network/arp/arp.cpp =================================================================== --- haiku/trunk/src/bin/network/arp/arp.cpp 2007-04-15 21:00:12 UTC (rev 20712) +++ haiku/trunk/src/bin/network/arp/arp.cpp 2007-04-15 21:00:32 UTC (rev 20713) @@ -170,6 +170,7 @@ {ARP_FLAG_LOCAL, "local"}, {ARP_FLAG_PUBLISH, "publish"}, {ARP_FLAG_REJECT, "reject"}, + {ARP_FLAG_VALID, "valid"}, }; bool first = true; From hugosantos at mail.berlios.de Mon Apr 16 00:11:32 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Mon, 16 Apr 2007 00:11:32 +0200 Subject: [Haiku-commits] r20714 - in haiku/trunk: headers/private/net src/add-ons/kernel/network/protocols/ipv4 src/add-ons/kernel/network/protocols/udp src/add-ons/kernel/network/stack Message-ID: <200704152211.l3FMBWv5003863@sheep.berlios.de> Author: hugosantos Date: 2007-04-16 00:11:12 +0200 (Mon, 16 Apr 2007) New Revision: 20714 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20714&view=rev Modified: haiku/trunk/headers/private/net/net_datalink.h haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp Log: introduced datalink's send_datagram to perform route and source address selection and dispatch the datagram to appropriate domain/protocol. Modified: haiku/trunk/headers/private/net/net_datalink.h =================================================================== --- haiku/trunk/headers/private/net/net_datalink.h 2007-04-15 21:00:32 UTC (rev 20713) +++ haiku/trunk/headers/private/net/net_datalink.h 2007-04-15 22:11:12 UTC (rev 20714) @@ -66,10 +66,12 @@ status_t (*control)(struct net_domain *domain, int32 option, void *value, size_t *_length); status_t (*send_data)(struct net_route *route, struct net_buffer *buffer); + status_t (*send_datagram)(struct net_protocol *protocol, + struct net_domain *domain, struct net_buffer *buffer); - bool (*is_local_address)(struct net_domain *domain, + bool (*is_local_address)(struct net_domain *domain, const struct sockaddr *address, - net_interface **_interface, + net_interface **_interface, uint32 *_matchedType); net_interface *(*get_interface)(struct net_domain *domain, uint32 index); net_interface *(*get_interface_with_address)(struct net_domain *domain, Modified: haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp 2007-04-15 21:00:32 UTC (rev 20713) +++ haiku/trunk/src/add-ons/kernel/network/protocols/ipv4/ipv4.cpp 2007-04-15 22:11:12 UTC (rev 20714) @@ -1353,34 +1353,20 @@ TRACE_SK(protocol, "SendData(%p [%ld bytes])", buffer, buffer->size); - if (protocol) { - if (protocol->flags & IP_FLAG_HEADER_INCLUDED) { - if (buffer->size < sizeof(ipv4_header)) - return EINVAL; + if (protocol && (protocol->flags & IP_FLAG_HEADER_INCLUDED)) { + if (buffer->size < sizeof(ipv4_header)) + return EINVAL; - sockaddr_in *source = (sockaddr_in *)&buffer->source; - sockaddr_in *destination = (sockaddr_in *)&buffer->destination; + sockaddr_in *source = (sockaddr_in *)&buffer->source; + sockaddr_in *destination = (sockaddr_in *)&buffer->destination; - fill_sockaddr_in(source, *NetBufferField(buffer)); - fill_sockaddr_in(destination, *NetBufferField(buffer)); - } + fill_sockaddr_in(source, *NetBufferField(buffer)); + fill_sockaddr_in(destination, *NetBufferField(buffer)); } - net_route *route = NULL; - status_t status = sDatalinkModule->get_buffer_route(sDomain, buffer, - &route); - if (status >= B_OK) { - if (protocol) - status = protocol->socket->first_protocol->module->send_routed_data( - protocol->socket->first_protocol, route, buffer); - else - status = ipv4_send_routed_data(NULL, route, buffer); - sDatalinkModule->put_route(sDomain, route); - } - - return status; + return sDatalinkModule->send_datagram(protocol, sDomain, buffer); } Modified: haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp 2007-04-15 21:00:32 UTC (rev 20713) +++ haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp 2007-04-15 22:11:12 UTC (rev 20714) @@ -911,10 +911,7 @@ { TRACE_EP("SendData(%p [%lu bytes])", buffer, buffer->size); - // This will call into IPv4 which will do all of the obtaining - // routes and other datagram related dirty work and eventually - // call back into our send_routed_data. - return next->module->send_data(next, buffer); + return gDatalinkModule->send_datagram(this, NULL, buffer); } Modified: haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp 2007-04-15 21:00:32 UTC (rev 20713) +++ haiku/trunk/src/add-ons/kernel/network/stack/datalink.cpp 2007-04-15 22:11:12 UTC (rev 20714) @@ -362,6 +362,30 @@ } +status_t +datalink_send_datagram(net_protocol *protocol, net_domain *domain, + net_buffer *buffer) +{ + if (protocol == NULL && domain == NULL) + return B_BAD_VALUE; + + net_protocol_module_info *module = protocol ? protocol->module + : domain->module; + + if (domain == NULL) + domain = protocol->module->get_domain(protocol); + + net_route *route = NULL; + status_t status = get_buffer_route(domain, buffer, &route); + if (status < B_OK) + return status; + + status = module->send_routed_data(protocol, route, buffer); + put_route(domain, route); + return status; +} + + /*! Tests if \a address is a local address in the domain. \param _interface will be set to the interface belonging to that address @@ -784,6 +808,7 @@ datalink_control, datalink_send_data, + datalink_send_datagram, datalink_is_local_address, datalink_get_interface, datalink_get_interface_with_address, From marcusoverhagen at mail.berlios.de Mon Apr 16 00:25:18 2007 From: marcusoverhagen at mail.berlios.de (marcusoverhagen at BerliOS) Date: Mon, 16 Apr 2007 00:25:18 +0200 Subject: [Haiku-commits] r20715 - in haiku/trunk/src/add-ons/kernel/drivers: . dvb dvb/cx23882 Message-ID: <200704152225.l3FMPIvw006834@sheep.berlios.de> Author: marcusoverhagen Date: 2007-04-16 00:25:14 +0200 (Mon, 16 Apr 2007) New Revision: 20715 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20715&view=rev Added: haiku/trunk/src/add-ons/kernel/drivers/dvb/Jamfile haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/Jamfile Modified: haiku/trunk/src/add-ons/kernel/drivers/Jamfile haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/config.h haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/cx22702.c haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/cx22702.h haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/cx23882.h haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/cx23882_i2c.c haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/driver.c haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/dtt7592.c haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/dtt7592.h haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/dvb_interface.c haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/dvb_interface.h haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/i2c_core.c Log: Added Jamfiles, changed some includes. The driver now builds for Haiku. Modified: haiku/trunk/src/add-ons/kernel/drivers/Jamfile =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/Jamfile 2007-04-15 22:11:12 UTC (rev 20714) +++ haiku/trunk/src/add-ons/kernel/drivers/Jamfile 2007-04-15 22:25:14 UTC (rev 20715) @@ -5,6 +5,7 @@ SubInclude HAIKU_TOP src add-ons kernel drivers audio ; SubInclude HAIKU_TOP src add-ons kernel drivers common ; SubInclude HAIKU_TOP src add-ons kernel drivers disk ; +SubInclude HAIKU_TOP src add-ons kernel drivers dvb ; SubInclude HAIKU_TOP src add-ons kernel drivers input ; SubInclude HAIKU_TOP src add-ons kernel drivers graphics ; SubInclude HAIKU_TOP src add-ons kernel drivers midi ; Added: haiku/trunk/src/add-ons/kernel/drivers/dvb/Jamfile =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/dvb/Jamfile 2007-04-15 22:11:12 UTC (rev 20714) +++ haiku/trunk/src/add-ons/kernel/drivers/dvb/Jamfile 2007-04-15 22:25:14 UTC (rev 20715) @@ -0,0 +1,3 @@ +SubDir HAIKU_TOP src add-ons kernel drivers dvb ; + +SubInclude HAIKU_TOP src add-ons kernel drivers dvb cx23882 ; Added: haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/Jamfile =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/Jamfile 2007-04-15 22:11:12 UTC (rev 20714) +++ haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/Jamfile 2007-04-15 22:25:14 UTC (rev 20715) @@ -0,0 +1,15 @@ +SubDir HAIKU_TOP src add-ons kernel drivers dvb cx23882 ; + +UsePrivateHeaders drivers ; + +KernelAddon cx23882 : + cx22702.c + cx23882.c + cx23882_i2c.c + driver.c + dtt7592.c + dvb_interface.c + i2c_core.c + util.c +; + Modified: haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/config.h =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/config.h 2007-04-15 22:11:12 UTC (rev 20714) +++ haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/config.h 2007-04-15 22:25:14 UTC (rev 20715) @@ -25,10 +25,10 @@ #ifndef __CONFIG_H #define __CONFIG_H +#define REVISION "unknown" #define VERSION "1.0" #define BUILD __DATE__ " "__TIME__ -#define INFO1 "cx23882: DVB-T Driver. Version " VERSION ", Revision " REVISION ", Build " BUILD -#define INFO2 "cx23882: Copyright (c) 2004-2006 Marcus Overhagen. All rights reserved.\n" +#define INFO "cx23882: DVB-T Driver. Version " VERSION ", Revision " REVISION ", Build " BUILD "\n" #define MAX_CARDS 8 Modified: haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/cx22702.c =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/cx22702.c 2007-04-15 22:11:12 UTC (rev 20714) +++ haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/cx22702.c 2007-04-15 22:25:14 UTC (rev 20715) @@ -23,6 +23,7 @@ */ #include +#include #include "cx22702.h" #include "dtt7592.h" #include "config.h" @@ -36,6 +37,7 @@ #endif +#if 0 static void cx22702_reg_dump(i2c_bus *bus) { @@ -48,6 +50,7 @@ dprintf("cx22702_reg 0x%02x value 0x%02x\n", i, data); } } +#endif status_t Modified: haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/cx22702.h =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/cx22702.h 2007-04-15 22:11:12 UTC (rev 20714) +++ haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/cx22702.h 2007-04-15 22:25:14 UTC (rev 20715) @@ -25,7 +25,7 @@ #ifndef __CX22702_H #define __CX22702_H -#include "i2c-core.h" +#include "i2c_core.h" #include "dvb.h" status_t cx22702_reg_write(i2c_bus *bus, uint8 reg, uint8 data); Modified: haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/cx23882.h =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/cx23882.h 2007-04-15 22:11:12 UTC (rev 20714) +++ haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/cx23882.h 2007-04-15 22:25:14 UTC (rev 20715) @@ -28,7 +28,7 @@ #include #include "driver.h" #include "cx23882_regs.h" -#include "i2c-core.h" +#include "i2c_core.h" typedef struct { const pci_info * pci_info; Modified: haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/cx23882_i2c.c =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/cx23882_i2c.c 2007-04-15 22:11:12 UTC (rev 20714) +++ haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/cx23882_i2c.c 2007-04-15 22:25:14 UTC (rev 20715) @@ -22,8 +22,8 @@ * OTHER DEALINGS IN THE SOFTWARE. */ -#include "i2c.h" -#include "i2c-core.h" +#include "cx23882_i2c.h" +#include "i2c_core.h" static void Modified: haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/driver.c =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/driver.c 2007-04-15 22:11:12 UTC (rev 20714) +++ haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/driver.c 2007-04-15 22:25:14 UTC (rev 20715) @@ -29,10 +29,9 @@ #include #include -#include "version.h" #include "config.h" #include "driver.h" -#include "mktime.h" +#include "dvb_interface.h" #define TRACE_DRIVER #ifdef TRACE_DRIVER @@ -126,7 +125,7 @@ load_driver_symbols("cx23882"); #endif - dprintf(gBanner); + dprintf(INFO); item = (pci_info *)malloc(sizeof(pci_info)); if (!item) Modified: haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/dtt7592.c =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/dtt7592.c 2007-04-15 22:11:12 UTC (rev 20714) +++ haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/dtt7592.c 2007-04-15 22:25:14 UTC (rev 20715) @@ -131,6 +131,7 @@ } +#if 0 void dtt7582_dump(i2c_bus *bus) { @@ -163,6 +164,4 @@ dtt7592_set_frequency(bus, 333000000, DVB_BANDWIDTH_7_MHZ); dtt7582_dump(bus); } - - - +#endif Modified: haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/dtt7592.h =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/dtt7592.h 2007-04-15 22:11:12 UTC (rev 20714) +++ haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/dtt7592.h 2007-04-15 22:25:14 UTC (rev 20715) @@ -25,7 +25,7 @@ #ifndef __DTT7592_H #define __DTT7592_H -#include "i2c-core.h" +#include "i2c_core.h" #include "dvb.h" status_t dtt7592_write(i2c_bus *bus, const uint8 data[4]); Modified: haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/dvb_interface.c =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/dvb_interface.c 2007-04-15 22:11:12 UTC (rev 20714) +++ haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/dvb_interface.c 2007-04-15 22:25:14 UTC (rev 20715) @@ -24,14 +24,15 @@ #include #include -#include "interface.h" +#include +#include "dvb_interface.h" #include "cx23882.h" +#include "cx23882_i2c.h" #include "cx22702.h" #include "dtt7592.h" #include "driver.h" #include "config.h" #include "util.h" -#include "i2c.h" #define TRACE_INTERFACE #ifdef TRACE_INTERFACE @@ -40,9 +41,8 @@ #define TRACE(a...) #endif -static inline status_t user_memcpy(void *d, const void *s, size_t z) { memcpy(d, s, z); return B_OK; } -#define B_BAD_ADDRESS B_ERROR +#if 0 static void dump_eeprom(cx23882_device *device) { @@ -62,6 +62,7 @@ TRACE("EEPROM %02x: %02x %02x %02x %02x %02x %02x %02x %02x\n", i * 8, p[0], p[1], p[2], p[3], p[4], p[5], p[6], p[7]); } +#endif status_t Modified: haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/dvb_interface.h =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/dvb_interface.h 2007-04-15 22:11:12 UTC (rev 20714) +++ haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/dvb_interface.h 2007-04-15 22:25:14 UTC (rev 20715) @@ -25,6 +25,8 @@ #ifndef __DVB_INTERFACE_H #define __DVB_INTERFACE_H +#include + status_t interface_attach(void **cookie, const pci_info *info); void interface_detach(void *cookie); status_t interface_ioctl(void *cookie, uint32 op, void *arg, size_t len); Modified: haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/i2c_core.c =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/i2c_core.c 2007-04-15 22:11:12 UTC (rev 20714) +++ haiku/trunk/src/add-ons/kernel/drivers/dvb/cx23882/i2c_core.c 2007-04-15 22:25:14 UTC (rev 20715) @@ -25,7 +25,7 @@ #include #include #include -#include "i2c-core.h" +#include "i2c_core.h" #define TRACE_I2C #ifdef TRACE_I2C From marcusoverhagen at mail.berlios.de Mon Apr 16 00:44:39 2007 From: marcusoverhagen at mail.berlios.de (marcusoverhagen at BerliOS) Date: Mon, 16 Apr 2007 00:44:39 +0200 Subject: [Haiku-commits] r20716 - haiku/trunk/build/jam Message-ID: <200704152244.l3FMidHY002884@sheep.berlios.de> Author: marcusoverhagen Date: 2007-04-16 00:44:37 +0200 (Mon, 16 Apr 2007) New Revision: 20716 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20716&view=rev Modified: haiku/trunk/build/jam/HaikuImage Log: integrate DVB-T driver into haiku-image Modified: haiku/trunk/build/jam/HaikuImage =================================================================== --- haiku/trunk/build/jam/HaikuImage 2007-04-15 22:25:14 UTC (rev 20715) +++ haiku/trunk/build/jam/HaikuImage 2007-04-15 22:44:37 UTC (rev 20716) @@ -147,6 +147,7 @@ AddDriversToHaikuImage midi : $(BEOS_ADD_ONS_DRIVERS_MIDI) ; AddDriversToHaikuImage bus : usb_raw ; AddDriversToHaikuImage disk scsi : scsi_cd scsi_dsk ; +AddDriversToHaikuImage dvb : cx23882 ; AddDriversToHaikuImage graphics : $(BEOS_ADD_ONS_DRIVERS_GRAPHICS) ; AddDriversToHaikuImage input : ps2_hid usb_hid ; AddDriversToHaikuImage misc : poke ; From hugosantos at mail.berlios.de Mon Apr 16 01:18:45 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Mon, 16 Apr 2007 01:18:45 +0200 Subject: [Haiku-commits] r20717 - in haiku/trunk: headers/private/net src/add-ons/kernel/network/protocols/tcp src/add-ons/kernel/network/protocols/udp Message-ID: <200704152318.l3FNIjZo011454@sheep.berlios.de> Author: hugosantos Date: 2007-04-16 01:18:15 +0200 (Mon, 16 Apr 2007) New Revision: 20717 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20717&view=rev Modified: haiku/trunk/headers/private/net/NetUtilities.h haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.cpp haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp Log: introduced Checksum::PseudoHeader helper. Modified: haiku/trunk/headers/private/net/NetUtilities.h =================================================================== --- haiku/trunk/headers/private/net/NetUtilities.h 2007-04-15 22:44:37 UTC (rev 20716) +++ haiku/trunk/headers/private/net/NetUtilities.h 2007-04-15 23:18:15 UTC (rev 20717) @@ -9,6 +9,8 @@ #include #include +#include // for htons + #include class Checksum { @@ -32,6 +34,10 @@ operator uint16(); + static uint16 PseudoHeader(net_address_module_info *addressModule, + net_buffer_module_info *bufferModule, net_buffer *buffer, + uint16 protocol); + private: uint32 fSum; }; @@ -77,6 +83,19 @@ } +inline uint16 +Checksum::PseudoHeader(net_address_module_info *addressModule, + net_buffer_module_info *bufferModule, net_buffer *buffer, uint16 protocol) +{ + Checksum checksum; + addressModule->checksum_address(&checksum, (sockaddr *)&buffer->source); + addressModule->checksum_address(&checksum, (sockaddr *)&buffer->destination); + checksum << (uint16)htons(protocol) << (uint16)htons(buffer->size) + << Checksum::BufferHelper(buffer, bufferModule); + return checksum; +} + + // helper class that prints an address (and optionally a port) into a buffer that // is automatically freed at end of scope: class AddressString { Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.cpp 2007-04-15 22:44:37 UTC (rev 20716) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.cpp 2007-04-15 23:18:15 UTC (rev 20717) @@ -161,17 +161,9 @@ TRACE(("add_tcp_header(): buffer %p, flags 0x%x, seq %lu, ack %lu, win %u\n", buffer, segment.flags, segment.sequence, segment.acknowledge, segment.advertised_window)); - // compute and store checksum - Checksum checksum; - gAddressModule->checksum_address(&checksum, (sockaddr *)&buffer->source); - gAddressModule->checksum_address(&checksum, (sockaddr *)&buffer->destination); - checksum - << (uint16)htons(IPPROTO_TCP) - << (uint16)htons(buffer->size) - << Checksum::BufferHelper(buffer, gBufferModule); + *TCPChecksumField(buffer) = Checksum::PseudoHeader(gAddressModule, + gBufferModule, buffer, IPPROTO_TCP); - *TCPChecksumField(buffer) = checksum; - return B_OK; } @@ -518,15 +510,8 @@ if (headerLength < sizeof(tcp_header)) return B_BAD_DATA; - // compute checksum using a pseudo IP header - Checksum checksum; - gAddressModule->checksum_address(&checksum, (sockaddr *)&buffer->source); - gAddressModule->checksum_address(&checksum, (sockaddr *)&buffer->destination); - checksum << (uint16)htons(IPPROTO_TCP) - << (uint16)htons(buffer->size) - << Checksum::BufferHelper(buffer, gBufferModule); - - if (checksum != 0) + if (Checksum::PseudoHeader(gAddressModule, gBufferModule, buffer, + IPPROTO_TCP) != 0) return B_BAD_DATA; gAddressModule->set_port((struct sockaddr *)&buffer->source, header.source_port); Modified: haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp 2007-04-15 22:44:37 UTC (rev 20716) +++ haiku/trunk/src/add-ons/kernel/network/protocols/udp/udp.cpp 2007-04-15 23:18:15 UTC (rev 20717) @@ -617,16 +617,8 @@ if (header.udp_checksum != 0) { // check UDP-checksum (simulating a so-called "pseudo-header"): - Checksum udpChecksum; - addressModule->checksum_address(&udpChecksum, source); - addressModule->checksum_address(&udpChecksum, destination); - udpChecksum - << (uint16)htons(IPPROTO_UDP) - << header.udp_length - // peculiar but correct: UDP-len is used twice for checksum - // (as it is already contained in udp_header) - << Checksum::BufferHelper(buffer, gBufferModule); - uint16 sum = udpChecksum; + uint16 sum = Checksum::PseudoHeader(addressModule, gBufferModule, + buffer, IPPROTO_UDP); if (sum != 0) { TRACE_EPM(" Deframe(): bad checksum 0x%hx.", sum); return B_BAD_VALUE; @@ -881,20 +873,8 @@ header.Sync(); - // generate UDP-checksum (simulating a so-called "pseudo-header"): - Checksum udpChecksum; - AddressModule()->checksum_address(&udpChecksum, - (sockaddr *)route->interface->address); - AddressModule()->checksum_address(&udpChecksum, - (sockaddr *)&buffer->destination); - udpChecksum - << (uint16)htons(IPPROTO_UDP) - << (uint16)htons(buffer->size) - // peculiar but correct: UDP-len is used twice for checksum - // (as it is already contained in udp_header) - << Checksum::BufferHelper(buffer, gBufferModule); - - uint16 calculatedChecksum = udpChecksum; + uint16 calculatedChecksum = Checksum::PseudoHeader(AddressModule(), + gBufferModule, buffer, IPPROTO_UDP); if (calculatedChecksum == 0) calculatedChecksum = 0xffff; From hugosantos at mail.berlios.de Mon Apr 16 02:28:02 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Mon, 16 Apr 2007 02:28:02 +0200 Subject: [Haiku-commits] r20718 - haiku/trunk/src/add-ons/kernel/network/protocols/tcp Message-ID: <200704160028.l3G0S2w6000993@sheep.berlios.de> Author: hugosantos Date: 2007-04-16 02:27:39 +0200 (Mon, 16 Apr 2007) New Revision: 20718 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20718&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/EndpointManager.cpp haiku/trunk/src/add-ons/kernel/network/protocols/tcp/EndpointManager.h haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.cpp haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.h Log: made TCP handle multiple domains. Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/EndpointManager.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/EndpointManager.cpp 2007-04-15 23:18:15 UTC (rev 20717) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/EndpointManager.cpp 2007-04-16 00:27:39 UTC (rev 20718) @@ -26,6 +26,7 @@ struct connection_key { + net_address_module_info *address_module; const sockaddr *local; const sockaddr *peer; }; @@ -42,7 +43,8 @@ static const uint16 kFirstEphemeralPort = 40000; -EndpointManager::EndpointManager() +EndpointManager::EndpointManager(net_domain *domain) + : fDomain(domain) { fConnectionHash = hash_init(kConnectionHashBuckets, offsetof(TCPEndpoint, fConnectionHashNext), @@ -89,6 +91,7 @@ EndpointManager::_LookupConnection(sockaddr *local, sockaddr *peer) { connection_key key; + key.address_module = AddressModule(); key.local = local; key.peer = peer; @@ -109,9 +112,6 @@ { RecursiveLocker lock(&fLock); - if (gDomain == NULL) - return; - struct hash_iterator iterator; hash_open(fConnectionHash, &iterator); @@ -120,8 +120,8 @@ TCPEndpoint *endpoint; while ((endpoint = (TCPEndpoint *)hash_next(fConnectionHash, &iterator)) != NULL) { TRACE((" TCPEndpoint %p: local %s, peer %s\n", endpoint, - AddressString(gDomain, (sockaddr *)&endpoint->socket->address, true).Data(), - AddressString(gDomain, (sockaddr *)&endpoint->socket->peer, true).Data())); + AddressString(Domain(), (sockaddr *)&endpoint->socket->address, true).Data(), + AddressString(Domain(), (sockaddr *)&endpoint->socket->peer, true).Data())); } hash_close(fConnectionHash, &iterator, false); @@ -138,13 +138,14 @@ sockaddr localBuffer; // need to associate this connection with a real address, not INADDR_ANY - if (gAddressModule->is_empty_address(local, false)) { - gAddressModule->set_to(&localBuffer, interfaceLocal); - gAddressModule->set_port(&localBuffer, gAddressModule->get_port(local)); + if (AddressModule()->is_empty_address(local, false)) { + AddressModule()->set_to(&localBuffer, interfaceLocal); + AddressModule()->set_port(&localBuffer, AddressModule()->get_port(local)); local = &localBuffer; } connection_key key; + key.address_module = AddressModule(); key.local = local; key.peer = peer; @@ -153,8 +154,8 @@ _RemoveConnection(endpoint); - gAddressModule->set_to((sockaddr *)&endpoint->socket->address, local); - gAddressModule->set_to((sockaddr *)&endpoint->socket->peer, peer); + AddressModule()->set_to((sockaddr *)&endpoint->socket->address, local); + AddressModule()->set_to((sockaddr *)&endpoint->socket->peer, peer); return hash_insert(fConnectionHash, endpoint); } @@ -172,7 +173,7 @@ // no explicit endpoint exists, check for wildcard endpoints sockaddr wildcard; - gAddressModule->set_to_empty_address(&wildcard); + AddressModule()->set_to_empty_address(&wildcard); endpoint = _LookupConnection(local, &wildcard); if (endpoint != NULL) { @@ -181,8 +182,8 @@ } sockaddr localWildcard; - gAddressModule->set_to_empty_address(&localWildcard); - gAddressModule->set_port(&localWildcard, gAddressModule->get_port(local)); + AddressModule()->set_to_empty_address(&localWildcard); + AddressModule()->set_port(&localWildcard, AddressModule()->get_port(local)); endpoint = _LookupConnection(&localWildcard, &wildcard); if (endpoint != NULL) { @@ -217,12 +218,12 @@ sockaddr *address = (sockaddr *)&endpoint->socket->address; TRACE(("EndpointManager::Bind(%p, %s)\n", endpoint, - AddressString(gDomain, address, true).Data())); + AddressString(Domain(), address, true).Data())); - if (gAddressModule->is_empty_address(address, true)) + if (AddressModule()->is_empty_address(address, true)) return B_BAD_VALUE; - uint16 port = gAddressModule->get_port(address); + uint16 port = AddressModule()->get_port(address); // TODO: check the root group instead? if (ntohs(port) <= kLastReservedPort && geteuid() != 0) @@ -245,7 +246,7 @@ TCPEndpoint *last = first; while (true) { // check if this endpoint binds to a wildcard address - if (gAddressModule->is_empty_address((sockaddr *)&last->socket->address, false)) { + if (AddressModule()->is_empty_address((sockaddr *)&last->socket->address, false)) { // you cannot specialize a wildcard endpoint - you have to open the // wildcard endpoint last return B_PERMISSION_DENIED; @@ -293,9 +294,9 @@ TCPEndpoint *other = _LookupEndpoint(port); if (other == NULL) { // found a port - gAddressModule->set_port((sockaddr *)&endpoint->socket->address, port); + AddressModule()->set_port((sockaddr *)&endpoint->socket->address, port); TRACE((" EndpointManager::BindToEphemeral(%p) -> %s\n", endpoint, - AddressString(gDomain, (sockaddr *)&endpoint->socket->address, true).Data())); + AddressString(Domain(), (sockaddr *)&endpoint->socket->address, true).Data())); endpoint->fEndpointNextWithSamePort = NULL; hash_insert(fEndpointHash, endpoint); hash_insert(fConnectionHash, endpoint); @@ -320,7 +321,7 @@ RecursiveLocker locker(&fLock); if (!endpoint->fSpawned) { - TCPEndpoint *other = _LookupEndpoint(gAddressModule->get_port( + TCPEndpoint *other = _LookupEndpoint(AddressModule()->get_port( (sockaddr *)&endpoint->socket->address)); if (other != endpoint) { // remove endpoint from the list of endpoints with the same port @@ -351,6 +352,45 @@ } +status_t +EndpointManager::ReplyWithReset(tcp_segment_header &segment, + net_buffer *buffer) +{ + TRACE(("TCP: Sending RST...\n")); + + net_buffer *reply = gBufferModule->create(512); + if (reply == NULL) + return B_NO_MEMORY; + + AddressModule()->set_to((sockaddr *)&reply->source, + (sockaddr *)&buffer->destination); + AddressModule()->set_to((sockaddr *)&reply->destination, + (sockaddr *)&buffer->source); + + tcp_segment_header outSegment; + outSegment.flags = TCP_FLAG_RESET; + outSegment.sequence = 0; + outSegment.acknowledge = 0; + outSegment.advertised_window = 0; + outSegment.urgent_offset = 0; + + if ((segment.flags & TCP_FLAG_ACKNOWLEDGE) == 0) { + outSegment.flags |= TCP_FLAG_ACKNOWLEDGE; + outSegment.acknowledge = segment.sequence + buffer->size; + } else + outSegment.sequence = segment.acknowledge; + + status_t status = add_tcp_header(AddressModule(), outSegment, reply); + if (status == B_OK) + status = Domain()->module->send_data(NULL, reply); + + if (status != B_OK) + gBufferModule->free(reply); + + return status; +} + + // #pragma mark - hash functions @@ -360,9 +400,9 @@ const connection_key *key = (connection_key *)_key; TCPEndpoint *endpoint = (TCPEndpoint *)_endpoint; - if (gAddressModule->equal_addresses_and_ports(key->local, + if (key->address_module->equal_addresses_and_ports(key->local, (sockaddr *)&endpoint->socket->address) - && gAddressModule->equal_addresses_and_ports(key->peer, + && key->address_module->equal_addresses_and_ports(key->peer, (sockaddr *)&endpoint->socket->peer)) return 0; @@ -373,20 +413,23 @@ /*static*/ uint32 EndpointManager::_ConnectionHash(void *_endpoint, const void *_key, uint32 range) { + net_address_module_info *address_module; const sockaddr *local; const sockaddr *peer; if (_endpoint != NULL) { TCPEndpoint *endpoint = (TCPEndpoint *)_endpoint; + address_module = endpoint->AddressModule(); local = (sockaddr *)&endpoint->socket->address; peer = (sockaddr *)&endpoint->socket->peer; } else { const connection_key *key = (connection_key *)_key; + address_module = key->address_module; local = key->local; peer = key->peer; } - return gAddressModule->hash_address_pair(local, peer) % range; + return address_module->hash_address_pair(local, peer) % range; } @@ -396,8 +439,8 @@ const endpoint_key *key = (endpoint_key *)_key; TCPEndpoint *endpoint = (TCPEndpoint *)_endpoint; - return gAddressModule->get_port((sockaddr *)&endpoint->socket->address) - == key->port ? 0 : 1; + return endpoint->AddressModule()->get_port( + (sockaddr *)&endpoint->socket->address) == key->port ? 0 : 1; } @@ -406,7 +449,8 @@ { if (_endpoint != NULL) { TCPEndpoint *endpoint = (TCPEndpoint *)_endpoint; - return gAddressModule->get_port((sockaddr *)&endpoint->socket->address) % range; + return endpoint->AddressModule()->get_port( + (sockaddr *)&endpoint->socket->address) % range; } const endpoint_key *key = (endpoint_key *)_key; Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/EndpointManager.h =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/EndpointManager.h 2007-04-15 23:18:15 UTC (rev 20717) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/EndpointManager.h 2007-04-16 00:27:39 UTC (rev 20718) @@ -8,18 +8,24 @@ #ifndef ENDPOINT_MANAGER_H #define ENDPOINT_MANAGER_H +#include "tcp.h" +#include + #include +#include #include #include +struct net_address_module_info; +struct net_domain; class TCPEndpoint; -class EndpointManager { +class EndpointManager : public DoublyLinkedListLinkImpl { public: - EndpointManager(); + EndpointManager(net_domain *domain); ~EndpointManager(); status_t InitCheck() const; @@ -34,6 +40,13 @@ status_t BindToEphemeral(TCPEndpoint *endpoint); status_t Unbind(TCPEndpoint *endpoint); + status_t ReplyWithReset(tcp_segment_header &segment, + net_buffer *buffer); + + net_domain *Domain() const { return fDomain; } + net_address_module_info *AddressModule() const + { return Domain()->address_module; } + private: TCPEndpoint *_LookupConnection(sockaddr *local, sockaddr *peer); status_t _RemoveConnection(TCPEndpoint *endpoint); @@ -45,6 +58,8 @@ static int _EndpointCompare(void *_endpoint, const void *_key); static uint32 _EndpointHash(void *_endpoint, const void *_key, uint32 range); + net_domain *fDomain; + hash_table *fConnectionHash; hash_table *fEndpointHash; recursive_lock fLock; Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-15 23:18:15 UTC (rev 20717) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-16 00:27:39 UTC (rev 20718) @@ -158,6 +158,7 @@ TCPEndpoint::TCPEndpoint(net_socket *socket) : + fManager(NULL), fReceiveList("tcp receive"), fSendList("tcp send"), fOptions(0), @@ -205,7 +206,10 @@ gStackModule->cancel_timer(&fDelayedAcknowledgeTimer); gStackModule->cancel_timer(&fTimeWaitTimer); - gEndpointManager->Unbind(this); + if (fManager) { + fManager->Unbind(this); + return_endpoint_manager(fManager); + } recursive_lock_destroy(&fLock); } @@ -234,7 +238,14 @@ TCPEndpoint::Open() { TRACE("Open()"); - // nothing to do here... + + if (Domain() == NULL || AddressModule() == NULL) + return EAFNOSUPPORT; + + fManager = create_endpoint_manager(Domain()); + if (fManager == NULL) + return EAFNOSUPPORT; + return B_OK; } @@ -304,7 +315,7 @@ TCPEndpoint::Connect(const struct sockaddr *address) { TRACE("Connect() on address %s", - AddressString(gDomain, address, true).Data()); + AddressString(Domain(), address, true).Data()); RecursiveLocker locker(&fLock); @@ -319,14 +330,14 @@ // get a net_route if there isn't one // TODO: get a net_route_info instead! if (fRoute == NULL) { - fRoute = gDatalinkModule->get_route(gDomain, (sockaddr *)address); + fRoute = gDatalinkModule->get_route(Domain(), (sockaddr *)address); TRACE(" Connect(): Using Route %p", fRoute); if (fRoute == NULL) return ENETUNREACH; } // make sure connection does not already exist - status_t status = gEndpointManager->SetConnection(this, + status_t status = fManager->SetConnection(this, (sockaddr *)&socket->address, address, fRoute->interface->address); if (status < B_OK) { TRACE(" Connect(): could not add connection: %s!", strerror(status)); @@ -413,7 +424,7 @@ return B_BAD_VALUE; TRACE("Bind() on address %s", - AddressString(gDomain, address, true).Data()); + AddressString(Domain(), address, true).Data()); RecursiveLocker lock(fLock); @@ -425,13 +436,13 @@ if (status < B_OK) return status; - if (gAddressModule->get_port(address) == 0) - status = gEndpointManager->BindToEphemeral(this); + if (AddressModule()->get_port(address) == 0) + status = fManager->BindToEphemeral(this); else - status = gEndpointManager->Bind(this); + status = fManager->Bind(this); TRACE(" Bind() bound to %s (status %i)", - AddressString(gDomain, (sockaddr *)&socket->address, true).Data(), + AddressString(Domain(), (sockaddr *)&socket->address, true).Data(), (int)status); return status; @@ -444,7 +455,7 @@ TRACE("Unbind()"); RecursiveLocker lock(fLock); - return gEndpointManager->Unbind(this); + return fManager->Unbind(this); } @@ -646,10 +657,18 @@ bool TCPEndpoint::IsBound() const { - return !gAddressModule->is_empty_address((sockaddr *)&socket->address, true); + return !AddressModule()->is_empty_address((sockaddr *)&socket->address, true); } +void +TCPEndpoint::DeleteSocket() +{ + // the next call will delete `this'. + gSocketModule->delete_socket(socket); +} + + status_t TCPEndpoint::DelayedAcknowledge() { @@ -723,9 +742,9 @@ if (gSocketModule->spawn_pending_socket(socket, &newSocket) < B_OK) return DROP; - gAddressModule->set_to((sockaddr *)&newSocket->address, + AddressModule()->set_to((sockaddr *)&newSocket->address, (sockaddr *)&buffer->destination); - gAddressModule->set_to((sockaddr *)&newSocket->peer, + AddressModule()->set_to((sockaddr *)&newSocket->peer, (sockaddr *)&buffer->source); TCPEndpoint *endpoint = (TCPEndpoint *)newSocket->first_protocol; @@ -734,12 +753,12 @@ // TODO: proper error handling! - endpoint->fRoute = gDatalinkModule->get_route(gDomain, + endpoint->fRoute = gDatalinkModule->get_route(Domain(), (sockaddr *)&newSocket->peer); if (endpoint->fRoute == NULL) return DROP; - if (gEndpointManager->SetConnection(endpoint, (sockaddr *)&buffer->destination, + if (fManager->SetConnection(endpoint, (sockaddr *)&buffer->destination, (sockaddr *)&buffer->source, NULL) < B_OK) return DROP; @@ -1085,8 +1104,8 @@ return status; } - gAddressModule->set_to((sockaddr *)&buffer->source, (sockaddr *)&socket->address); - gAddressModule->set_to((sockaddr *)&buffer->destination, (sockaddr *)&socket->peer); + AddressModule()->set_to((sockaddr *)&buffer->source, (sockaddr *)&socket->address); + AddressModule()->set_to((sockaddr *)&buffer->destination, (sockaddr *)&socket->peer); uint32 size = buffer->size; if (length > 0 && fSendNext + segmentLength == fSendQueue.LastSequence()) { @@ -1108,10 +1127,10 @@ TRACE("SendQueued() flags %x, buffer %p, size %lu, from address %s to %s", segment.flags, buffer, buffer->size, - AddressString(gDomain, (sockaddr *)&buffer->source, true).Data(), - AddressString(gDomain, (sockaddr *)&buffer->destination, true).Data()); + AddressString(Domain(), (sockaddr *)&buffer->source, true).Data(), + AddressString(Domain(), (sockaddr *)&buffer->destination, true).Data()); - status = add_tcp_header(segment, buffer); + status = add_tcp_header(AddressModule(), segment, buffer); if (status != B_OK) { gBufferModule->free(buffer); return status; @@ -1525,6 +1544,6 @@ if (recursive_lock_lock(&endpoint->Lock()) < B_OK) return; - gSocketModule->delete_socket(endpoint->socket); + endpoint->DeleteSocket(); } Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h 2007-04-15 23:18:15 UTC (rev 20717) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h 2007-04-16 00:27:39 UTC (rev 20718) @@ -64,6 +64,8 @@ tcp_state State() const { return fState; } bool IsBound() const; + void DeleteSocket(); + status_t DelayedAcknowledge(); status_t SendAcknowledge(); status_t UpdateTimeWait(); @@ -72,6 +74,12 @@ net_buffer *buffer); int32 Receive(tcp_segment_header& segment, net_buffer *buffer); + net_domain *Domain() const + { return socket->first_protocol->module->get_domain( + socket->first_protocol); } + net_address_module_info *AddressModule() const + { return Domain()->address_module; } + private: friend class EndpointManager; @@ -93,6 +101,8 @@ static void _PersistTimer(net_timer *timer, void *data); static void _DelayedAcknowledgeTimer(net_timer *timer, void *data); + EndpointManager *fManager; + TCPEndpoint *fConnectionHashNext; TCPEndpoint *fEndpointHashNext; TCPEndpoint *fEndpointNextWithSamePort; Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.cpp 2007-04-15 23:18:15 UTC (rev 20717) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.cpp 2007-04-16 00:27:39 UTC (rev 20718) @@ -42,37 +42,59 @@ typedef NetBufferField TCPChecksumField; -net_domain *gDomain; -net_address_module_info *gAddressModule; net_buffer_module_info *gBufferModule; net_datalink_module_info *gDatalinkModule; net_socket_module_info *gSocketModule; net_stack_module_info *gStackModule; -EndpointManager *gEndpointManager; -status_t -set_domain(net_interface *interface = NULL) -{ - if (gDomain == NULL) { - // domain and address module are not known yet, we copy them from - // the buffer's interface (if any): - if (interface == NULL || interface->domain == NULL) - gDomain = gStackModule->get_domain(AF_INET); - else - gDomain = interface->domain; +// TODO we need to think of a better way to do this. It would be +// nice if we registered a per EndpointManager receiving +// protocol cookie, so we don't have to go through the list +// for each segment. +typedef DoublyLinkedList EndpointManagerList; +static benaphore sEndpointManagersLock; +static EndpointManagerList sEndpointManagers; - if (gDomain == NULL) { - // this shouldn't occur, of course, but who knows... - return B_BAD_VALUE; - } - gAddressModule = gDomain->address_module; + +static EndpointManager * +endpoint_manager_for(net_domain *domain) +{ + EndpointManagerList::Iterator iterator = sEndpointManagers.GetIterator(); + while (iterator.HasNext()) { + EndpointManager *endpointManager = iterator.Next(); + if (endpointManager->Domain() == domain) + return endpointManager; } - return B_OK; + return NULL; } +EndpointManager * +create_endpoint_manager(net_domain *domain) +{ + EndpointManager *endpointManager = endpoint_manager_for(domain); + if (endpointManager) + return endpointManager; + + endpointManager = new (std::nothrow) EndpointManager(domain); + if (endpointManager) + sEndpointManagers.Add(endpointManager); + + return endpointManager; +} + + +void +return_endpoint_manager(EndpointManager *endpointManager) +{ + // TODO when the connection and endpoint count reach zero + // we should remove the endpoint manager from the endpoints + // list and delete it. +} + + static inline void bump_option(tcp_option *&option, size_t &length) { @@ -125,7 +147,8 @@ for \a flags, \a seq \a ack and \a advertisedWindow. */ status_t -add_tcp_header(tcp_segment_header &segment, net_buffer *buffer) +add_tcp_header(net_address_module_info *addressModule, + tcp_segment_header &segment, net_buffer *buffer) { buffer->protocol = IPPROTO_TCP; @@ -138,8 +161,8 @@ tcp_header &header = bufferHeader.Data(); - header.source_port = gAddressModule->get_port((sockaddr *)&buffer->source); - header.destination_port = gAddressModule->get_port((sockaddr *)&buffer->destination); + header.source_port = addressModule->get_port((sockaddr *)&buffer->source); + header.destination_port = addressModule->get_port((sockaddr *)&buffer->destination); header.sequence = htonl(segment.sequence); header.acknowledge = (segment.flags & TCP_FLAG_ACKNOWLEDGE) ? htonl(segment.acknowledge) : 0; @@ -161,7 +184,7 @@ TRACE(("add_tcp_header(): buffer %p, flags 0x%x, seq %lu, ack %lu, win %u\n", buffer, segment.flags, segment.sequence, segment.acknowledge, segment.advertised_window)); - *TCPChecksumField(buffer) = Checksum::PseudoHeader(gAddressModule, + *TCPChecksumField(buffer) = Checksum::PseudoHeader(addressModule, gBufferModule, buffer, IPPROTO_TCP); return B_OK; @@ -222,44 +245,6 @@ } -status_t -reply_with_reset(tcp_segment_header &segment, net_buffer *buffer) -{ - TRACE(("TCP: Sending RST...\n")); - - net_buffer *reply = gBufferModule->create(512); - if (reply == NULL) - return B_NO_MEMORY; - - gAddressModule->set_to((sockaddr *)&reply->source, - (sockaddr *)&buffer->destination); - gAddressModule->set_to((sockaddr *)&reply->destination, - (sockaddr *)&buffer->source); - - tcp_segment_header outSegment; - outSegment.flags = TCP_FLAG_RESET; - outSegment.sequence = 0; - outSegment.acknowledge = 0; - outSegment.advertised_window = 0; - outSegment.urgent_offset = 0; - - if ((segment.flags & TCP_FLAG_ACKNOWLEDGE) == 0) { - outSegment.flags |= TCP_FLAG_ACKNOWLEDGE; - outSegment.acknowledge = segment.sequence + buffer->size; - } else - outSegment.sequence = segment.acknowledge; - - status_t status = add_tcp_header(outSegment, reply); - if (status == B_OK) - status = gDomain->module->send_data(NULL, reply); - - if (status != B_OK) - gBufferModule->free(reply); - - return status; -} - - const char * name_for_state(tcp_state state) { @@ -350,9 +335,6 @@ status_t tcp_open(net_protocol *protocol) { - if (gDomain == NULL && set_domain() != B_OK) - return B_ERROR; - return ((TCPEndpoint *)protocol)->Open(); } @@ -497,9 +479,12 @@ { TRACE(("TCP: Received buffer %p\n", buffer)); - if (gDomain == NULL && set_domain(buffer->interface) != B_OK) + if (buffer->interface == NULL || buffer->interface->domain == NULL) return B_ERROR; + net_domain *domain = buffer->interface->domain; + net_address_module_info *addressModule = domain->address_module; + NetBufferHeaderReader bufferHeader(buffer); if (bufferHeader.Status() < B_OK) return bufferHeader.Status(); @@ -510,16 +495,17 @@ if (headerLength < sizeof(tcp_header)) return B_BAD_DATA; - if (Checksum::PseudoHeader(gAddressModule, gBufferModule, buffer, + if (Checksum::PseudoHeader(addressModule, gBufferModule, buffer, IPPROTO_TCP) != 0) return B_BAD_DATA; - gAddressModule->set_port((struct sockaddr *)&buffer->source, header.source_port); - gAddressModule->set_port((struct sockaddr *)&buffer->destination, header.destination_port); + addressModule->set_port((sockaddr *)&buffer->source, header.source_port); + addressModule->set_port((sockaddr *)&buffer->destination, + header.destination_port); TRACE((" Looking for: peer %s, local %s\n", - AddressString(gDomain, (sockaddr *)&buffer->source, true).Data(), - AddressString(gDomain, (sockaddr *)&buffer->destination, true).Data())); + AddressString(domain, (sockaddr *)&buffer->source, true).Data(), + AddressString(domain, (sockaddr *)&buffer->destination, true).Data())); //dump_tcp_header(header); //gBufferModule->dump(buffer); @@ -538,11 +524,17 @@ bufferHeader.Remove(headerLength); // we no longer need to keep the header around - RecursiveLocker locker(gEndpointManager->Locker()); + BenaphoreLocker _(sEndpointManagersLock); + + EndpointManager *endpointManager = endpoint_manager_for(domain); + if (endpointManager == NULL) + return B_ERROR; + + RecursiveLocker locker(endpointManager->Locker()); int32 segmentAction = DROP; - TCPEndpoint *endpoint = gEndpointManager->FindConnection( - (struct sockaddr *)&buffer->destination, (struct sockaddr *)&buffer->source); + TCPEndpoint *endpoint = endpointManager->FindConnection( + (sockaddr *)&buffer->destination, (sockaddr *)&buffer->source); if (endpoint != NULL) { RecursiveLocker locker(endpoint->Lock()); TRACE(("Endpoint %p in state %s\n", endpoint, name_for_state(endpoint->State()))); @@ -575,13 +567,13 @@ else if (segmentAction & ACKNOWLEDGE) endpoint->DelayedAcknowledge(); else if (segmentAction & DELETE) - gSocketModule->delete_socket(endpoint->socket); + endpoint->DeleteSocket(); } else if ((segment.flags & TCP_FLAG_RESET) == 0) segmentAction = DROP | RESET; if (segmentAction & RESET) { // send reset - reply_with_reset(segment, buffer); + endpointManager->ReplyWithReset(segment, buffer); } if (segmentAction & DROP) gBufferModule->free(buffer); @@ -611,52 +603,39 @@ static status_t tcp_init() { - status_t status; + status_t status = benaphore_init(&sEndpointManagersLock, + "endpoint managers lock"); - gDomain = NULL; - gAddressModule = NULL; - - gEndpointManager = new (std::nothrow) EndpointManager(); - if (gEndpointManager == NULL) - return B_NO_MEMORY; - - status = gEndpointManager->InitCheck(); if (status < B_OK) - goto err1; + return status; status = gStackModule->register_domain_protocols(AF_INET, SOCK_STREAM, 0, "network/protocols/tcp/v1", "network/protocols/ipv4/v1", NULL); if (status < B_OK) - goto err1; + return status; status = gStackModule->register_domain_protocols(AF_INET, SOCK_STREAM, IPPROTO_TCP, "network/protocols/tcp/v1", "network/protocols/ipv4/v1", NULL); if (status < B_OK) - goto err1; + return status; status = gStackModule->register_domain_receiving_protocol(AF_INET, IPPROTO_TCP, "network/protocols/tcp/v1"); if (status < B_OK) - goto err1; + return status; return B_OK; - -err1: - delete gEndpointManager; - - TRACE(("init_tcp() fails with %lx (%s)\n", status, strerror(status))); - return status; } static status_t tcp_uninit() { - delete gEndpointManager; + benaphore_destroy(&sEndpointManagersLock); return B_OK; } Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.h =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.h 2007-04-15 23:18:15 UTC (rev 20717) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.h 2007-04-16 00:27:39 UTC (rev 20718) @@ -157,17 +157,18 @@ }; -extern net_domain *gDomain; -extern net_address_module_info *gAddressModule; extern net_buffer_module_info *gBufferModule; extern net_datalink_module_info *gDatalinkModule; extern net_socket_module_info *gSocketModule; extern net_stack_module_info *gStackModule; -extern EndpointManager *gEndpointManager; -status_t add_tcp_header(tcp_segment_header &segment, net_buffer *buffer); +status_t add_tcp_header(net_address_module_info *addressModule, + tcp_segment_header &segment, net_buffer *buffer); const char *name_for_state(tcp_state state); +EndpointManager *create_endpoint_manager(net_domain *domain); +void return_endpoint_manager(EndpointManager *); + #endif // TCP_H From hugosantos at mail.berlios.de Mon Apr 16 05:20:10 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Mon, 16 Apr 2007 05:20:10 +0200 Subject: [Haiku-commits] r20719 - haiku/trunk/src/add-ons/kernel/network/protocols/tcp Message-ID: <200704160320.l3G3KAlZ011443@sheep.berlios.de> Author: hugosantos Date: 2007-04-16 05:19:59 +0200 (Mon, 16 Apr 2007) New Revision: 20719 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20719&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.cpp haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.h Log: support RFC 1323's TCP Timestamps (we are still not updating our estimator though). Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-16 00:27:39 UTC (rev 20718) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-16 03:19:59 UTC (rev 20719) @@ -179,6 +179,8 @@ fReceiveMaxSegmentSize(TCP_DEFAULT_MAX_SEGMENT_SIZE), fReceiveQueue(socket->receive.buffer_size), fRoundTripTime(TCP_INITIAL_RTT), + fReceivedTSval(0), + fUsingTimestamps(false), fState(CLOSED), fFlags(0), //FLAG_OPTION_WINDOW_SHIFT), fError(B_OK), @@ -363,6 +365,10 @@ fSendMax = fInitialSendSequence; fSendQueue.SetInitialSequence(fSendNext + 1); + // try to use timestamps, if the peer doesn't reply with the TS + // option as well we'll stop using them. + fUsingTimestamps = true; + // send SYN status = _SendQueued(); if (status != B_OK) { @@ -794,6 +800,8 @@ TRACE(" ListenReceive() created new endpoint %p", endpoint); + endpoint->_UpdateTimestamps(segment, 0, false); + // send SYN+ACK status_t status = endpoint->_SendQueued(); @@ -866,10 +874,12 @@ fState = SYNCHRONIZE_RECEIVED; } + _UpdateTimestamps(segment, 0, false); + segment.flags &= ~TCP_FLAG_SYNCHRONIZE; // we handled this flag now, it must not be set for further processing - return Receive(segment, buffer) | IMMEDIATE_ACKNOWLEDGE; + return _Receive(segment, buffer) | IMMEDIATE_ACKNOWLEDGE; } @@ -892,6 +902,9 @@ && fReceiveNext == segment.sequence && advertisedWindow > 0 && advertisedWindow == fSendWindow && fSendNext == fSendMax) { + + _UpdateTimestamps(segment, buffer->size, true); + if (buffer->size == 0) { // this is a pure acknowledge segment - we're on the sending end if (fSendUnacknowledged < segment.acknowledge @@ -1047,7 +1060,14 @@ tcp_segment_header segment; segment.flags = _CurrentFlags(); + segment.urgent_offset = 0; + if (fUsingTimestamps) { + segment.has_timestamps = true; + segment.TSecr = fReceivedTSval; + segment.TSval = system_time(); + } + uint32 sendWindow = fSendWindow; uint32 available = fSendQueue.Available(fSendNext); bool outstandingAcknowledge = fSendMax != fSendUnacknowledged; @@ -1172,6 +1192,9 @@ return status; } + if (segment.flags & TCP_FLAG_ACKNOWLEDGE) + fLastAcknowledgeSent = segment.acknowledge; + length -= segmentLength; if (length == 0) break; @@ -1257,6 +1280,8 @@ { uint32 advertisedWindow = (uint32)segment.advertised_window << fSendWindowShift; + size_t segmentLength = buffer->size; + if (segment.flags & TCP_FLAG_RESET) { // is this a valid reset? if (fLastAcknowledgeSent <= segment.sequence @@ -1449,6 +1474,7 @@ } if (segment.flags & TCP_FLAG_FINISH) { + segmentLength++; if (fState != CLOSED && fState != LISTEN && fState != SYNCHRONIZE_SENT) { TRACE("Receive(): peer is finishing connection!"); fReceiveNext++; @@ -1486,12 +1512,30 @@ if (buffer->size > 0 || (segment.flags & TCP_FLAG_SYNCHRONIZE) != 0) action |= ACKNOWLEDGE; + _UpdateTimestamps(segment, segmentLength, true); + TRACE("Receive() Action %ld", action); return action; } +void +TCPEndpoint::_UpdateTimestamps(tcp_segment_header &segment, size_t segmentLength, + bool checkSequence) +{ + fUsingTimestamps = segment.has_timestamps; + + if (fUsingTimestamps) { + tcp_sequence sequence(segment.sequence); + + if (!checkSequence || (fLastAcknowledgeSent >= sequence + && fLastAcknowledgeSent < (sequence + segmentLength))) + fReceivedTSval = segment.TSval; + } +} + + // #pragma mark - timer Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h 2007-04-16 00:27:39 UTC (rev 20718) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h 2007-04-16 03:19:59 UTC (rev 20719) @@ -95,6 +95,8 @@ void _NotifyReader(); bool _ShouldReceive() const; int32 _Receive(tcp_segment_header& segment, net_buffer *buffer); + void _UpdateTimestamps(tcp_segment_header& segment, + size_t segmentLength, bool checkSequence); static void _TimeWaitTimer(net_timer *timer, void *data); static void _RetransmitTimer(net_timer *timer, void *data); @@ -146,6 +148,9 @@ uint32 fTrackingSequence; bool fTracking; + uint32 fReceivedTSval; + bool fUsingTimestamps; + uint32 fCongestionWindow; uint32 fSlowStartThreshold; Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.cpp 2007-04-16 00:27:39 UTC (rev 20718) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.cpp 2007-04-16 03:19:59 UTC (rev 20719) @@ -120,11 +120,26 @@ option->max_segment_size = htons(segment.max_segment_size); bump_option(option, length); } + + if (segment.has_timestamps && length + 12 < bufferSize) { + // two NOPs so the timestamps get aligned to a 4 byte boundary + option->kind = TCP_OPTION_NOP; + bump_option(option, length); + option->kind = TCP_OPTION_NOP; + bump_option(option, length); + option->kind = TCP_OPTION_TIMESTAMP; + option->length = 10; + option->timestamp.TSval = htonl(segment.TSval); + // TSecr is opaque to us, we send it as we received it. + option->timestamp.TSecr = segment.TSecr; + bump_option(option, length); + } + if (segment.has_window_shift && length + 4 < bufferSize) { // insert one NOP so that the subsequent data is aligned on a 4 byte boundary option->kind = TCP_OPTION_NOP; bump_option(option, length); - + option->kind = TCP_OPTION_WINDOW_SHIFT; option->length = 3; option->window_shift = segment.window_shift; @@ -171,8 +186,7 @@ header.flags = segment.flags; header.advertised_window = htons(segment.advertised_window); header.checksum = 0; - header.urgent_offset = 0; - // TODO: urgent pointer not yet supported + header.urgent_offset = segment.urgent_offset; // we must detach before calculating the checksum as we may // not have a contiguous buffer. @@ -226,7 +240,9 @@ length = 3; break; case TCP_OPTION_TIMESTAMP: - // TODO: support timestamp! + segment.has_timestamps = true; + segment.TSval = option->timestamp.TSval; + segment.TSecr = ntohl(option->timestamp.TSecr); length = 10; break; @@ -515,11 +531,7 @@ segment.advertised_window = header.AdvertisedWindow(); segment.urgent_offset = header.UrgentOffset(); segment.flags = header.flags; - if ((segment.flags & TCP_FLAG_SYNCHRONIZE) != 0) { - // for now, we only process the options in the SYN segment - // TODO: when we support timestamps, they could be handled specifically - process_options(segment, buffer, headerLength - sizeof(tcp_header)); - } + process_options(segment, buffer, headerLength - sizeof(tcp_header)); bufferHeader.Remove(headerLength); // we no longer need to keep the header around Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.h =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.h 2007-04-16 00:27:39 UTC (rev 20718) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.h 2007-04-16 03:19:59 UTC (rev 20719) @@ -112,9 +112,11 @@ union { uint8 window_shift; uint16 max_segment_size; - uint32 timestamp; + struct { + uint32 TSval; + uint32 TSecr; + } timestamp; }; - uint32 timestamp_reply; } _PACKED; enum tcp_option_kind { @@ -128,18 +130,28 @@ #define TCP_MAX_WINDOW_SHIFT 14 struct tcp_segment_header { - tcp_segment_header() : has_window_shift(false), window_shift(0), max_segment_size(0) {} - // constructor zeros options + tcp_segment_header() + : + window_shift(0), + max_segment_size(0), + has_window_shift(false), + has_timestamps(false) + {} uint32 sequence; uint32 acknowledge; uint16 advertised_window; uint16 urgent_offset; uint8 flags; - uint8 has_window_shift : 1; - uint8 window_shift : 7; + uint8 window_shift; uint16 max_segment_size; + uint32 TSval; + uint32 TSecr; + + bool has_window_shift : 1; + bool has_timestamps : 1; + bool AcknowledgeOnly() const { return (flags & (TCP_FLAG_SYNCHRONIZE | TCP_FLAG_FINISH | TCP_FLAG_RESET From geist at mail.berlios.de Mon Apr 16 05:20:42 2007 From: geist at mail.berlios.de (geist at BerliOS) Date: Mon, 16 Apr 2007 05:20:42 +0200 Subject: [Haiku-commits] r20720 - haiku/trunk/src/system/libroot/posix/unistd Message-ID: <200704160320.l3G3KgLw011525@sheep.berlios.de> Author: geist Date: 2007-04-16 05:20:42 +0200 (Mon, 16 Apr 2007) New Revision: 20720 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20720&view=rev Modified: haiku/trunk/src/system/libroot/posix/unistd/_exit.c Log: fix a bug in _exit() that called the _IO_cleanup routine as if it was a function pointer, which it isn't. The mistake was probably made because there appears to be multiple stdio implementations in the tree (BSD and glibc) so it's easy to look at the wrong code. Perhaps we should clean that up. Modified: haiku/trunk/src/system/libroot/posix/unistd/_exit.c =================================================================== --- haiku/trunk/src/system/libroot/posix/unistd/_exit.c 2007-04-16 03:19:59 UTC (rev 20719) +++ haiku/trunk/src/system/libroot/posix/unistd/_exit.c 2007-04-16 03:20:42 UTC (rev 20720) @@ -8,9 +8,8 @@ #include -extern void (*_IO_cleanup)(void); +extern void _IO_cleanup(void); - void _exit(int status) { From hugosantos at mail.berlios.de Mon Apr 16 06:27:48 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Mon, 16 Apr 2007 06:27:48 +0200 Subject: [Haiku-commits] r20721 - haiku/trunk/src/add-ons/kernel/drivers/network/etherpci Message-ID: <200704160427.l3G4Rm6J015134@sheep.berlios.de> Author: hugosantos Date: 2007-04-16 06:27:37 +0200 (Mon, 16 Apr 2007) New Revision: 20721 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20721&view=rev Modified: haiku/trunk/src/add-ons/kernel/drivers/network/etherpci/etherpci.c Log: made ETHER_DEBUG use dprintf() as the previous logic was screwing badly and making the boot sequence hang in some setups (specifically qemu, may have fixed issues with Parallels as well). Modified: haiku/trunk/src/add-ons/kernel/drivers/network/etherpci/etherpci.c =================================================================== --- haiku/trunk/src/add-ons/kernel/drivers/network/etherpci/etherpci.c 2007-04-16 03:20:42 UTC (rev 20720) +++ haiku/trunk/src/add-ons/kernel/drivers/network/etherpci/etherpci.c 2007-04-16 04:27:37 UTC (rev 20721) @@ -39,22 +39,11 @@ /* diagnostic debug flags - compile in here or set while running with debugger "AcmeRoadRunner" command */ #define DEFAULT_DEBUG_FLAGS ( ERR | INFO | WARN | FUNCTION ) -//void ETHER_DEBUG(int32 debug_mask, int32 enabled, char * format, ...); +#define ETHER_DEBUG(mask, enabled, format, args...) \ + do { if (mask & enabled) \ + dprintf(format , ##args); } while (0) -static void -ETHER_DEBUG(int32 debug_mask, int32 enabled, char * format, ...) -{ - if (debug_mask & enabled) { - va_list args; - char s[4096]; - va_start(args, format); - vsprintf( s, format, args ); - va_end(args); - dprintf("%s",s); - } -} - static pci_module_info *gPCIModInfo; static char *gDevNameList[MAX_CARDS+1]; static pci_info *gDevList[MAX_CARDS+1]; From geist at mail.berlios.de Mon Apr 16 08:17:15 2007 From: geist at mail.berlios.de (geist at BerliOS) Date: Mon, 16 Apr 2007 08:17:15 +0200 Subject: [Haiku-commits] r20722 - in haiku/trunk/src/system: boot kernel kernel/lib libroot libroot/posix/string libroot/posix/string/arch/ppc libroot/posix/string/arch/sh4 libroot/posix/string/arch/x86 runtime_loader Message-ID: <200704160617.l3G6HF7S032192@sheep.berlios.de> Author: geist Date: 2007-04-16 08:17:14 +0200 (Mon, 16 Apr 2007) New Revision: 20722 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20722&view=rev Added: haiku/trunk/src/system/libroot/posix/string/arch/ppc/arch_string.S haiku/trunk/src/system/libroot/posix/string/arch/sh4/arch_string.S haiku/trunk/src/system/libroot/posix/string/arch/x86/arch_string.S Removed: haiku/trunk/src/system/libroot/posix/string/arch/ppc/libc.mk haiku/trunk/src/system/libroot/posix/string/arch/sh4/libc.mk haiku/trunk/src/system/libroot/posix/string/arch/x86/memcpy.S Modified: haiku/trunk/src/system/boot/Jamfile haiku/trunk/src/system/kernel/Jamfile haiku/trunk/src/system/kernel/lib/Jamfile haiku/trunk/src/system/libroot/Jamfile haiku/trunk/src/system/libroot/posix/string/Jamfile haiku/trunk/src/system/libroot/posix/string/memcpy.c haiku/trunk/src/system/runtime_loader/Jamfile Log: Turn the assembly optimized memcpy (simple rep movsd) back on for x86. Had to hack around the make system a bit, and the result is pretty nasty, specifically due to the amount of places in the system where various targets poke their fingers into the libroot directory. The solution is less than optimal, but should work for now. Modified: haiku/trunk/src/system/boot/Jamfile =================================================================== --- haiku/trunk/src/system/boot/Jamfile 2007-04-16 04:27:37 UTC (rev 20721) +++ haiku/trunk/src/system/boot/Jamfile 2007-04-16 06:17:14 UTC (rev 20722) @@ -22,6 +22,7 @@ strchr.o strrchr.o strtol.o + arch_string.o ; local platformObjects = ; Modified: haiku/trunk/src/system/kernel/Jamfile =================================================================== --- haiku/trunk/src/system/kernel/Jamfile 2007-04-16 04:27:37 UTC (rev 20721) +++ haiku/trunk/src/system/kernel/Jamfile 2007-04-16 06:17:14 UTC (rev 20722) @@ -101,6 +101,7 @@ kernel_os_main.o kernel_os_arch_$(TARGET_ARCH).o kernel_posix.o + kernel_posix_arch_$(TARGET_ARCH).o $(HAIKU_STATIC_LIBSUPC++) Modified: haiku/trunk/src/system/kernel/lib/Jamfile =================================================================== --- haiku/trunk/src/system/kernel/lib/Jamfile 2007-04-16 04:27:37 UTC (rev 20721) +++ haiku/trunk/src/system/kernel/lib/Jamfile 2007-04-16 06:17:14 UTC (rev 20722) @@ -104,7 +104,7 @@ strspn.c strstr.c strtok.c - + : $(TARGET_KERNEL_PIC_CCFLAGS) ; @@ -120,12 +120,14 @@ ; SEARCH_SOURCE += [ FDirName $(posixSources) arch $(TARGET_ARCH) ] ; +SEARCH_SOURCE += [ FDirName $(posixSources) string arch $(TARGET_ARCH) ] ; KernelMergeObject kernel_posix_arch_$(TARGET_ARCH).o : setjmp.S siglongjmp.S sigsetjmp.S kernel_setjmp_save_sigs.c + arch_string.S : $(TARGET_KERNEL_PIC_CCFLAGS) ; Modified: haiku/trunk/src/system/libroot/Jamfile =================================================================== --- haiku/trunk/src/system/libroot/Jamfile 2007-04-16 04:27:37 UTC (rev 20721) +++ haiku/trunk/src/system/libroot/Jamfile 2007-04-16 06:17:14 UTC (rev 20722) @@ -32,6 +32,7 @@ posix_gnu_wctype.o posix_stdlib.o posix_string.o + posix_string_arch_$(TARGET_ARCH).o posix_sys.o posix_time.o posix_unistd.o Modified: haiku/trunk/src/system/libroot/posix/string/Jamfile =================================================================== --- haiku/trunk/src/system/libroot/posix/string/Jamfile 2007-04-16 04:27:37 UTC (rev 20721) +++ haiku/trunk/src/system/libroot/posix/string/Jamfile 2007-04-16 06:17:14 UTC (rev 20722) @@ -36,3 +36,10 @@ strtok.c strxfrm.c ; + +SubDir HAIKU_TOP src system libroot posix string arch $(TARGET_ARCH) ; + +MergeObject posix_string_arch_$(TARGET_ARCH).o : + arch_string.S +; + Added: haiku/trunk/src/system/libroot/posix/string/arch/ppc/arch_string.S =================================================================== Deleted: haiku/trunk/src/system/libroot/posix/string/arch/ppc/libc.mk Added: haiku/trunk/src/system/libroot/posix/string/arch/sh4/arch_string.S =================================================================== Deleted: haiku/trunk/src/system/libroot/posix/string/arch/sh4/libc.mk Copied: haiku/trunk/src/system/libroot/posix/string/arch/x86/arch_string.S (from rev 20720, haiku/trunk/src/system/libroot/posix/string/arch/x86/memcpy.S) =================================================================== --- haiku/trunk/src/system/libroot/posix/string/arch/x86/memcpy.S 2007-04-16 03:20:42 UTC (rev 20720) +++ haiku/trunk/src/system/libroot/posix/string/arch/x86/arch_string.S 2007-04-16 06:17:14 UTC (rev 20722) @@ -0,0 +1,31 @@ +/* +** Copyright 2001, Travis Geiselbrecht. All rights reserved. +** Distributed under the terms of the NewOS License. +*/ + +.globl memcpy + +.align 4 +memcpy: + pushl %esi + pushl %edi + movl 12(%esp),%edi /* dest */ + movl %edi,%eax /* save dest ptr as return address */ + movl 16(%esp),%esi /* source */ + movl 20(%esp),%ecx /* count */ + + /* move by words */ + cld + shrl $2,%ecx + rep + movsl + + /* move any remaining data by bytes */ + movl 20(%esp),%ecx + andl $3,%ecx + rep + movsb + + popl %edi + popl %esi + ret Deleted: haiku/trunk/src/system/libroot/posix/string/arch/x86/memcpy.S Modified: haiku/trunk/src/system/libroot/posix/string/memcpy.c =================================================================== --- haiku/trunk/src/system/libroot/posix/string/memcpy.c 2007-04-16 04:27:37 UTC (rev 20721) +++ haiku/trunk/src/system/libroot/posix/string/memcpy.c 2007-04-16 06:17:14 UTC (rev 20722) @@ -6,9 +6,9 @@ #include #include +/* do not build for for arches that have overridden this with an assembly version */ +#if !defined(ARCH_x86) -#if !_ASM_MEMCPY - typedef int word; #define lsize sizeof(word) @@ -46,3 +46,4 @@ } #endif + Modified: haiku/trunk/src/system/runtime_loader/Jamfile =================================================================== --- haiku/trunk/src/system/runtime_loader/Jamfile 2007-04-16 04:27:37 UTC (rev 20721) +++ haiku/trunk/src/system/runtime_loader/Jamfile 2007-04-16 06:17:14 UTC (rev 20722) @@ -46,6 +46,7 @@ strrchr.o strspn.o strstr.o + arch_string.o [ FGristFiles kernel_vsprintf.o ] ; From geist at mail.berlios.de Mon Apr 16 08:48:38 2007 From: geist at mail.berlios.de (geist at BerliOS) Date: Mon, 16 Apr 2007 08:48:38 +0200 Subject: [Haiku-commits] r20723 - in haiku/trunk/src/system/kernel: arch/x86 vm Message-ID: <200704160648.l3G6mc8B001024@sheep.berlios.de> Author: geist Date: 2007-04-16 08:48:38 +0200 (Mon, 16 Apr 2007) New Revision: 20723 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20723&view=rev Modified: haiku/trunk/src/system/kernel/arch/x86/arch_cpu.c haiku/trunk/src/system/kernel/arch/x86/arch_x86.S haiku/trunk/src/system/kernel/vm/vm.cpp Log: asm optimized user_memcpy(), which should help somewhat, since the old version was a byte-by-byte copy. Modified: haiku/trunk/src/system/kernel/arch/x86/arch_cpu.c =================================================================== --- haiku/trunk/src/system/kernel/arch/x86/arch_cpu.c 2007-04-16 06:17:14 UTC (rev 20722) +++ haiku/trunk/src/system/kernel/arch/x86/arch_cpu.c 2007-04-16 06:48:38 UTC (rev 20723) @@ -580,32 +580,6 @@ } } - -status_t -arch_cpu_user_memcpy(void *to, const void *from, size_t size, addr_t *faultHandler) -{ - char *tmp = (char *)to; - char *s = (char *)from; - addr_t oldFaultHandler = *faultHandler; - - // this check is to trick the gcc4 compiler and have it keep the error label - if (to == NULL) - goto error; - - *faultHandler = (addr_t)&&error; - - while (size--) - *tmp++ = *s++; - - *faultHandler = oldFaultHandler; - return 0; - -error: - *faultHandler = oldFaultHandler; - return B_BAD_ADDRESS; -} - - ssize_t arch_cpu_user_strlcpy(char *to, const char *from, size_t size, addr_t *faultHandler) { Modified: haiku/trunk/src/system/kernel/arch/x86/arch_x86.S =================================================================== --- haiku/trunk/src/system/kernel/arch/x86/arch_x86.S 2007-04-16 06:17:14 UTC (rev 20722) +++ haiku/trunk/src/system/kernel/arch/x86/arch_x86.S 2007-04-16 06:48:38 UTC (rev 20723) @@ -219,3 +219,46 @@ popl %eax popl %esi ret + +/* status_t arch_cpu_user_memcpy(void *to, const void *from, size_t size, addr_t *faultHandler) */ +FUNCTION(arch_cpu_user_memcpy): + pushl %esi + pushl %edi + movl 12(%esp),%edi /* dest */ + movl 16(%esp),%esi /* source */ + movl 20(%esp),%ecx /* count */ + + /* set the fault handler */ + movl 24(%esp),%edx /* fault handler */ + movl (%edx),%eax + movl $.L_user_memcpy_error, (%edx) + + /* move by words */ + cld + shrl $2,%ecx + rep + movsl + + /* move any remaining data by bytes */ + movl 20(%esp),%ecx + andl $3,%ecx + rep + movsb + + /* restore the old fault handler */ + movl %eax,(%edx) + xor %eax,%eax + + popl %edi + popl %esi + ret + + /* error condition */ +.L_user_memcpy_error: + /* restore the old fault handler */ + movl %eax,(%edx) + movl $-1,%eax /* return a generic error, the wrapper routine will deal with it */ + popl %edi + popl %esi + ret + Modified: haiku/trunk/src/system/kernel/vm/vm.cpp =================================================================== --- haiku/trunk/src/system/kernel/vm/vm.cpp 2007-04-16 06:17:14 UTC (rev 20722) +++ haiku/trunk/src/system/kernel/vm/vm.cpp 2007-04-16 06:48:38 UTC (rev 20723) @@ -3741,7 +3741,9 @@ status_t user_memcpy(void *to, const void *from, size_t size) { - return arch_cpu_user_memcpy(to, from, size, &thread_get_current_thread()->fault_handler); + if (arch_cpu_user_memcpy(to, from, size, &thread_get_current_thread()->fault_handler) < B_OK) + return B_BAD_ADDRESS; + return B_OK; } @@ -3765,10 +3767,11 @@ status_t user_memset(void *s, char c, size_t count) { - return arch_cpu_user_memset(s, c, count, &thread_get_current_thread()->fault_handler); + if (arch_cpu_user_memset(s, c, count, &thread_get_current_thread()->fault_handler) < B_OK) + return B_BAD_ADDRESS; + return B_OK; } - // #pragma mark - kernel public API From axeld at pinc-software.de Mon Apr 16 09:13:34 2007 From: axeld at pinc-software.de (Axel =?iso-8859-15?q?D=F6rfler?=) Date: Mon, 16 Apr 2007 09:13:34 +0200 CEST Subject: [Haiku-commits] =?iso-8859-15?q?r20719_-_haiku/trunk/src/add-ons/?= =?iso-8859-15?q?kernel/network/protocols/tcp?= In-Reply-To: <200704160320.l3G3KAlZ011443@sheep.berlios.de> Message-ID: <1087100721-BeMail@zon> hugosantos at mail.berlios.de wrote: > support RFC 1323's TCP Timestamps (we are still not updating our > estimator though). Nice! > + fReceivedTSval(0), [...] > + struct { > + uint32 TSval; > + uint32 TSecr; > + } timestamp; > }; [...] > + uint32 TSval; > + uint32 TSecr; What about names that follow our coding style? :-) Like: TCPEndpoint::fReceivedTimestamp tcp_option::struct timestamp { uint32 value; uint32 echo_reply; } tcp_segment::timestamp_value tcp_segment::timestamp_echo_reply ? I can do those changes if you don't have the time. Bye, Axel. From axeld at pinc-software.de Mon Apr 16 09:22:12 2007 From: axeld at pinc-software.de (Axel =?iso-8859-15?q?D=F6rfler?=) Date: Mon, 16 Apr 2007 09:22:12 +0200 CEST Subject: [Haiku-commits] =?iso-8859-15?q?r20714_-_in_haiku/trunk=3A_header?= =?iso-8859-15?q?s/private/net_src/add-ons/kernel/network/protocols/ipv4_s?= =?iso-8859-15?q?rc/add-ons/kernel/network/protocols/udp_src/add-ons/kerne?= =?iso-8859-15?q?l/network/stack?= In-Reply-To: <200704152211.l3FMBWv5003863@sheep.berlios.de> Message-ID: <1606011219-BeMail@zon> hugosantos at mail.berlios.de wrote: > + net_route *route = NULL; > + status_t status = get_buffer_route(domain, buffer, &route); > + if (status < B_OK) > + return status; > + > + status = module->send_routed_data(protocol, route, buffer); > + put_route(domain, route); > + return status; I still don't understand why UdpEndpoint::SendData() shouldn't look like this. It's far from complicated and looks a lot cleaner to me. Bye, Axel. From superstippi at gmx.de Mon Apr 16 11:12:24 2007 From: superstippi at gmx.de (Stephan Assmus) Date: Mon, 16 Apr 2007 11:12:24 +0200 Subject: [Haiku-commits] r20723 - in haiku/trunk/src/system/kernel: arch/x86 vm In-Reply-To: <200704160648.l3G6mc8B001024@sheep.berlios.de> References: <200704160648.l3G6mc8B001024@sheep.berlios.de> Message-ID: <20070416111224.376.1@stippis.mshome.net> Hi Travis, On 2007-04-16 at 08:48:38 [+0200], geist at BerliOS wrote: > Author: geist > Date: 2007-04-16 08:48:38 +0200 (Mon, 16 Apr 2007) > New Revision: 20723 > ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20723&view=rev > > Modified: > haiku/trunk/src/system/kernel/arch/x86/arch_cpu.c > haiku/trunk/src/system/kernel/arch/x86/arch_x86.S > haiku/trunk/src/system/kernel/vm/vm.cpp > Log: > asm optimized user_memcpy(), which should help somewhat, since the old > version was a byte-by-byte copy. your change seems to break binary compatibility. The runtime_loader says something about having found the symbol "memcpy" but it is of the wrong type. Best regards, -Stephan From nielx at mail.berlios.de Mon Apr 16 11:28:33 2007 From: nielx at mail.berlios.de (nielx at BerliOS) Date: Mon, 16 Apr 2007 11:28:33 +0200 Subject: [Haiku-commits] r20724 - in haiku/trunk/docs/user: . drivers midi2 support Message-ID: <200704160928.l3G9SX4l016988@sheep.berlios.de> Author: nielx Date: 2007-04-16 11:28:29 +0200 (Mon, 16 Apr 2007) New Revision: 20724 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20724&view=rev Added: haiku/trunk/docs/user/drivers/USB3.dox haiku/trunk/docs/user/drivers/USB_spec.dox haiku/trunk/docs/user/drivers/usb_modules.dox haiku/trunk/docs/user/support/Archivable.dox Removed: haiku/trunk/docs/user/support/support_archiving.dox Modified: haiku/trunk/docs/user/Doxyfile haiku/trunk/docs/user/apidoc.dox haiku/trunk/docs/user/drivers/drivers.dox haiku/trunk/docs/user/drivers/fs_interface.dox haiku/trunk/docs/user/midi2/midi2intro.dox haiku/trunk/docs/user/support/Autolock.dox haiku/trunk/docs/user/support/Beep.dox haiku/trunk/docs/user/support/BlockCache.dox haiku/trunk/docs/user/support/List.dox haiku/trunk/docs/user/support/SupportDefs.dox haiku/trunk/docs/user/support/parsedate.dox haiku/trunk/docs/user/support/stopwatch.dox haiku/trunk/docs/user/support/string.dox haiku/trunk/docs/user/support/support_intro.dox haiku/trunk/docs/user/support/syslog.dox haiku/trunk/docs/user/support/typeconstants.dox Log: Large documentation update: - Add the beginnings of the documentation for the USB module - Fix some mistakes here and there - Almost finished the support kit. Tried to update everything to the standards Modified: haiku/trunk/docs/user/Doxyfile =================================================================== --- haiku/trunk/docs/user/Doxyfile 2007-04-16 06:48:38 UTC (rev 20723) +++ haiku/trunk/docs/user/Doxyfile 2007-04-16 09:28:29 UTC (rev 20724) @@ -465,6 +465,8 @@ midi2 \ support \ ../../headers/os/drivers/fs_interface.h \ + ../../headers/os/drivers/USB3.h \ + ../../headers/os/drivers/USB_spec.h \ ../../headers/os/midi2 \ ../../headers/os/support \ ../../headers/posix/syslog.h Modified: haiku/trunk/docs/user/apidoc.dox =================================================================== --- haiku/trunk/docs/user/apidoc.dox 2007-04-16 06:48:38 UTC (rev 20723) +++ haiku/trunk/docs/user/apidoc.dox 2007-04-16 09:28:29 UTC (rev 20724) @@ -75,39 +75,37 @@ \subsection formalrequirements_headerblock The Header Block Every documentation file will begin with the header block. It's basically a - copyright block, with a reference to the author(s) and with the revision + copyright block, with a reference to the author(s) and with the revision against which the documentaton was written. \verbatim -// -// Copyright 2007, Haiku Inc. All Rights Reserved. -// -// Distributed under the terms of the MIT License. -// -// -// Documentation by: -// Niels Sascha Reedijk -// Corresponds to: -// /trunk/headers/os/support/String.h rev 19731 -// /trunk/src/kits/support/String.cpp rev 19731 -// +/* + * Copyright 2007, Haiku, Inc. All Rights Reserved. + * Distributed under the terms of the MIT License. + * + * Documentation by: + * Niels Sascha Reedijk + * Corresponds to: + * /trunk/headers/os/support/String.h rev 19731 + * /trunk/src/kits/support/String.cpp rev 19731 + * / \endverbatim The example above has a few elements that you should take note of: - -# First of all, every line starts with a C++ single line style comment. - So it starts with two slashes: \c //. If there is text on a line, the - tokens are followed by \e one space. If the text is part of a category, - such as Documentation by, put two spaces after the delimeter. + -# The header is put in a standard C comment, which are enclosed between + \c /* and \c *\/. + -# Every line starts with a whitespace and an asterix, followed by another + space. If the text is part of a category, such as Documentation + by, put three spaces after the delimeter. -# We start with a copyright notice. The first line is empty, then the - copyright notice, then another empty line, and then the line on \e MIT, - followed by two empty lines. + copyright notice, then the line on \e MIT, followed by an empty line. -# Then there is a label Documentation by:, which is followed by lines with names and email addresses between brackets. -# The final part is underneath the label Corresponds to:. Underneath there is a list of files and their svn revisions that the current documentation is known to correspond with. - -# The header block ends with an empty C++ comment, and the next block that - follows underneath will start after an empty line. + -# The header block ends with the \c *\/, where the asterix is alligned with + with the ones above it. \subsection formalrequirements_blocks Blocks Added: haiku/trunk/docs/user/drivers/USB3.dox =================================================================== --- haiku/trunk/docs/user/drivers/USB3.dox 2007-04-16 06:48:38 UTC (rev 20723) +++ haiku/trunk/docs/user/drivers/USB3.dox 2007-04-16 09:28:29 UTC (rev 20724) @@ -0,0 +1,477 @@ +/* + * Copyright 2007, Haiku, Inc. All Rights Reserved. + * Distributed under the terms of the MIT License. + * + * Documentation by: + * Niels Sascha Reedijk + * Corresponds to: + * /trunk/headers/os/drivers/USB3.h rev 19915 + */ + +/*! + \file USB3.h + \ingroup drivers + \brief Interface for the USB module. +*/ + +/*! + \typedef struct usb_module_info usb_module_info + \brief The main interface object. See the usb_module_info documentation. +*/ + +/*! + \typedef uint32 usb_id + \brief Uniquely identify various USB objects that are used in the module. +*/ + +/*! + \typedef usb_id usb_device + \brief Uniquely identify USB devices. +*/ + +/*! + \typedef usb_id usb_interface + \brief Uniquely identify USB interfaces. +*/ + +/*! + \typedef usb_id usb_pipe + \brief Uniquely identify USB pipes. +*/ + +/*! + \typedef struct usb_endpoint_info usb_endpoint_info + \brief Container for USB endpoint descriptors. + \see Documentation for usb_endpoint_info. +*/ + +/*! + \typedef struct usb_interface_info usb_interface_info + \brief Container for USB interface descriptors. + \see Documentation for usb_interface_info. +*/ + +/*! + \typedef usb_interface_list usb_interface_list + \brief Container that holds a list of USB interface descriptors. + \see Documentation for usb_interface_list. +*/ + +/*! + \typedef struct usb_configuration_info usb_configuration_info + \brief Container for USB configuration descriptors. + \see Documentation for usb_configuration_info. +*/ + +///// usb_notify_hooks ///// + +/*! + \struct usb_notify_hooks + \brief Hooks that the USB stack can callback in case of events. +*/ + +/*! + \fn status_t (*usb_notify_hooks::device_added)(usb_device device, void **cookie) + \brief Called by the stack in case a device is added. + + As soon as you have registered hooks using the + usb_module_info::install_notify() method, this hook will be called as soon as + a device is inserted that matches your provided usb_support_descriptor. + + \param device A unique id that identifies this USB device. + \param[in] cookie You can store a pointer to an object in this variable. + When the device is removed, this cookie will be provided to you. + \return You should return \c B_OK in case of success. If you return an error + value, the \a device id will become invalid and you will not be notified if + this device is removed. + \see device_removed() +*/ + +/*! + \var status_t (*usb_notify_hooks::device_removed)(void *cookie) + \brief Called by the stack in case a device you are using is removed. + + If you have accepted a device in the device_added() hook, this hook will + be called as soon as the device is removed. + + \param cookie The cookie you provided in the device_added() hook. Make sure + that you free the cookie, if necessary. + \return Currently the return value of this hook is ignored. It is recommended + to return \c B_OK though. +*/ + +///// usb_support_descriptor ///// + +/*! + \struct usb_support_descriptor + \brief Description of device descriptor that the driver can handle. + + Support descriptors can be used to match any form of class, subclass or + protocol, or a vendor and/or product. If any field has the value \c 0, it + is treated as a wildcard. + + For example, if you want to watch for all the hubs, which have a device + class of \c 0x09, you would pass this descriptor: + + \code + usb_support_descriptor hub_devs = { 9, 0, 0, 0, 0 }; + \endcode + + See usb_module_info::register_driver() for more information on how to use + this object. +*/ + +/*! + \var usb_support_descriptor::dev_class + \brief The supported device classes. +*/ + +/*! + \var usb_support_descriptor::dev_subclass + \brief The suported device subclasses. +*/ + +/*! + \var usb_support_descriptor::dev_protocol + \brief The supported device protocols. +*/ + +/*! + \var usb_support_descriptor::vendor + \brief The supported device vendor. +*/ + +/*! + \var usb_support_descriptor::product + \brief The supported device products. +*/ + +///// usb_endpoint_info ///// + +///// usb_interface_info ///// + +///// usb_interface_list ///// + +///// usb_configuration_info ///// + +///// usb_iso_packet_descriptor ///// + +///// usb_callback_func ///// + +/*! + \typedef typedef void (*usb_callback_func)(void *cookie, status_t status, void *data, size_t actualLength) + \brief Callback function for asynchronous transfers. + + \param cookie The cookie you supplied when you queued the transfer. + \param status The status of the transfer (whether it succeeded or not). + \param data The provided buffer. + \param actualLength The amount of bytes read or written during the transfer. +*/ + +///// usb_module_info ///// + +/*! + \struct usb_module_info + \brief Interface for drivers to interact with Haiku's USB stack. +*/ + +/*! + \var usb_module_info::binfo + \brief Instance of the bus_manager_info object. +*/ + +/*! + \fn status_t (*usb_module_info::register_driver)(const char *driverName, const usb_support_descriptor *supportDescriptors, size_t supportDescriptorCount, const char *optionalRepublishDriverName) + \brief Register your driver. + + To let the USB stack know that a driver is available to support devices, a + driver needs to register itself first. To let the stack know which devices + it needs to notify the driver of, have a look at usb_support_descriptor. + + It is possible to supply a list of support constructors. You should allocate + an array of support constructors, and give the amount of constructors in the + array using the \a supportDescriptorCount parameter. + + In case your driver supports all devices, or more likely, in case you want to + monitor all devices plugged in and removed, it is safe to pass \c NULL to the + \a supportDescriptors paramater and zero (0) to \a supportDescriptorCount. + + \param driverName A unique name that identifies your driver. Avoid names like + \c webcam or \c mouse, instead use vendor names and device types to avoid + nameclashes. The install_notify() and uninstall_notify() functions use the + driver name as an identifier. + \param supportDescriptors An array of the type usb_support_descriptor. Pass + the amount of objects in the next parameter. + \param supportDescriptorCount The number of objects in the array supplied in + the previous parameter. + \param optionalRepublishDriverName Undocumented parameter. It is safe to + pass \c NULL. + \retval B_OK The driver is registered. You can now call install_notify() + \retval B_BAD_VALUE You passed \c NULL as \a driverName. + \retval B_ERROR General internal error in the USB stack. You may retry the + request in this case. + \retval B_NO_MEMORY Error allocating some internal objects. The system is + out of memory. +*/ + +/*! + \fn status_t (*usb_module_info::install_notify)(const char *driverName, const usb_notify_hooks *hooks) + \brief Install notify hooks for your driver. + + After your driver is registered, you need to pass hooks to your driver that + are called whenever a device that matches your \link usb_support_descriptor + support descriptor \endlink . + + As soon as the hooks are installed you'll receive callbacks for devices that + are already attached, so make sure your driver is initialized properly when + calling this method. + + \param driverName The name you passed in register_driver(). + \param hooks The hooks the stack should call in case the status of devices + that match your support descriptor changes. + \retval B_OK Hooks are installed succesfully. + \retval B_NAME_NOT_FOUND Invalid \a driverName. + + \see usb_notify_hooks for information on how your hooks should behave. + \see uninstall_notify() +*/ + +/*! + \fn status_t (*usb_module_info::uninstall_notify)(const char *driverName) + \brief Uninstall notify hooks for your driver. + + If your driver needs to stop, you can uninstall the notifier hooks. This will + clear the stored hooks in the driver and you will not receive any + notifications when new devices are attached. This method will also call + usb_notify_hooks::device_removed() for all the devices that you are using and + all the stack's resources that are allocated to your driver are cleared. + + \param driverName The name you passed in register_driver(). + \retval B_OK Hooks are uninstalled. + \retval B_NAME_NOT_FOUND Invalid \a driverName. +*/ + +/*! + \fn const usb_device_descriptor *(*usb_module_info::get_device_descriptor)(usb_device device) + \brief Get the device descriptor. + + \param device The id of the device you want to query. + \return The standard usb_device_descriptor, or \c NULL in case of an error. +*/ + +/*! + \fn const usb_configuration_info *(*usb_module_info::get_nth_configuration)(usb_device device, uint index) + \brief Get a configuration descriptor by index. + + \param device The id of the device you want to query. + \param index The (zero based) offset of the list of configurations. + \return The usb_configuration_info with the standard usb configuration + descriptor, or \c NULL if the \a id is invalid or the \a index is out of + bounds. +*/ + +/*! + \fn const usb_configuration_info *(*usb_module_info::get_configuration)(usb_device device) + \brief Get the current configuration. + + \param id The id of the device you want to query. + \retval The usb_configuration_info with the standard usb configuration + descriptor, or \c NULL if the \a id is invalid. +*/ + +/*! + \fn status_t (*usb_module_info::set_configuration)(usb_device device, const usb_configuration_info *configuration) + \brief Change the current configuration. + + Changing the configuration will destroy all the current endpoints. If the + \a configuration points to the current configuration, the request will be + ignored and \c B_OK will be returned. + + \param device The id of the device you want to query. + \param configuration The pointer to the new configuration you want to set. + \retval B_OK The new configuration is set succesfully. + \retval B_DEV_INVALID_PIPE The \a device parameter is invalid. + \retval B_BAD_VALUE The configuration does not exist. + + \note This method also allows you to completely unconfigure the device, which + means that all the current endpoints, pipes and transfers will be freed. + Pass \c NULL to the parameter \a configuration if you want to do that. +*/ + +/*! + \fn status_t (*usb_module_info::set_alt_interface)(usb_device device, const usb_interface_info *interface) + \brief Set an alternative interface. Not implemented. + + This method currently always returns \c B_ERROR. +*/ + +/*! + \fn status_t (*usb_module_info::set_feature)(usb_id handle, uint16 selector) + \brief Convenience function for standard control pipe set feature requests. + + Both the set_feature() and clear_feature() requests work on all the Stack's + objects: devices, interfaces and pipes. + + \param handle The object you want to query. + \param selector The value you want to pass in the feature request. + \return \c B_OK in case the request succeeded and the device responded + positively, or an error code in case it failed. +*/ + +/*! + \fn status_t (*usb_module_info::clear_feature)(usb_id handle, uint16 selector) + \brief Convenience function for standard control pipe clear feature requests. + + \see set_feature() to see how this method works. +*/ + +/*! + \fn status_t (*usb_module_info::get_status)(usb_id handle, uint16 *status) + \brief Convenience function for standard usb status requests. + + \param[in] handle The object you want to query. + \param[out] status A variable in which the device can store it's status. + \return \c B_OK in case the request succeeded and the device responded + positively, or an error code in case it failed. +*/ + +/*! + \fn status_t (*usb_module_info::get_descriptor)(usb_device device, uint8 descriptorType, uint8 index, uint16 languageID, void *data, size_t dataLength, size_t *actualLength) + \brief Convenience function to get a descriptor from a device. + + \param[in] device The device you want to query. + \param[in] descriptorType The type of descriptor you are requesting. + \param[in] index In case there are multiple descriptors of this type, you + select which one you want. + \param[in] languageID The language you want the descriptor in (if applicable, + like with string_descriptors). + \param[out] data The buffer in which the descriptor can be written. + \param[in] dataLength The size of the buffer (in bytes). + \param[out] actualLength A pointer to a variable in which the actual number + of bytes written can be stored. + \retval B_OK The request succeeded, and the descriptor is written. + \retval B_DEV_INVALID_PIPE Invalid \a device parameter. + \retval "other errors" Request failed. +*/ + +/*! + \fn status_t (*usb_module_info::send_request)(usb_device device, uint8 requestType, uint8 request, uint16 value, uint16 index, uint16 length, void *data, size_t *actualLength) + \brief Send a generic, synchronous request over the default control pipe. + + See queue_request() for an asynchronous version of this method. + + Most of the standard values of a request are defined in USB_spec.h. + + \param[in] device The device you want to query. + \param[in] requestType The request type. + \param[in] request The request you want to perform. + \param[in] value The value of the request. + \param[in] index The index for the request. + \param[in] length The size of the buffer pointed by \a data + \param[out] data The buffer where to put the result in. + \param[out] actualLength The actual numbers of bytes written. + + \retval B_OK The request succeeded. + \retval B_DEV_INVALID_PIPE Invalid \a device parameter. + \retval "other errors" Request failed. +*/ + +/*! + \fn status_t (*usb_module_info::queue_interrupt)(usb_pipe pipe, void *data, size_t dataLength, usb_callback_func callback, void *callbackCookie) + \brief Asynchronously queue an interrupt transfer. + + \param pipe The id of the pipe you want to query. + \param data The data buffer you want to pass. + \param dataLength The size of the data buffer. + \param callback The callback function the stack should call after finishing. + \param callbackCookie A cookie that will be supplied to your callback + function when the transfer is finished. + + \return Whether or not the queueing of the transfer went well. The return + value won't tell you if the transfer actually succeeded. + \retval B_OK The interrupt transfer is queued. + \retval B_NO_MEMORY Error allocating objects. + \retval B_DEV_INVALID_PIPE The \a pipe is invalid. +*/ + +/*! + \fn status_t (*usb_module_info::queue_bulk)(usb_pipe pipe, void *data, size_t dataLength, usb_callback_func callback, void *callbackCookie) + \brief Asynchronously queue a bulk transfer. + + This method behaves like the queue_interrupt() method, except that it queues + a bulk transfer. +*/ + +/*! + \fn status_t (*usb_module_info::queue_bulk_v)(usb_pipe pipe, iovec *vector, size_t vectorCount, usb_callback_func callback, void *callbackCookie) + \brief Asynchronously queue a bulk vector. + + This method behaves like the queue_interrupt() method, except that it queues + bulk transfers and that it is based on an (array of) io vectors. + + \param vector One or more io vectors. IO vectors are standard POSIX entities. + \param vectorCount The number of elements in the \a vector array. +*/ + +/*! + \fn status_t (*usb_module_info::queue_isochronous)(usb_pipe pipe, void *data, size_t dataLength, usb_iso_packet_descriptor *packetDesc, uint32 packetCount, uint32 *startingFrameNumber, uint32 flags, usb_callback_func callback, void *callbackCookie) + \brief Asynchronously queue a isochronous transfer. Not implemented. + + Not implemented in the current Haiku USB Stack. +*/ + +/*! + \fn status_t (*usb_module_info::queue_request)(usb_device device, uint8 requestType, uint8 request, uint16 value, uint16 index, uint16 length, void *data, usb_callback_func callback, void *callbackCookie) + \brief Asynchronously queue a control pipe request. + + This method does roughly the same as send_request(), however, it works + asynchronously. This means that the method will return as soon as the + transfer is queued. + + \param callback The callback function for when the transfer is done. + \param callbackCookie The cookie that the stack should pass to your callback + function. + \return Whether or not the queueing of the transfer went well. The return + value won't tell you if the transfer actually succeeded. + \retval B_OK The control transfer is queued. + \retval B_NO_MEMORY Error allocating objects. + \retval B_DEV_INVALID_PIPE The \a callback is invalid. +*/ + +/*! + \fn status_t (*usb_module_info::set_pipe_policy)(usb_pipe pipe, uint8 maxNumQueuedPackets, uint16 maxBufferDurationMS, uint16 sampleSize) + \brief Set some pipe features. + + The USB standard specifies some properties that should be able to be set on + isochronous pipes. If your driver requires the properties to be changed, you + should use this method. + + \param pipe The id of the isochronous pipe you want to alter. + \param maxNumQueuedPackets The maximum number of queued packets allowed on + this pipe. + \param maxBufferDurationMS The maximum time in ms that the buffers are valid. + \param sampleSize The size of the samples through this pipe. + \retval B_OK Pipe policy changed. + \retval B_DEV_INVALID_PIPE The \a pipe argument is invalid or not an + isochronous pipe. +*/ + +/*! + \fn status_t (*usb_module_info::cancel_queued_transfers)(usb_pipe pipe) + \brief Cancel pending transfers. Not Implemented. + + Call this method to cancel pending transfers in a \a pipe. + + \warning This is currently not implemented! + + \param pipe The id of the pipe to clear. The method will always return + \c B_ERROR. +*/ + +/*! + \fn status_t (*usb_module_info::usb_ioctl)(uint32 opcode, void *buffer, size_t bufferSize) + \brief Low level commands to the USB stack. + + This method is used to give lowlevel commands to the Stack. There are + currently no uses documented. +*/ Added: haiku/trunk/docs/user/drivers/USB_spec.dox =================================================================== --- haiku/trunk/docs/user/drivers/USB_spec.dox 2007-04-16 06:48:38 UTC (rev 20723) +++ haiku/trunk/docs/user/drivers/USB_spec.dox 2007-04-16 09:28:29 UTC (rev 20724) @@ -0,0 +1,296 @@ +/* + * Copyright 2007, Haiku, Inc. All Rights Reserved. + * Distributed under the terms of the MIT License. + * + * Documentation by: + * Niels Sascha Reedijk + * Corresponds to: + * /trunk/headers/os/drivers/USB_spec.h rev 19915 + */ + +/*! + \file USB_spec.h + \brief General definitions as defined by the USB standard. +*/ + +/*! + \name Request Types: targets and direction + + These request types can be used in the usb_module_info::send_request() + and usb_module_info::queue_request() methods. They specifiy both the type + of interface and the direction of the transfer. + + These are usually combined with a category (found on this page). +*/ + +//! @{ + +/*! + \def USB_REQTYPE_DEVICE_IN + \brief Device. In. +*/ + +/*! + \def USB_REQTYPE_DEVICE_OUT + \brief Device. Out. +*/ + +/*! + \def USB_REQTYPE_INTERFACE_IN + \brief Interface. In. +*/ + +/*! + \def USB_REQTYPE_INTERFACE_OUT + \brief Interface. Out. +*/ + +/*! + \def USB_REQTYPE_ENDPOINT_IN + \brief Endpoint. In. +*/ + +/*! + \def USB_REQTYPE_ENDPOINT_OUT + \brief Endpoint. Out. +*/ + +/*! + \def USB_REQTYPE_OTHER_OUT + \brief Other. Out. +*/ + +/*! + \def USB_REQTYPE_OTHER_IN + \brief Other. In. +*/ + +//! @} + +/*! + \name Request Types: categories + + These request types can be used in the usb_module_info::send_request() + and usb_module_info::queue_request() methods. They specifiy the category + of the transfer. + + These are usually combined with a target and direction (found on this page). +*/ + +//! @{ + +/*! + \def USB_REQTYPE_STANDARD + \brief Request that adheres to the USB specifications. +*/ + +/*! + \def USB_REQTYPE_CLASS + \brief Request that adheres to the specifications of the class. +*/ + +/*! + \def USB_REQTYPE_VENDOR + \brief Request that is defined by the specifications of the vendor. +*/ + +/*! + \def USB_REQTYPE_RESERVED + \brief Reserved for special implementations. +*/ + +/*! + \def USB_REQTYPE_MASK + \brief Constant that can be used as mask over the requesttype field. +*/ + +//! @} + +/*! + \name Standard Request Values + + These request values are defined by the USB standard. You can use these + constants in both the usb_module_info::send_request() and + usb_module_info::queue_request() methods. + + \warning The stack handles most of these standard requests for you. Use the + supplied convenience functions the the usb_module_info interface rather than + doing the requests yourself. Some of these request may actually interfere + with the inner workings of the USB stack! +*/ + +//! @{ + +/*! + \def USB_REQUEST_GET_STATUS + \brief Get the status of a device. +*/ + +/*! + \def USB_REQUEST_CLEAR_FEATURE + \brief Clear a feature. +*/ + +/*! + \def USB_REQUEST_SET_FEATURE + \brief Set a feature. +*/ + +/*! + \def USB_REQUEST_SET_ADDRESS + \brief Set the device address. +*/ + +/*! + \def USB_REQUEST_GET_DESCRIPTOR + \brief Get a descriptor. +*/ + +/*! + \def USB_REQUEST_SET_DESCRIPTOR + \brief Update a descriptor to a supplied one. +*/ + +/*! + \def USB_REQUEST_GET_CONFIGURATION + \brief Get a configuration. +*/ + +/*! + \def USB_REQUEST_SET_CONFIGURATION + \brief Set the configuration. +*/ + +/*! + \def USB_REQUEST_GET_INTERFACE + \brief Request an interface descriptor. +*/ + +/*! + \def USB_REQUEST_SET_INTERFACE + \brief Set a specific interface. +*/ + +/*! + \def USB_REQUEST_SYNCH_FRAME + \brief Synchronize a frame. +*/ + +//! @} + +/*! + \name Descriptor Constants + + These constants refer to a specific descriptor. They can be used when + building a standard USB request for a descriptor, or in the + usb_module_info::get_descriptor() method. +*/ + +//! @{ + +/*! + \def USB_DESCRIPTOR_DEVICE + \brief Constant for the device descriptor. +*/ + +/*! + \def USB_DESCRIPTOR_CONFIGURATION + \brief Constant for a configuration descriptor. +*/ + +/*! + \def USB_DESCRIPTOR_STRING + \brief Constant for a string descriptor. +*/ + +/*! + \def USB_DESCRIPTOR_INTERFACE + \brief Constant for an interface descriptor. +*/ + +/*! + \def USB_DESCRIPTOR_ENDPOINT + \brief Constant for an endpoint descriptor. +*/ + +//! @} + +/*! + \name Feature Requests + + These constants refer to standard feature requests. You can use these using + the convenient usb_module_info::set_feature() and + usb_module_info::clear_feature() methods. +*/ + +//! @{ + +/*! + \def USB_FEATURE_DEVICE_REMOTE_WAKEUP + \brief Request a device to wakeup from remote calls. +*/ + +/*! + \def USB_FEATURE_ENDPOINT_HALT + \brief Request for a specific endpoint to halt. +*/ + +//! @} + +/*! + \name Endpoint Attributes + + These constants refer to values in the usb_endpoint_descriptor::attributes + field. +*/ + +//! @{ + +/*! + \def USB_ENDPOINT_ATTR_CONTROL + \brief Endpoint facilitates control transfers. +*/ + +/*! + \def USB_ENDPOINT_ATTR_ISOCHRONOUS + \brief Endpoint facilitates isochronous transfers. +*/ + +/*! + \def USB_ENDPOINT_ATTR_BULK + \brief Endpoint facilitates bulk transfers. +*/ + +/*! + \def USB_ENDPOINT_ATTR_INTERRUPT + \brief Endpoint facilitates interrupt transfers. +*/ + +/*! + \def USB_ENDPOINT_ATTR_MASK + \brief Constant to mask out transfer types. +*/ + +//! @} + +/*! + \name Endpoint Address + + These constants refer to the direction that is embedded in the + usb_endpoint_descriptor::address field. +*/ + +//! @{ + +/*! + \def USB_ENDPOINT_ADDR_DIR_IN + \brief The endpoint provides data for the driver. +*/ + +/*! + \def USB_ENDPOINT_ADDR_DIR_OUT + \brief The endpoint accepts data from the host. +*/ + +//! @} + Modified: haiku/trunk/docs/user/drivers/drivers.dox =================================================================== --- haiku/trunk/docs/user/drivers/drivers.dox 2007-04-16 06:48:38 UTC (rev 20723) +++ haiku/trunk/docs/user/drivers/drivers.dox 2007-04-16 09:28:29 UTC (rev 20724) @@ -4,5 +4,6 @@ \section topics Topics - \ref fs_modules +- \ref usb_modules */ Modified: haiku/trunk/docs/user/drivers/fs_interface.dox =================================================================== --- haiku/trunk/docs/user/drivers/fs_interface.dox 2007-04-16 06:48:38 UTC (rev 20723) +++ haiku/trunk/docs/user/drivers/fs_interface.dox 2007-04-16 09:28:29 UTC (rev 20724) @@ -325,7 +325,7 @@ For most FSs the permissions a user has are defined by the \c st_mode, \c st_uid, and \c st_gid fields of the node's stat data. As a special -exception, the root user (geteuid() == 0<\tt>) does always have +exception, the root user (geteuid() == 0) does always have read and write permissions, execution permission only when at least one of the execution permission bits are set. Added: haiku/trunk/docs/user/drivers/usb_modules.dox =================================================================== --- haiku/trunk/docs/user/drivers/usb_modules.dox 2007-04-16 06:48:38 UTC (rev 20723) +++ haiku/trunk/docs/user/drivers/usb_modules.dox 2007-04-16 09:28:29 UTC (rev 20724) @@ -0,0 +1,18 @@ +/* + * Copyright 2007, Haiku, Inc. All Rights Reserved. + * Distributed under the terms of the MIT License. + * + * Documentation by: + * Niels Sascha Reedijk + */ + +/*! + \page usb_modules Writing drivers for USB devices + + This page will describe how the Haiku USB stack is structured. +*/ + + + + + \ No newline at end of file Modified: haiku/trunk/docs/user/midi2/midi2intro.dox =================================================================== --- haiku/trunk/docs/user/midi2/midi2intro.dox 2007-04-16 06:48:38 UTC (rev 20723) +++ haiku/trunk/docs/user/midi2/midi2intro.dox 2007-04-16 09:28:29 UTC (rev 20724) @@ -287,12 +287,12 @@ - \ref Midi2Defs.h - Be Newsletter Volume 3, Issue 47 - Motor Mix sample code - Be Newsletter Volume 4, Issue 3 - Overview of the new kit -- OpenBeOS - Newsletter 33, Introduction to MIDI, Part 1 -- OpenBeOS - Newsletter 36, Introduction to MIDI, Part 2 +- Newsletter + 33, Introduction to MIDI, Part 1 +- Newsletter + 36, Introduction to MIDI, Part 2 - Sample code and other goodies at the - OpenBeOS Midi Kit team page + Haiku Midi Kit team page Information about MIDI in general: Added: haiku/trunk/docs/user/support/Archivable.dox =================================================================== --- haiku/trunk/docs/user/support/Archivable.dox 2007-04-16 06:48:38 UTC (rev 20723) +++ haiku/trunk/docs/user/support/Archivable.dox 2007-04-16 09:28:29 UTC (rev 20724) @@ -0,0 +1,172 @@ +/* + * Copyright 2007, Haiku, Inc. All Rights Reserved. + * Distributed under the terms of the MIT License. + * + * Documentation by: + * Niels Sascha Reedijk + * Corresponds to: + * /trunk/headers/os/support/Archivable.h rev 19972 + * /trunk/src/kits/support/Archivable.cpp rev 19095 + */ + +/*! + \file Archivable.h + \brief Provides the BArchivable interface. +*/ + +/*! + \class BArchivable + \ingroup support + \ingroup libbe + \brief Interfaced for objects that can be archived into a BMessage. + + BArchivable provides an interface for objects that can be archived into + messages and unarchived to objects in another location. By these means you + are able to send objects between applications, or even between computers over + networks. + + BArchivable differs from BFlattenable in way that BFlattenable is designed to + store objects to flat streams of data, where the main objective is storing it + to disk. The objective of this interface is to archive objects that will be + restored as objects. To illustrate that point, BArchivable messages know how + to restore itself, whereas BFlattenables have a datatype which you manually + need to map to classes. + + Archiving is done with the Archive() method. If your class support it, the + caller can request your class to to a deep archivation, which means that all + child objects should be stored. Unarchiving works with the Instantiate() + method, which is static. However, since the interface is designed to + unarchive objects without the caller knowing what kind of object it + actually is, the global function #instantiate_object() instantiates a message + without you manually having to determine the class the message is from. This + adds considerable flexibility and allows BArchivable to be used in + combination with add-ons. + + To provide this interface in your classes, you should publicly inherit this + class. You should reimplement Archive() and Instantiate(), and provide one + constructor that takes one BMessage argument. +*/ + +/*! + \fn BArchivable::BArchivable(BMessage* from) + \brief Constructor. Does nothing. + + If you inherit this interface, you should at least provide one constructor + that takes one BMessage argument. +*/ + +/*! [... truncated: 1801 lines follow ...] From marcusoverhagen at arcor.de Mon Apr 16 11:31:54 2007 From: marcusoverhagen at arcor.de (Marcus Overhagen) Date: Mon, 16 Apr 2007 11:31:54 +0200 (CEST) Subject: [Haiku-commits] r20721 - haiku/trunk/src/add-ons/kernel/drivers/network/etherpci In-Reply-To: <200704160427.l3G4Rm6J015134@sheep.berlios.de> References: <200704160427.l3G4Rm6J015134@sheep.berlios.de> Message-ID: <12749138.1176715914963.JavaMail.ngmail@webmail12> Hi Hugo, and Axel, and Travis, and enyone else reading this, the code doesn't look wrong to me (except for possible buffer overflow), but I expect it to have used a lot of stack space. What exactly were the symptoms, and how did you debug this? I think we should handle such cases gracefully (with a panic) I noticed we already use B_KERNEL_STACK_AREA as flags when creating the stack, and DEBUG_KERNEL_STACKS inside the VM. So why isn't this working? regards Marcus ----- Original Nachricht ---- Von: hugosantos at mail.berlios.de An: haiku-commits at lists.berlios.de Datum: 16.04.2007 06:27 Betreff: [Haiku-commits] r20721 - haiku/trunk/src/add-ons/kernel/drivers/network/etherpci > Author: hugosantos > Date: 2007-04-16 06:27:37 +0200 (Mon, 16 Apr 2007) > New Revision: 20721 > ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20721&view=rev > > Modified: > haiku/trunk/src/add-ons/kernel/drivers/network/etherpci/etherpci.c > Log: > made ETHER_DEBUG use dprintf() as the previous logic was screwing badly and > making the boot sequence hang in some setups (specifically qemu, may have > fixed issues with Parallels as well). > > > Modified: > haiku/trunk/src/add-ons/kernel/drivers/network/etherpci/etherpci.c > =================================================================== > --- haiku/trunk/src/add-ons/kernel/drivers/network/etherpci/etherpci.c > 2007-04-16 03:20:42 UTC (rev 20720) > +++ haiku/trunk/src/add-ons/kernel/drivers/network/etherpci/etherpci.c > 2007-04-16 04:27:37 UTC (rev 20721) > @@ -39,22 +39,11 @@ > /* diagnostic debug flags - compile in here or set while running with > debugger "AcmeRoadRunner" command */ > #define DEFAULT_DEBUG_FLAGS ( ERR | INFO | WARN | FUNCTION ) > > -//void ETHER_DEBUG(int32 debug_mask, int32 enabled, char * format, ...); > +#define ETHER_DEBUG(mask, enabled, format, args...) \ > + do { if (mask & enabled) \ > + dprintf(format , ##args); } while (0) > > -static void > -ETHER_DEBUG(int32 debug_mask, int32 enabled, char * format, ...) > -{ > - if (debug_mask & enabled) { > - va_list args; > - char s[4096]; > - va_start(args, format); > - vsprintf( s, format, args ); > - va_end(args); > - dprintf("%s",s); > - } > -} > > - > static pci_module_info *gPCIModInfo; > static char *gDevNameList[MAX_CARDS+1]; > static pci_info *gDevList[MAX_CARDS+1]; > > _______________________________________________ > Haiku-commits mailing list > Haiku-commits at lists.berlios.de > https://lists.berlios.de/mailman/listinfo/haiku-commits > 50? AMAZON-Einkaufsgutschein bei Bestellung von Arcor-DSL: Viel oder wenig? Schnell oder langsam? Unbegrenzt surfen + telefonieren ohne Zeit- und Volumenbegrenzung? DAS TOP ANGEBOT JETZT bei Arcor: g?nstig und schnell mit DSL - das All-Inclusive-Paket f?r clevere Doppel-Sparer, nur 39,85 ? inkl. DSL- und ISDN-Grundgeb?hr! http://www.arcor.de/rd/emf-dsl-2 From axeld at pinc-software.de Mon Apr 16 12:03:39 2007 From: axeld at pinc-software.de (Axel =?iso-8859-15?q?D=F6rfler?=) Date: Mon, 16 Apr 2007 12:03:39 +0200 CEST Subject: [Haiku-commits] r20721 - haiku/trunk/src/add-ons/kernel/drivers/network/etherpci In-Reply-To: <12749138.1176715914963.JavaMail.ngmail@webmail12> Message-ID: <11292609142-BeMail@zon> Marcus Overhagen wrote: > I think we should handle such cases gracefully (with a panic) > > I noticed we already use B_KERNEL_STACK_AREA as flags > when creating the stack, and DEBUG_KERNEL_STACKS inside > the VM. So why isn't this working? Writing over the kernel stack should indeed work - however, it should result in a double fault, since the fault handler cannot use the kernel stack anymore. Maybe that's what Hugo reported as "hang". Bye, Axel. From jackburton at mail.berlios.de Mon Apr 16 14:43:38 2007 From: jackburton at mail.berlios.de (jackburton at BerliOS) Date: Mon, 16 Apr 2007 14:43:38 +0200 Subject: [Haiku-commits] r20725 - haiku/trunk/src/tests/kits/opengl/direct_mode Message-ID: <200704161243.l3GChc1e013417@sheep.berlios.de> Author: jackburton Date: 2007-04-16 14:43:38 +0200 (Mon, 16 Apr 2007) New Revision: 20725 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20725&view=rev Modified: haiku/trunk/src/tests/kits/opengl/direct_mode/GLDirectMode.cpp Log: Calling LockGL() before BGLView::AttachedToWindow() isn't allowed, it seems, as it leads to a crash. The GLDirectMode test app now works. Modified: haiku/trunk/src/tests/kits/opengl/direct_mode/GLDirectMode.cpp =================================================================== --- haiku/trunk/src/tests/kits/opengl/direct_mode/GLDirectMode.cpp 2007-04-16 09:28:29 UTC (rev 20724) +++ haiku/trunk/src/tests/kits/opengl/direct_mode/GLDirectMode.cpp 2007-04-16 12:43:38 UTC (rev 20725) @@ -102,8 +102,8 @@ void SampleGLView::AttachedToWindow(void) { + BGLView::AttachedToWindow(); LockGL(); - BGLView::AttachedToWindow(); gInit(); gReshape(width, height); UnlockGL(); From philippe.houdoin at free.fr Mon Apr 16 14:48:05 2007 From: philippe.houdoin at free.fr (Philippe Houdoin) Date: Mon, 16 Apr 2007 14:48:05 +0200 Subject: [Haiku-commits] haiku/trunk/src/tests/kits/opengl/direct_mode Message-ID: <1176727685.46237085b3be2@imp.free.fr> > Author: jackburton > Date: 2007-04-16 14:43:38 +0200 (Mon, 16 Apr 2007) > New Revision: 20725 > ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20725&view=rev > > Modified: > haiku/trunk/src/tests/kits/opengl/direct_mode/GLDirectMode.cpp > Log: > Calling LockGL() before BGLView::AttachedToWindow() isn't allowed, it > seems, as it leads to a crash. The GLDirectMode test app now works. Then, we have a regression, since it works fine under R5. I'll investigate why. Meanwhile, I'm glad you've fixed this test app. - Philippe From hugosantos at gmail.com Mon Apr 16 14:57:46 2007 From: hugosantos at gmail.com (Hugo Santos) Date: Mon, 16 Apr 2007 13:57:46 +0100 Subject: [Haiku-commits] r20719 - haiku/trunk/src/add-ons/kernel/network/protocols/tcp In-Reply-To: <1087100721-BeMail@zon> References: <200704160320.l3G3KAlZ011443@sheep.berlios.de> <1087100721-BeMail@zon> Message-ID: <9c46321e0704160557m1bc9c74aya2a3913f3e790057@mail.gmail.com> Axel, I understand your motivation but i really think we should follow the names the RFC uses or at least maintain close to them. I'm saying this from personal experience where in the first days i had to keep going back and forward to check which of the TCP States was FIN1 and FIN2. I don't mind renaming them a bit, but at least the name should be very similiar if you don't mind. Hugo On 4/16/07, Axel D?rfler wrote: > hugosantos at mail.berlios.de wrote: > > support RFC 1323's TCP Timestamps (we are still not updating our > > estimator though). > > Nice! > > > + fReceivedTSval(0), > [...] > > + struct { > > + uint32 TSval; > > + uint32 TSecr; > > + } timestamp; > > }; > [...] > > + uint32 TSval; > > + uint32 TSecr; > > What about names that follow our coding style? :-) > Like: > TCPEndpoint::fReceivedTimestamp > tcp_option::struct timestamp { uint32 value; uint32 echo_reply; } > tcp_segment::timestamp_value > tcp_segment::timestamp_echo_reply > ? > > I can do those changes if you don't have the time. > > Bye, > Axel. > > _______________________________________________ > Haiku-commits mailing list > Haiku-commits at lists.berlios.de > https://lists.berlios.de/mailman/listinfo/haiku-commits > From hugosantos at gmail.com Mon Apr 16 15:02:26 2007 From: hugosantos at gmail.com (Hugo Santos) Date: Mon, 16 Apr 2007 14:02:26 +0100 Subject: [Haiku-commits] r20714 - in haiku/trunk: headers/private/net src/add-ons/kernel/network/protocols/ipv4 src/add-ons/kernel/network/protocols/udp src/add-ons/kernel/network/stack In-Reply-To: <1606011219-BeMail@zon> References: <200704152211.l3FMBWv5003863@sheep.berlios.de> <1606011219-BeMail@zon> Message-ID: <9c46321e0704160602h33feca26r2e9471cb7d2f3548@mail.gmail.com> Axel, Because this is a common operation for all datagram sockets (i.e. unbound). I would rather have this route and source address selection in one place than changing N places when we decide that something different or new stuff should be done in this step. It seems more cleaner to me to not repeat code and keep this functionality in one place. :-) Hugo On 4/16/07, Axel D?rfler wrote: > hugosantos at mail.berlios.de wrote: > > + net_route *route = NULL; > > + status_t status = get_buffer_route(domain, buffer, &route); > > + if (status < B_OK) > > + return status; > > + > > + status = module->send_routed_data(protocol, route, buffer); > > + put_route(domain, route); > > + return status; > > I still don't understand why UdpEndpoint::SendData() shouldn't look > like this. > It's far from complicated and looks a lot cleaner to me. > > Bye, > Axel. > > _______________________________________________ > Haiku-commits mailing list > Haiku-commits at lists.berlios.de > https://lists.berlios.de/mailman/listinfo/haiku-commits > From hugosantos at gmail.com Mon Apr 16 15:05:44 2007 From: hugosantos at gmail.com (Hugo Santos) Date: Mon, 16 Apr 2007 14:05:44 +0100 Subject: [Haiku-commits] r20721 - haiku/trunk/src/add-ons/kernel/drivers/network/etherpci In-Reply-To: <12749138.1176715914963.JavaMail.ngmail@webmail12> References: <200704160427.l3G4Rm6J015134@sheep.berlios.de> <12749138.1176715914963.JavaMail.ngmail@webmail12> Message-ID: <9c46321e0704160605l39c1a961tc9fcb35387a7ccc5@mail.gmail.com> Hi Marcus, The behaviour was very strange where a single printing line (with two format arguments) was hanging the boot in qemu. Commenting that line made it boot correctly. I do suspect from stack overflow as if printed a long line but removed the two arguments it was using it worked. Considering dprintf's behaviour is the same, i don't think it broke anything and it now works correctly. Let me know if you think something should be done differently. Hugo On 4/16/07, Marcus Overhagen wrote: > Hi Hugo, and Axel, and Travis, and enyone else reading this, > > the code doesn't look wrong to me (except for possible buffer overflow), > but I expect it to have used a lot of stack space. > > What exactly were the symptoms, and how did you debug this? > > I think we should handle such cases gracefully (with a panic) > > I noticed we already use B_KERNEL_STACK_AREA as flags > when creating the stack, and DEBUG_KERNEL_STACKS inside > the VM. So why isn't this working? > > regards > Marcus > > > ----- Original Nachricht ---- > Von: hugosantos at mail.berlios.de > An: haiku-commits at lists.berlios.de > Datum: 16.04.2007 06:27 > Betreff: [Haiku-commits] r20721 - > haiku/trunk/src/add-ons/kernel/drivers/network/etherpci > > > Author: hugosantos > > Date: 2007-04-16 06:27:37 +0200 (Mon, 16 Apr 2007) > > New Revision: 20721 > > ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20721&view=rev > > > > Modified: > > haiku/trunk/src/add-ons/kernel/drivers/network/etherpci/etherpci.c > > Log: > > made ETHER_DEBUG use dprintf() as the previous logic was screwing badly and > > making the boot sequence hang in some setups (specifically qemu, may have > > fixed issues with Parallels as well). > > > > > > Modified: > > haiku/trunk/src/add-ons/kernel/drivers/network/etherpci/etherpci.c > > =================================================================== > > --- haiku/trunk/src/add-ons/kernel/drivers/network/etherpci/etherpci.c > > 2007-04-16 03:20:42 UTC (rev 20720) > > +++ haiku/trunk/src/add-ons/kernel/drivers/network/etherpci/etherpci.c > > 2007-04-16 04:27:37 UTC (rev 20721) > > @@ -39,22 +39,11 @@ > > /* diagnostic debug flags - compile in here or set while running with > > debugger "AcmeRoadRunner" command */ > > #define DEFAULT_DEBUG_FLAGS ( ERR | INFO | WARN | FUNCTION ) > > > > -//void ETHER_DEBUG(int32 debug_mask, int32 enabled, char * format, ...); > > +#define ETHER_DEBUG(mask, enabled, format, args...) \ > > + do { if (mask & enabled) \ > > + dprintf(format , ##args); } while (0) > > > > -static void > > -ETHER_DEBUG(int32 debug_mask, int32 enabled, char * format, ...) > > -{ > > - if (debug_mask & enabled) { > > - va_list args; > > - char s[4096]; > > - va_start(args, format); > > - vsprintf( s, format, args ); > > - va_end(args); > > - dprintf("%s",s); > > - } > > -} > > > > - > > static pci_module_info *gPCIModInfo; > > static char *gDevNameList[MAX_CARDS+1]; > > static pci_info *gDevList[MAX_CARDS+1]; > > > > _______________________________________________ > > Haiku-commits mailing list > > Haiku-commits at lists.berlios.de > > https://lists.berlios.de/mailman/listinfo/haiku-commits > > > > 50? AMAZON-Einkaufsgutschein bei Bestellung von Arcor-DSL: > Viel oder wenig? Schnell oder langsam? Unbegrenzt surfen + telefonieren > ohne Zeit- und Volumenbegrenzung? DAS TOP ANGEBOT JETZT bei Arcor: g?nstig > und schnell mit DSL - das All-Inclusive-Paket f?r clevere Doppel-Sparer, > nur 39,85 ? inkl. DSL- und ISDN-Grundgeb?hr! > http://www.arcor.de/rd/emf-dsl-2 > _______________________________________________ > Haiku-commits mailing list > Haiku-commits at lists.berlios.de > https://lists.berlios.de/mailman/listinfo/haiku-commits > From marcusoverhagen at arcor.de Mon Apr 16 15:28:15 2007 From: marcusoverhagen at arcor.de (Marcus Overhagen) Date: Mon, 16 Apr 2007 15:28:15 +0200 (CEST) Subject: [Haiku-commits] r20721 - haiku/trunk/src/add-ons/kernel/drivers/network/etherpci In-Reply-To: <9c46321e0704160605l39c1a961tc9fcb35387a7ccc5@mail.gmail.com> References: <9c46321e0704160605l39c1a961tc9fcb35387a7ccc5@mail.gmail.com> <200704160427.l3G4Rm6J015134@sheep.berlios.de> <12749138.1176715914963.JavaMail.ngmail@webmail12> Message-ID: <13443642.1176730095556.JavaMail.ngmail@webmail18> Hi Hugo, please don't get me wrong. Your change was correct and is better code than the original solution. I just think we probably need to change something in the way the kernel manages thread stacks, to detect a possible overflow. regards Marcus ----- Original Nachricht ---- Von: Hugo Santos An: SVN commits to the Haiku source repository Datum: 16.04.2007 15:05 Betreff: Re: [Haiku-commits] r20721 - haiku/trunk/src/add-ons/kernel/drivers/network/etherpci > Hi Marcus, > > The behaviour was very strange where a single printing line (with > two format arguments) was hanging the boot in qemu. Commenting that > line made it boot correctly. I do suspect from stack overflow as if > printed a long line but removed the two arguments it was using it > worked. Considering dprintf's behaviour is the same, i don't think it > broke anything and it now works correctly. Let me know if you think > something should be done differently. > > Hugo > > On 4/16/07, Marcus Overhagen wrote: > > Hi Hugo, and Axel, and Travis, and enyone else reading this, > > > > the code doesn't look wrong to me (except for possible buffer overflow), > > but I expect it to have used a lot of stack space. > > > > What exactly were the symptoms, and how did you debug this? > > > > I think we should handle such cases gracefully (with a panic) > > > > I noticed we already use B_KERNEL_STACK_AREA as flags > > when creating the stack, and DEBUG_KERNEL_STACKS inside > > the VM. So why isn't this working? > > > > regards > > Marcus > > > > > > ----- Original Nachricht ---- > > Von: hugosantos at mail.berlios.de > > An: haiku-commits at lists.berlios.de > > Datum: 16.04.2007 06:27 > > Betreff: [Haiku-commits] r20721 - > > haiku/trunk/src/add-ons/kernel/drivers/network/etherpci > > > > > Author: hugosantos > > > Date: 2007-04-16 06:27:37 +0200 (Mon, 16 Apr 2007) > > > New Revision: 20721 > > > ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20721&view=rev > > > > > > Modified: > > > haiku/trunk/src/add-ons/kernel/drivers/network/etherpci/etherpci.c > > > Log: > > > made ETHER_DEBUG use dprintf() as the previous logic was screwing badly > and > > > making the boot sequence hang in some setups (specifically qemu, may > have > > > fixed issues with Parallels as well). > > > > > > > > > Modified: > > > haiku/trunk/src/add-ons/kernel/drivers/network/etherpci/etherpci.c > > > =================================================================== > > > --- haiku/trunk/src/add-ons/kernel/drivers/network/etherpci/etherpci.c > > > 2007-04-16 03:20:42 UTC (rev 20720) > > > +++ haiku/trunk/src/add-ons/kernel/drivers/network/etherpci/etherpci.c > > > 2007-04-16 04:27:37 UTC (rev 20721) > > > @@ -39,22 +39,11 @@ > > > /* diagnostic debug flags - compile in here or set while running with > > > debugger "AcmeRoadRunner" command */ > > > #define DEFAULT_DEBUG_FLAGS ( ERR | INFO | WARN | FUNCTION ) > > > > > > -//void ETHER_DEBUG(int32 debug_mask, int32 enabled, char * format, > ...); > > > +#define ETHER_DEBUG(mask, enabled, format, args...) \ > > > + do { if (mask & enabled) \ > > > + dprintf(format , ##args); } while (0) > > > > > > -static void > > > -ETHER_DEBUG(int32 debug_mask, int32 enabled, char * format, ...) > > > -{ > > > - if (debug_mask & enabled) { > > > - va_list args; > > > - char s[4096]; > > > - va_start(args, format); > > > - vsprintf( s, format, args ); > > > - va_end(args); > > > - dprintf("%s",s); > > > - } > > > -} > > > > > > - > > > static pci_module_info *gPCIModInfo; > > > static char *gDevNameList[MAX_CARDS+1]; > > > static pci_info *gDevList[MAX_CARDS+1]; > > > > > > _______________________________________________ > > > Haiku-commits mailing list > > > Haiku-commits at lists.berlios.de > > > https://lists.berlios.de/mailman/listinfo/haiku-commits > > > > > > > 50? AMAZON-Einkaufsgutschein bei Bestellung von Arcor-DSL: > > Viel oder wenig? Schnell oder langsam? Unbegrenzt surfen + telefonieren > > ohne Zeit- und Volumenbegrenzung? DAS TOP ANGEBOT JETZT bei Arcor: > g?nstig > > und schnell mit DSL - das All-Inclusive-Paket f?r clevere Doppel-Sparer, > > nur 39,85 ? inkl. DSL- und ISDN-Grundgeb?hr! > > http://www.arcor.de/rd/emf-dsl-2 > > _______________________________________________ > > Haiku-commits mailing list > > Haiku-commits at lists.berlios.de > > https://lists.berlios.de/mailman/listinfo/haiku-commits > > > _______________________________________________ > Haiku-commits mailing list > Haiku-commits at lists.berlios.de > https://lists.berlios.de/mailman/listinfo/haiku-commits > 50? AMAZON-Einkaufsgutschein bei Bestellung von Arcor-DSL: Viel oder wenig? Schnell oder langsam? Unbegrenzt surfen + telefonieren ohne Zeit- und Volumenbegrenzung? DAS TOP ANGEBOT JETZT bei Arcor: g?nstig und schnell mit DSL - das All-Inclusive-Paket f?r clevere Doppel-Sparer, nur 39,85 ? inkl. DSL- und ISDN-Grundgeb?hr! http://www.arcor.de/rd/emf-dsl-2 From hugosantos at mail.berlios.de Mon Apr 16 17:27:23 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Mon, 16 Apr 2007 17:27:23 +0200 Subject: [Haiku-commits] r20726 - haiku/trunk/src/add-ons/kernel/network/datalink_protocols/arp Message-ID: <200704161527.l3GFRNHL028269@sheep.berlios.de> Author: hugosantos Date: 2007-04-16 17:27:13 +0200 (Mon, 16 Apr 2007) New Revision: 20726 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20726&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/datalink_protocols/arp/arp.cpp Log: fixed arp's ClearQueue when an entry is rejected. Modified: haiku/trunk/src/add-ons/kernel/network/datalink_protocols/arp/arp.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/datalink_protocols/arp/arp.cpp 2007-04-16 12:43:38 UTC (rev 20725) +++ haiku/trunk/src/add-ons/kernel/network/datalink_protocols/arp/arp.cpp 2007-04-16 15:27:13 UTC (rev 20726) @@ -209,8 +209,9 @@ { BufferList::Iterator iterator = queue.GetIterator(); while (iterator.HasNext()) { - gBufferModule->free(iterator.Next()); + net_buffer *buffer = iterator.Next(); iterator.Remove(); + gBufferModule->free(buffer); } } From axeld at pinc-software.de Mon Apr 16 17:41:03 2007 From: axeld at pinc-software.de (Axel =?iso-8859-15?q?D=F6rfler?=) Date: Mon, 16 Apr 2007 17:41:03 +0200 CEST Subject: [Haiku-commits] =?iso-8859-15?q?r20719_-_haiku/trunk/src/add-ons/?= =?iso-8859-15?q?kernel/network/protocols/tcp?= In-Reply-To: <9c46321e0704160557m1bc9c74aya2a3913f3e790057@mail.gmail.com> Message-ID: <31536441397-BeMail@zon> "Hugo Santos" wrote: > I understand your motivation but i really think we should follow > the > names the RFC uses or at least maintain close to them. I'm saying > this > from personal experience where in the first days i had to keep going > back and forward to check which of the TCP States was FIN1 and FIN2. > I > don't mind renaming them a bit, but at least the name should be very > similiar if you don't mind. I agree that the FIN1/2 renaming was probably not a good decision because you usually implement from specs. However, this case is completely different, as the suggested names are (ugly) abbreviations. It doesn't hurt to write them out; it will ease reading, and make you understand the code without knowing the RFC in detail before. So yes, I do mind. Bye, Axel. From axeld at pinc-software.de Mon Apr 16 17:46:03 2007 From: axeld at pinc-software.de (Axel =?iso-8859-15?q?D=F6rfler?=) Date: Mon, 16 Apr 2007 17:46:03 +0200 CEST Subject: [Haiku-commits] =?iso-8859-15?q?r20714_-_in_haiku/trunk=3A_header?= =?iso-8859-15?q?s/private/net_src/add-ons/kernel/network/protocols/ipv4_s?= =?iso-8859-15?q?rc/add-ons/kernel/network/protocols/udp_src/add-ons/kerne?= =?iso-8859-15?q?l/network/stack?= In-Reply-To: <9c46321e0704160602h33feca26r2e9471cb7d2f3548@mail.gmail.com> Message-ID: <31836115933-BeMail@zon> "Hugo Santos" wrote: > Because this is a common operation for all datagram sockets (i.e. > unbound). I would rather have this route and source address selection > in one place than changing N places when we decide that something > different or new stuff should be done in this step. It seems more > cleaner to me to not repeat code and keep this functionality in one > place. :-) It's simple code, so I don't mind duplication. However, if you insist on it, I can surely live with this as well :) BTW a cleaner solution would then be to remove send_data() completely, and have the upper layer carry out the work needed to call send_routed_data(). But I don't know other protocols too well to be sure that this would be a good idea. Bye, Axel. From hugosantos at gmail.com Mon Apr 16 17:52:34 2007 From: hugosantos at gmail.com (Hugo Santos) Date: Mon, 16 Apr 2007 16:52:34 +0100 Subject: [Haiku-commits] r20714 - in haiku/trunk: headers/private/net src/add-ons/kernel/network/protocols/ipv4 src/add-ons/kernel/network/protocols/udp src/add-ons/kernel/network/stack In-Reply-To: <31836115933-BeMail@zon> References: <9c46321e0704160602h33feca26r2e9471cb7d2f3548@mail.gmail.com> <31836115933-BeMail@zon> Message-ID: <9c46321e0704160852k48ec42fcw86f4700df03e758@mail.gmail.com> I think we need send_data/send_routed_data for the time being as some protocols hold their own route reference (TCP) and thus call down directly to the next module's send_routed_data while others (unbound, UDP and IPv4 raw) need to resolve the route and thus work through send_data. Which is essentially what send_datagram does, the unbound sockets' dirty work. Hugo On 4/16/07, Axel D?rfler wrote: > "Hugo Santos" wrote: > > Because this is a common operation for all datagram sockets (i.e. > > unbound). I would rather have this route and source address selection > > in one place than changing N places when we decide that something > > different or new stuff should be done in this step. It seems more > > cleaner to me to not repeat code and keep this functionality in one > > place. :-) > > It's simple code, so I don't mind duplication. However, if you insist > on it, I can surely live with this as well :) > BTW a cleaner solution would then be to remove send_data() completely, > and have the upper layer carry out the work needed to call > send_routed_data(). But I don't know other protocols too well to be > sure that this would be a good idea. > > Bye, > Axel. > > _______________________________________________ > Haiku-commits mailing list > Haiku-commits at lists.berlios.de > https://lists.berlios.de/mailman/listinfo/haiku-commits > From hugosantos at gmail.com Mon Apr 16 17:55:06 2007 From: hugosantos at gmail.com (Hugo Santos) Date: Mon, 16 Apr 2007 16:55:06 +0100 Subject: [Haiku-commits] r20719 - haiku/trunk/src/add-ons/kernel/network/protocols/tcp In-Reply-To: <31536441397-BeMail@zon> References: <9c46321e0704160557m1bc9c74aya2a3913f3e790057@mail.gmail.com> <31536441397-BeMail@zon> Message-ID: <9c46321e0704160855u5695df3di2f455eff8e2200d0@mail.gmail.com> I was asking if you don't mind them remaining similiar, not as they are, which i suppose you don't. I can do this change later, but feel free to go ahead and do it yourself. I'm ok with it as long as the names reflect "timestamp value" and "timestamp reply". Hugo On 4/16/07, Axel D?rfler wrote: > "Hugo Santos" wrote: > > I understand your motivation but i really think we should follow > > the > > names the RFC uses or at least maintain close to them. I'm saying > > this > > from personal experience where in the first days i had to keep going > > back and forward to check which of the TCP States was FIN1 and FIN2. > > I > > don't mind renaming them a bit, but at least the name should be very > > similiar if you don't mind. > > I agree that the FIN1/2 renaming was probably not a good decision > because you usually implement from specs. > However, this case is completely different, as the suggested names are > (ugly) abbreviations. It doesn't hurt to write them out; it will ease > reading, and make you understand the code without knowing the RFC in > detail before. So yes, I do mind. > > Bye, > Axel. > > _______________________________________________ > Haiku-commits mailing list > Haiku-commits at lists.berlios.de > https://lists.berlios.de/mailman/listinfo/haiku-commits > From axeld at pinc-software.de Mon Apr 16 17:59:37 2007 From: axeld at pinc-software.de (Axel =?iso-8859-15?q?D=F6rfler?=) Date: Mon, 16 Apr 2007 17:59:37 +0200 CEST Subject: [Haiku-commits] =?iso-8859-15?q?r20714_-_in_haiku/trunk=3A_header?= =?iso-8859-15?q?s/private/net_src/add-ons/kernel/network/protocols/ipv4_s?= =?iso-8859-15?q?rc/add-ons/kernel/network/protocols/udp_src/add-ons/kerne?= =?iso-8859-15?q?l/network/stack?= In-Reply-To: <9c46321e0704160852k48ec42fcw86f4700df03e758@mail.gmail.com> Message-ID: <32650420152-BeMail@zon> "Hugo Santos" wrote: > I think we need send_data/send_routed_data for the time being as > some protocols hold their own route reference (TCP) and thus call > down > directly to the next module's send_routed_data while others (unbound, > UDP and IPv4 raw) need to resolve the route and thus work through > send_data. Which is essentially what send_datagram does, the unbound > sockets' dirty work. Indeed, one doesn't even have to look at other protocols for that :-) Bye, Axel. From geist at foobox.com Mon Apr 16 19:19:11 2007 From: geist at foobox.com (Travis Geiselbrecht) Date: Mon, 16 Apr 2007 10:19:11 -0700 Subject: [Haiku-commits] r20723 - in haiku/trunk/src/system/kernel: arch/x86 vm References: <200704160648.l3G6mc8B001024@sheep.berlios.de> <20070416111224.376.1@stippis.mshome.net> Message-ID: <003b01c7804b$6c947680$87020b0a@secretlevel.com> > Hi Travis, > > On 2007-04-16 at 08:48:38 [+0200], geist at BerliOS > > wrote: >> Author: geist >> Date: 2007-04-16 08:48:38 +0200 (Mon, 16 Apr 2007) >> New Revision: 20723 >> ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20723&view=rev >> >> Modified: >> haiku/trunk/src/system/kernel/arch/x86/arch_cpu.c >> haiku/trunk/src/system/kernel/arch/x86/arch_x86.S >> haiku/trunk/src/system/kernel/vm/vm.cpp >> Log: >> asm optimized user_memcpy(), which should help somewhat, since the old >> version was a byte-by-byte copy. > > your change seems to break binary compatibility. The runtime_loader says > something about having found the symbol "memcpy" but it is of the wrong > type. Err wait, what do you mean? On a clean haiku build you saw this? I can see why it might have this problem, but I didn't see it on my test build. I'll fix it tonight. Travis From kaoutsis at sch.gr Mon Apr 16 19:36:33 2007 From: kaoutsis at sch.gr (Kaoutsis) Date: Mon, 16 Apr 2007 20:36:33 +0300 EEST Subject: [Haiku-commits] =?utf-8?q?r20723_-_in_haiku/trunk/src/system/kern?= =?utf-8?q?el=3A_arch/x86_vm?= In-Reply-To: <003b01c7804b$6c947680$87020b0a@secretlevel.com> Message-ID: <943062335-BeMail@zoidberg> Travis Geiselbrecht> > Hi Travis, > > > > On 2007-04-16 at 08:48:38 [+0200], geist at BerliOS > > > > wrote: > >> Author: geist > >> Date: 2007-04-16 08:48:38 +0200 (Mon, 16 Apr 2007) > >> New Revision: 20723 > >> ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20723&view=rev > >> > >> Modified: > >> haiku/trunk/src/system/kernel/arch/x86/arch_cpu.c > >> haiku/trunk/src/system/kernel/arch/x86/arch_x86.S > >> haiku/trunk/src/system/kernel/vm/vm.cpp > >> Log: > >> asm optimized user_memcpy(), which should help somewhat, since the > > > old > >> version was a byte-by-byte copy. > > > > your change seems to break binary compatibility. The runtime_loader > > says > > something about having found the symbol "memcpy" but it is of the > > wrong > > type. > > Err wait, what do you mean? On a clean haiku build you saw this? I > can see > why it might have this problem, but I didn't see it on my test build. i can also confirm this: clean build with r20724. I saw this message when trying to run NetPositive from r5, at least. I am not sure for other apps. Bye, Vasilis From geist at foobox.com Mon Apr 16 19:41:41 2007 From: geist at foobox.com (Travis Geiselbrecht) Date: Mon, 16 Apr 2007 10:41:41 -0700 Subject: [Haiku-commits] r20723 - in haiku/trunk/src/system/kernel: arch/x86 vm References: <943062335-BeMail@zoidberg> Message-ID: <000501c7804e$8acacf20$87020b0a@secretlevel.com> > Travis Geiselbrecht> > Hi Travis, >> > >> > On 2007-04-16 at 08:48:38 [+0200], geist at BerliOS >> > >> > wrote: >> >> Author: geist >> >> Date: 2007-04-16 08:48:38 +0200 (Mon, 16 Apr 2007) >> >> New Revision: 20723 >> >> ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20723&view=rev >> >> >> >> Modified: >> >> haiku/trunk/src/system/kernel/arch/x86/arch_cpu.c >> >> haiku/trunk/src/system/kernel/arch/x86/arch_x86.S >> >> haiku/trunk/src/system/kernel/vm/vm.cpp >> >> Log: >> >> asm optimized user_memcpy(), which should help somewhat, since the >> > > old >> >> version was a byte-by-byte copy. >> > >> > your change seems to break binary compatibility. The runtime_loader >> > says >> > something about having found the symbol "memcpy" but it is of the >> > wrong >> > type. >> >> Err wait, what do you mean? On a clean haiku build you saw this? I >> can see >> why it might have this problem, but I didn't see it on my test build. > > i can also confirm this: clean build with r20724. I saw this message > when > trying to run NetPositive from r5, at least. I am not sure for other > apps. > Bye, > Vasilis Run Netpositive from r5? What does that have to do with haiku? Travis From superstippi at gmx.de Mon Apr 16 19:44:26 2007 From: superstippi at gmx.de (Stephan Assmus) Date: Mon, 16 Apr 2007 19:44:26 +0200 Subject: [Haiku-commits] r20723 - in haiku/trunk/src/system/kernel: arch/x86 vm In-Reply-To: <000501c7804e$8acacf20$87020b0a@secretlevel.com> References: <943062335-BeMail@zoidberg> <000501c7804e$8acacf20$87020b0a@secretlevel.com> Message-ID: <20070416194426.6142.3@stippis.mshome.net> On 2007-04-16 at 19:41:41 [+0200], Travis Geiselbrecht wrote: > > Travis Geiselbrecht> > Hi Travis, > >> > > >> > On 2007-04-16 at 08:48:38 [+0200], geist at BerliOS > >> > > >> > wrote: > >> >> Author: geist > >> >> Date: 2007-04-16 08:48:38 +0200 (Mon, 16 Apr 2007) > >> >> New Revision: 20723 > >> >> ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20723&view=rev > >> >> > >> >> Modified: > >> >> haiku/trunk/src/system/kernel/arch/x86/arch_cpu.c > >> >> haiku/trunk/src/system/kernel/arch/x86/arch_x86.S > >> >> haiku/trunk/src/system/kernel/vm/vm.cpp > >> >> Log: > >> >> asm optimized user_memcpy(), which should help somewhat, since the > >> > > old > >> >> version was a byte-by-byte copy. > >> > > >> > your change seems to break binary compatibility. The runtime_loader > >> > says > >> > something about having found the symbol "memcpy" but it is of the > >> > wrong > >> > type. > >> > >> Err wait, what do you mean? On a clean haiku build you saw this? I > >> can see > >> why it might have this problem, but I didn't see it on my test build. > > > > i can also confirm this: clean build with r20724. I saw this message > > when > > trying to run NetPositive from r5, at least. I am not sure for other > > apps. > > Bye, > > Vasilis > > Run Netpositive from r5? What does that have to do with haiku? Well, it used to work (running Net+ on Haiku). :-) After your commit, it doesn't anymore. The same problem appears to affect the binary R5 driver for my epro100 nic. After your change, it is not loaded anymore. Best regards, -Stephan From geist at foobox.com Mon Apr 16 20:15:12 2007 From: geist at foobox.com (Travis Geiselbrecht) Date: Mon, 16 Apr 2007 11:15:12 -0700 Subject: [Haiku-commits] r20723 - in haiku/trunk/src/system/kernel: arch/x86 vm References: <943062335-BeMail@zoidberg> <000501c7804e$8acacf20$87020b0a@secretlevel.com> <20070416194426.6142.3@stippis.mshome.net> Message-ID: <000501c78053$3370a650$87020b0a@secretlevel.com> >> Run Netpositive from r5? What does that have to do with haiku? > > Well, it used to work (running Net+ on Haiku). :-) After your commit, it > doesn't anymore. The same problem appears to affect the binary R5 driver > for my epro100 nic. After your change, it is not loaded anymore. Oh I read it wrong. I read it as running NetPositive on r5, which has nothing to do with haiku. Yeah I know the problem, but I can't get to my machine until tonight. From hugosantos at mail.berlios.de Mon Apr 16 20:33:17 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Mon, 16 Apr 2007 20:33:17 +0200 Subject: [Haiku-commits] r20727 - haiku/trunk/src/add-ons/kernel/network/protocols/tcp Message-ID: <200704161833.l3GIXH23024578@sheep.berlios.de> Author: hugosantos Date: 2007-04-16 20:32:49 +0200 (Mon, 16 Apr 2007) New Revision: 20727 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20727&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/BufferQueue.h haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.cpp haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.h Log: assorted TCP fixes. - fixed the locking for spawned connections and accept()s. - return EMSGSIZE if the user is trying to write more data than the send buffer can hold. - fixed a crash when receiving a RST while the connection is being closed. - don't wake up readers when the connection gets established. - endpoint managers lock must be recursive to properly work with spawn'ed sockets. Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/BufferQueue.h =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/BufferQueue.h 2007-04-16 15:27:13 UTC (rev 20726) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/BufferQueue.h 2007-04-16 18:32:49 UTC (rev 20727) @@ -45,6 +45,7 @@ size_t Used() const { return fNumBytes; } size_t Free() const { return fMaxBytes - fNumBytes; } + size_t Size() const { return fMaxBytes; } bool IsContiguous() const { return fNumBytes == fContiguousBytes; } Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-16 15:27:13 UTC (rev 20726) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-16 18:32:49 UTC (rev 20727) @@ -256,6 +256,7 @@ TCPEndpoint::Close() { TRACE("Close()"); + RecursiveLocker lock(fLock); if (fState == LISTEN) @@ -270,8 +271,6 @@ if (status != B_OK) return status; - TRACE("Close() after Shutdown()"); - if (socket->options & SO_LINGER) { TRACE("Close(): Lingering for %i secs", socket->linger); @@ -299,6 +298,8 @@ { TRACE("Free()"); + RecursiveLocker _(fLock); + if (fState <= SYNCHRONIZE_SENT || fState == TIME_WAIT) return B_OK; @@ -319,7 +320,7 @@ TRACE("Connect() on address %s", AddressString(Domain(), address, true).Data()); - RecursiveLocker locker(&fLock); + RecursiveLocker locker(fLock); // Can only call connect() from CLOSED or LISTEN states // otherwise endpoint is considered already connected @@ -391,11 +392,8 @@ return EINPROGRESS; } - while (status == B_OK && fState != ESTABLISHED) - status = fSendList.Wait(locker, absolute_timeout(timeout)); - + status = _WaitForEstablished(locker, absolute_timeout(timeout)); TRACE(" Connect(): Connection complete: %s", strerror(status)); - return posix_error(status); } @@ -405,15 +403,20 @@ { TRACE("Accept()"); + RecursiveLocker locker(fLock); + status_t status; bigtime_t timeout = absolute_timeout(socket->receive.timeout); do { - status = acquire_sem_etc(fAcceptSemaphore, 1, B_ABSOLUTE_TIMEOUT | - B_CAN_INTERRUPT, timeout); + locker.Unlock(); + + status = acquire_sem_etc(fAcceptSemaphore, 1, B_ABSOLUTE_TIMEOUT + | B_CAN_INTERRUPT, timeout); if (status < B_OK) return status; + locker.Lock(); status = gSocketModule->dequeue_connected(socket, _acceptedSocket); if (status == B_OK) TRACE(" Accept() returning %p", (*_acceptedSocket)->first_protocol); @@ -429,11 +432,11 @@ if (address == NULL) return B_BAD_VALUE; + RecursiveLocker lock(fLock); + TRACE("Bind() on address %s", AddressString(Domain(), address, true).Data()); - RecursiveLocker lock(fLock); - if (fState != CLOSED) return EISCONN; @@ -478,6 +481,9 @@ return EDESTADDRREQ; fAcceptSemaphore = create_sem(0, "tcp accept"); + if (fAcceptSemaphore < B_OK) + return ENOBUFS; + fState = LISTEN; return B_OK; } @@ -524,6 +530,9 @@ } if (buffer->size > 0) { + if (buffer->size > fSendQueue.Size()) + return EMSGSIZE; + bigtime_t timeout = absolute_timeout(socket->send.timeout); while (fSendQueue.Free() < buffer->size) { @@ -579,12 +588,9 @@ if (flags & MSG_DONTWAIT) return B_WOULD_BLOCK; - while (fState != ESTABLISHED) { - // we need to wait until the connection becomes established - status_t status = fSendList.Wait(locker, timeout); - if (status < B_OK) - return posix_error(status); - } + status_t status = _WaitForEstablished(locker, timeout); + if (status < B_OK) + return posix_error(status); } size_t dataNeeded = socket->receive.low_water_mark; @@ -727,10 +733,9 @@ int32 -TCPEndpoint::ListenReceive(tcp_segment_header &segment, net_buffer *buffer) +TCPEndpoint::_ListenReceive(tcp_segment_header &segment, net_buffer *buffer) { - TRACE("ListenReceive(): packet %p (%lu bytes) with flags 0x%x, seq %lu, ack %lu!", - buffer, buffer->size, segment.flags, segment.sequence, segment.acknowledge); + TRACE("ListenReceive()"); // Essentially, we accept only TCP_FLAG_SYNCHRONIZE in this state, // but the error behaviour differs @@ -753,60 +758,71 @@ AddressModule()->set_to((sockaddr *)&newSocket->peer, (sockaddr *)&buffer->source); - TCPEndpoint *endpoint = (TCPEndpoint *)newSocket->first_protocol; + return ((TCPEndpoint *)newSocket->first_protocol)->Spawn(this, segment, buffer); +} - endpoint->fSpawned = true; +int32 +TCPEndpoint::Spawn(TCPEndpoint *parent, tcp_segment_header &segment, + net_buffer *buffer) +{ + RecursiveLocker _(fLock); + + fState = SYNCHRONIZE_RECEIVED; + fManager = parent->fManager; + + TRACE("Spawn()"); + + fSpawned = true; + + sockaddr *local = (sockaddr *)&socket->address; + sockaddr *peer = (sockaddr *)&socket->peer; + // TODO: proper error handling! - endpoint->fRoute = gDatalinkModule->get_route(Domain(), - (sockaddr *)&newSocket->peer); - if (endpoint->fRoute == NULL) + fRoute = gDatalinkModule->get_route(Domain(), peer); + if (fRoute == NULL) return DROP; - if (fManager->SetConnection(endpoint, (sockaddr *)&buffer->destination, - (sockaddr *)&buffer->source, NULL) < B_OK) + if (fManager->SetConnection(this, local, peer, NULL) < B_OK) return DROP; - endpoint->fInitialReceiveSequence = segment.sequence; - endpoint->fReceiveQueue.SetInitialSequence(segment.sequence + 1); - endpoint->fState = SYNCHRONIZE_RECEIVED; - endpoint->fAcceptSemaphore = fAcceptSemaphore; - endpoint->fReceiveMaxSegmentSize = _GetMSS((sockaddr *)&newSocket->peer); + fInitialReceiveSequence = segment.sequence; + fReceiveQueue.SetInitialSequence(segment.sequence + 1); + fAcceptSemaphore = parent->fAcceptSemaphore; + fReceiveMaxSegmentSize = _GetMSS(peer); // 40 bytes for IP and TCP header without any options // TODO: make this depending on the RTF_LOCAL flag? - endpoint->fReceiveNext = segment.sequence + 1; + fReceiveNext = segment.sequence + 1; // account for the extra sequence number for the synchronization - endpoint->fInitialSendSequence = system_time() >> 4; - endpoint->fSendNext = endpoint->fInitialSendSequence; - endpoint->fSendUnacknowledged = endpoint->fSendNext; - endpoint->fSendMax = endpoint->fSendNext; + fInitialSendSequence = system_time() >> 4; + fSendNext = fInitialSendSequence; + fSendUnacknowledged = fSendNext; + fSendMax = fSendNext; // set options - if ((fOptions & TCP_NOOPT) == 0) { + if ((parent->fOptions & TCP_NOOPT) == 0) { if (segment.max_segment_size > 0) - endpoint->fSendMaxSegmentSize = segment.max_segment_size; + fSendMaxSegmentSize = segment.max_segment_size; else - endpoint->fReceiveMaxSegmentSize = TCP_DEFAULT_MAX_SEGMENT_SIZE; + fReceiveMaxSegmentSize = TCP_DEFAULT_MAX_SEGMENT_SIZE; if (segment.has_window_shift) { - endpoint->fFlags |= FLAG_OPTION_WINDOW_SHIFT; - endpoint->fSendWindowShift = segment.window_shift; + fFlags |= FLAG_OPTION_WINDOW_SHIFT; + fSendWindowShift = segment.window_shift; } else { - endpoint->fFlags &= ~FLAG_OPTION_WINDOW_SHIFT; - endpoint->fReceiveWindowShift = 0; + fFlags &= ~FLAG_OPTION_WINDOW_SHIFT; + fReceiveWindowShift = 0; } } - TRACE(" ListenReceive() created new endpoint %p", endpoint); + _UpdateTimestamps(segment, 0, false); - endpoint->_UpdateTimestamps(segment, 0, false); - // send SYN+ACK - status_t status = endpoint->_SendQueued(); + status_t status = _SendQueued(); - endpoint->fInitialSendSequence = endpoint->fSendNext; - endpoint->fSendQueue.SetInitialSequence(endpoint->fSendNext); + fInitialSendSequence = fSendNext; + fSendQueue.SetInitialSequence(fSendNext); if (status < B_OK) return DROP; @@ -814,16 +830,14 @@ segment.flags &= ~TCP_FLAG_SYNCHRONIZE; // we handled this flag now, it must not be set for further processing - return endpoint->_Receive(segment, buffer); - // TODO: here, the ack/delayed ack call will be made on the parent socket! + return _Receive(segment, buffer); } int32 -TCPEndpoint::SynchronizeSentReceive(tcp_segment_header &segment, net_buffer *buffer) +TCPEndpoint::_SynchronizeSentReceive(tcp_segment_header &segment, net_buffer *buffer) { - TRACE("SynchronizeSentReceive(): packet %p (%lu bytes) with flags 0x%x, seq %lu, ack %lu!", - buffer, buffer->size, segment.flags, segment.sequence, segment.acknowledge); + TRACE("SynchronizeSentReceive()"); if ((segment.flags & TCP_FLAG_ACKNOWLEDGE) != 0 && (fInitialSendSequence >= segment.acknowledge @@ -859,16 +873,7 @@ } if (segment.flags & TCP_FLAG_ACKNOWLEDGE) { - // the connection has been established - fState = ESTABLISHED; - - if (socket->parent != NULL) { - gSocketModule->set_connected(socket); - release_sem_etc(fAcceptSemaphore, 1, B_DO_NOT_RESCHEDULE); - } - - fSendList.Signal(); - _NotifyReader(); + _MarkEstablished(); } else { // simultaneous open fState = SYNCHRONIZE_RECEIVED; @@ -884,13 +889,50 @@ int32 -TCPEndpoint::Receive(tcp_segment_header &segment, net_buffer *buffer) +TCPEndpoint::SegmentReceived(tcp_segment_header &segment, net_buffer *buffer) { - TRACE("Receive(): packet %p (%lu bytes) with flags 0x%x, seq %lu, ack %lu!", - buffer, buffer->size, segment.flags, segment.sequence, segment.acknowledge); + RecursiveLocker locker(fLock); - // TODO: rethink locking! + TRACE("SegmentReceived(): packet %p (%lu bytes) with flags 0x%x, seq %lu, " + "ack %lu", buffer, buffer->size, segment.flags, segment.sequence, + segment.acknowledge); + int32 segmentAction = DROP; + + switch (fState) { + case LISTEN: + segmentAction = _ListenReceive(segment, buffer); + break; + + case SYNCHRONIZE_SENT: + segmentAction = _SynchronizeSentReceive(segment, buffer); + break; + + case SYNCHRONIZE_RECEIVED: + case ESTABLISHED: + case FINISH_RECEIVED: + case WAIT_FOR_FINISH_ACKNOWLEDGE: + case FINISH_SENT: + case FINISH_ACKNOWLEDGED: + case CLOSING: + case TIME_WAIT: + case CLOSED: + segmentAction = _SegmentReceived(segment, buffer); + break; + } + + // process acknowledge action as asked for by the *Receive() method + if (segmentAction & IMMEDIATE_ACKNOWLEDGE) + SendAcknowledge(); + else if (segmentAction & ACKNOWLEDGE) + DelayedAcknowledge(); + + return segmentAction; +} + +int32 +TCPEndpoint::_SegmentReceived(tcp_segment_header &segment, net_buffer *buffer) +{ uint32 advertisedWindow = (uint32)segment.advertised_window << fSendWindowShift; // First, handle the most common case for uni-directional data transfer @@ -1287,23 +1329,15 @@ if (fLastAcknowledgeSent <= segment.sequence && tcp_sequence(segment.sequence) < (fLastAcknowledgeSent + fReceiveWindow)) { - if (fState == SYNCHRONIZE_RECEIVED) { - // TODO: if we came from SYN-SENT signal connection refused - // and remove all segments from tx queue - } else if (fState == ESTABLISHED || fState == FINISH_SENT - || fState == FINISH_RECEIVED || fState == FINISH_ACKNOWLEDGED) { - // TODO: RFC 793 states that on ESTABLISHED, FIN-WAIT{1,2} - // or CLOSE-WAIT "All segment queues should be - // flushed". - } + if (fState == SYNCHRONIZE_RECEIVED) + fError = ECONNREFUSED; + else if (fState == CLOSING || fState == TIME_WAIT + || fState == WAIT_FOR_FINISH_ACKNOWLEDGE) + fError = ENOTCONN; + else + fError = ECONNRESET; - if (fState != TIME_WAIT && fReceiveQueue.Available() > 0) { - _NotifyReader(); - } else { - return DELETE | DROP; - } - - fError = ECONNREFUSED; + _NotifyReader(); fState = CLOSED; } @@ -1371,15 +1405,7 @@ // process acknowledged data if (fState == SYNCHRONIZE_RECEIVED) { // TODO: window scaling! - if (socket->parent != NULL) { - gSocketModule->set_connected(socket); - release_sem_etc(fAcceptSemaphore, 1, B_DO_NOT_RESCHEDULE); - } - - fState = ESTABLISHED; - - fSendList.Signal(); - _NotifyReader(); + _MarkEstablished(); } if (fSendMax < segment.acknowledge || fState == TIME_WAIT) @@ -1536,6 +1562,33 @@ } +void +TCPEndpoint::_MarkEstablished() +{ + fState = ESTABLISHED; + + if (socket->parent != NULL) { + gSocketModule->set_connected(socket); + release_sem_etc(fAcceptSemaphore, 1, B_DO_NOT_RESCHEDULE); + } + + fSendList.Signal(); +} + + +status_t +TCPEndpoint::_WaitForEstablished(RecursiveLocker &locker, bigtime_t timeout) +{ + while (fState != ESTABLISHED) { + status_t status = fSendList.Wait(locker, timeout); + if (status < B_OK) + return status; + } + + return B_OK; +} + + // #pragma mark - timer @@ -1544,7 +1597,7 @@ { TCPEndpoint *endpoint = (TCPEndpoint *)data; - RecursiveLocker locker(endpoint->Lock()); + RecursiveLocker locker(endpoint->fLock); if (!locker.IsLocked()) return; @@ -1559,7 +1612,7 @@ { TCPEndpoint *endpoint = (TCPEndpoint *)data; - RecursiveLocker locker(endpoint->Lock()); + RecursiveLocker locker(endpoint->fLock); if (!locker.IsLocked()) return; @@ -1572,7 +1625,7 @@ { TCPEndpoint *endpoint = (TCPEndpoint *)data; - RecursiveLocker locker(endpoint->Lock()); + RecursiveLocker locker(endpoint->fLock); if (!locker.IsLocked()) return; @@ -1585,7 +1638,7 @@ { TCPEndpoint *endpoint = (TCPEndpoint *)data; - if (recursive_lock_lock(&endpoint->Lock()) < B_OK) + if (recursive_lock_lock(&endpoint->fLock) < B_OK) return; endpoint->DeleteSocket(); Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h 2007-04-16 15:27:13 UTC (rev 20726) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h 2007-04-16 18:32:49 UTC (rev 20727) @@ -45,8 +45,6 @@ status_t InitCheck() const; - recursive_lock &Lock() { return fLock; } - status_t Open(); status_t Close(); status_t Free(); @@ -69,10 +67,10 @@ status_t DelayedAcknowledge(); status_t SendAcknowledge(); status_t UpdateTimeWait(); - int32 ListenReceive(tcp_segment_header& segment, net_buffer *buffer); - int32 SynchronizeSentReceive(tcp_segment_header& segment, + + int32 SegmentReceived(tcp_segment_header& segment, net_buffer *buffer); + int32 Spawn(TCPEndpoint *parent, tcp_segment_header& segment, net_buffer *buffer); - int32 Receive(tcp_segment_header& segment, net_buffer *buffer); net_domain *Domain() const { return socket->first_protocol->module->get_domain( @@ -94,9 +92,15 @@ ssize_t _AvailableData() const; void _NotifyReader(); bool _ShouldReceive() const; + int32 _ListenReceive(tcp_segment_header& segment, net_buffer *buffer); + int32 _SynchronizeSentReceive(tcp_segment_header& segment, + net_buffer *buffer); + int32 _SegmentReceived(tcp_segment_header& segment, net_buffer *buffer); int32 _Receive(tcp_segment_header& segment, net_buffer *buffer); void _UpdateTimestamps(tcp_segment_header& segment, size_t segmentLength, bool checkSequence); + void _MarkEstablished(); + status_t _WaitForEstablished(RecursiveLocker &lock, bigtime_t timeout); static void _TimeWaitTimer(net_timer *timer, void *data); static void _RetransmitTimer(net_timer *timer, void *data); Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.cpp 2007-04-16 15:27:13 UTC (rev 20726) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.cpp 2007-04-16 18:32:49 UTC (rev 20727) @@ -53,7 +53,7 @@ // protocol cookie, so we don't have to go through the list // for each segment. typedef DoublyLinkedList EndpointManagerList; -static benaphore sEndpointManagersLock; +static recursive_lock sEndpointManagersLock; static EndpointManagerList sEndpointManagers; @@ -536,7 +536,7 @@ bufferHeader.Remove(headerLength); // we no longer need to keep the header around - BenaphoreLocker _(sEndpointManagersLock); + RecursiveLocker _(sEndpointManagersLock); EndpointManager *endpointManager = endpoint_manager_for(domain); if (endpointManager == NULL) @@ -547,40 +547,9 @@ TCPEndpoint *endpoint = endpointManager->FindConnection( (sockaddr *)&buffer->destination, (sockaddr *)&buffer->source); - if (endpoint != NULL) { - RecursiveLocker locker(endpoint->Lock()); - TRACE(("Endpoint %p in state %s\n", endpoint, name_for_state(endpoint->State()))); - - switch (endpoint->State()) { - case LISTEN: - segmentAction = endpoint->ListenReceive(segment, buffer); - break; - - case SYNCHRONIZE_SENT: - segmentAction = endpoint->SynchronizeSentReceive(segment, buffer); - break; - - case SYNCHRONIZE_RECEIVED: - case ESTABLISHED: - case FINISH_RECEIVED: - case WAIT_FOR_FINISH_ACKNOWLEDGE: - case FINISH_SENT: - case FINISH_ACKNOWLEDGED: - case CLOSING: - case TIME_WAIT: - case CLOSED: - segmentAction = endpoint->Receive(segment, buffer); - break; - } - - // process acknowledge action as asked for by the *Receive() method - if (segmentAction & IMMEDIATE_ACKNOWLEDGE) - endpoint->SendAcknowledge(); - else if (segmentAction & ACKNOWLEDGE) - endpoint->DelayedAcknowledge(); - else if (segmentAction & DELETE) - endpoint->DeleteSocket(); - } else if ((segment.flags & TCP_FLAG_RESET) == 0) + if (endpoint != NULL) + segmentAction = endpoint->SegmentReceived(segment, buffer); + else if ((segment.flags & TCP_FLAG_RESET) == 0) segmentAction = DROP | RESET; if (segmentAction & RESET) { @@ -615,7 +584,7 @@ static status_t tcp_init() { - status_t status = benaphore_init(&sEndpointManagersLock, + status_t status = recursive_lock_init(&sEndpointManagersLock, "endpoint managers lock"); if (status < B_OK) @@ -647,7 +616,7 @@ static status_t tcp_uninit() { - benaphore_destroy(&sEndpointManagersLock); + recursive_lock_destroy(&sEndpointManagersLock); return B_OK; } Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.h =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.h 2007-04-16 15:27:13 UTC (rev 20726) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/tcp.h 2007-04-16 18:32:49 UTC (rev 20727) @@ -165,7 +165,6 @@ RESET = 0x02, ACKNOWLEDGE = 0x04, IMMEDIATE_ACKNOWLEDGE = 0x08, - DELETE = 0x10, }; From korli at mail.berlios.de Mon Apr 16 21:15:47 2007 From: korli at mail.berlios.de (korli at BerliOS) Date: Mon, 16 Apr 2007 21:15:47 +0200 Subject: [Haiku-commits] r20728 - in haiku/trunk: headers/private/media src/kits/support src/servers/media src/servers/media_addon Message-ID: <200704161915.l3GJFlrT027060@sheep.berlios.de> Author: korli Date: 2007-04-16 21:15:46 +0200 (Mon, 16 Apr 2007) New Revision: 20728 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20728&view=rev Added: haiku/trunk/headers/private/media/MediaSounds.h Modified: haiku/trunk/headers/private/media/DataExchange.h haiku/trunk/src/kits/support/Beep.cpp haiku/trunk/src/servers/media/MMediaFilesManager.cpp haiku/trunk/src/servers/media/MMediaFilesManager.h haiku/trunk/src/servers/media/media_server.cpp haiku/trunk/src/servers/media_addon/main.cpp Log: added default sound events implemented system_beep() by sending an event to the media addon server Modified: haiku/trunk/headers/private/media/DataExchange.h =================================================================== --- haiku/trunk/headers/private/media/DataExchange.h 2007-04-16 18:32:49 UTC (rev 20727) +++ haiku/trunk/headers/private/media/DataExchange.h 2007-04-16 19:15:46 UTC (rev 20728) @@ -75,9 +75,14 @@ MEDIA_SERVER_GET_FORMATS, MEDIA_SERVER_MAKE_FORMAT_FOR, - MEDIA_SERVER_SYSTEM_BEEP_EVENT + // add_system_beep_event() + MEDIA_SERVER_ADD_SYSTEM_BEEP_EVENT, + + // media addon server + MEDIA_ADDON_SERVER_PLAY_MEDIA = '_TRU' }; + // Raw port based communication enum { ADDONSERVER_RESCAN_MEDIAADDON_FLAVORS = 0x50, @@ -1014,10 +1019,4 @@ { }; - - -enum { - SYSTEM_BEEP_EVENT_INVOKE = 1, - SYSTEM_BEEP_EVENT_ADD -}; #endif // _DATA_EXCHANGE_H Added: haiku/trunk/headers/private/media/MediaSounds.h =================================================================== --- haiku/trunk/headers/private/media/MediaSounds.h 2007-04-16 18:32:49 UTC (rev 20727) +++ haiku/trunk/headers/private/media/MediaSounds.h 2007-04-16 19:15:46 UTC (rev 20728) @@ -0,0 +1,29 @@ +/* + * Copyright 2007, J?r?me Duval. All rights reserved. + * Distributed under the terms of the MIT License. + */ + +#ifndef _MEDIA_SOUNDS_H +#define _MEDIA_SOUNDS_H + +#define MEDIA_NAME_KEY "be:media_name" +#define MEDIA_TYPE_KEY "be:media_type" +#define MEDIA_FLAGS_KEY "be:media_flags" + +#define MEDIA_TYPE_SOUNDS "Sounds" + +#define MEDIA_SOUNDS_BEEP "Beep" +#define MEDIA_SOUNDS_STARTUP "Startup" +#define MEDIA_SOUNDS_KEY_DOWN "Key Down" +#define MEDIA_SOUNDS_KEY_REPEAT "Key Repeat" +#define MEDIA_SOUNDS_KEY_UP "Key Up" +#define MEDIA_SOUNDS_MOUSE_DOWN "Mouse Down" +#define MEDIA_SOUNDS_MOUSE_UP "Mouse Up" +#define MEDIA_SOUNDS_WINDOW_ACTIVATED "Window Activated" +#define MEDIA_SOUNDS_WINDOW_CLOSE "Window Close" +#define MEDIA_SOUNDS_WINDOW_MINIMIZED "Window Minimized" +#define MEDIA_SOUNDS_WINDOW_OPEN "Window Open" +#define MEDIA_SOUNDS_WINDOW_RESTORED "Window Restored" +#define MEDIA_SOUNDS_WINDOW_ZOOMED "Window Zoomed" + +#endif // _MEDIA_SOUNDS_H Modified: haiku/trunk/src/kits/support/Beep.cpp =================================================================== --- haiku/trunk/src/kits/support/Beep.cpp 2007-04-16 18:32:49 UTC (rev 20727) +++ haiku/trunk/src/kits/support/Beep.cpp 2007-04-16 19:15:46 UTC (rev 20728) @@ -8,17 +8,18 @@ #include #include "DataExchange.h" +#include "MediaSounds.h" status_t system_beep(const char *eventName) { - BMessenger messenger("application/x-vnd.Be.media-server"); + BMessenger messenger("application/x-vnd.Be.addon-host"); if (!messenger.IsValid()) return B_ERROR; - BMessage msg(MEDIA_SERVER_SYSTEM_BEEP_EVENT), reply; - msg.AddInt32("action", SYSTEM_BEEP_EVENT_INVOKE); - msg.AddString("event", eventName); + BMessage msg(MEDIA_ADDON_SERVER_PLAY_MEDIA), reply; + msg.AddString(MEDIA_NAME_KEY, eventName ? eventName : MEDIA_SOUNDS_BEEP); + msg.AddString(MEDIA_TYPE_KEY, MEDIA_TYPE_SOUNDS); status_t err = messenger.SendMessage(&msg, &reply); if ((err != B_OK) @@ -36,15 +37,15 @@ status_t -add_system_beep_event(const char *eventName, uint32 flags) +add_system_beep_event(const char *name, uint32 flags) { BMessenger messenger("application/x-vnd.Be.media-server"); if (!messenger.IsValid()) return B_ERROR; - BMessage msg(MEDIA_SERVER_SYSTEM_BEEP_EVENT), reply; - msg.AddInt32("action", SYSTEM_BEEP_EVENT_ADD); - msg.AddString("event", eventName); - msg.AddInt32("flags", flags); + BMessage msg(MEDIA_SERVER_ADD_SYSTEM_BEEP_EVENT), reply; + msg.AddString(MEDIA_NAME_KEY, name); + msg.AddString(MEDIA_TYPE_KEY, MEDIA_TYPE_SOUNDS); + msg.AddInt32(MEDIA_FLAGS_KEY, flags); status_t err = messenger.SendMessage(&msg, &reply); if ((err != B_OK) Modified: haiku/trunk/src/servers/media/MMediaFilesManager.cpp =================================================================== --- haiku/trunk/src/servers/media/MMediaFilesManager.cpp 2007-04-16 18:32:49 UTC (rev 20727) +++ haiku/trunk/src/servers/media/MMediaFilesManager.cpp 2007-04-16 19:15:46 UTC (rev 20728) @@ -9,6 +9,7 @@ #include #include #include "MMediaFilesManager.h" +#include "MediaSounds.h" #include "debug.h" @@ -18,6 +19,21 @@ fRunner(NULL) { CALLED(); + entry_ref ref; + SetRefFor(MEDIA_TYPE_SOUNDS, MEDIA_SOUNDS_BEEP, ref, false); + SetRefFor(MEDIA_TYPE_SOUNDS, MEDIA_SOUNDS_STARTUP, ref, false); + SetRefFor(MEDIA_TYPE_SOUNDS, MEDIA_SOUNDS_KEY_DOWN, ref, false); + SetRefFor(MEDIA_TYPE_SOUNDS, MEDIA_SOUNDS_KEY_REPEAT, ref, false); + SetRefFor(MEDIA_TYPE_SOUNDS, MEDIA_SOUNDS_KEY_UP, ref, false); + SetRefFor(MEDIA_TYPE_SOUNDS, MEDIA_SOUNDS_MOUSE_DOWN, ref, false); + SetRefFor(MEDIA_TYPE_SOUNDS, MEDIA_SOUNDS_MOUSE_UP, ref, false); + SetRefFor(MEDIA_TYPE_SOUNDS, MEDIA_SOUNDS_WINDOW_ACTIVATED, ref, false); + SetRefFor(MEDIA_TYPE_SOUNDS, MEDIA_SOUNDS_WINDOW_CLOSE, ref, false); + SetRefFor(MEDIA_TYPE_SOUNDS, MEDIA_SOUNDS_WINDOW_MINIMIZED, ref, false); + SetRefFor(MEDIA_TYPE_SOUNDS, MEDIA_SOUNDS_WINDOW_OPEN, ref, false); + SetRefFor(MEDIA_TYPE_SOUNDS, MEDIA_SOUNDS_WINDOW_RESTORED, ref, false); + SetRefFor(MEDIA_TYPE_SOUNDS, MEDIA_SOUNDS_WINDOW_ZOOMED, ref, false); + LoadState(); #if DEBUG >=3 Dump(); @@ -366,35 +382,21 @@ void -MMediaFilesManager::HandleSystemBeepEvent(BMessage *msg) +MMediaFilesManager::HandleAddSystemBeepEvent(BMessage *msg) { - int32 action, flags; - BString event; - status_t err = B_OK; - if ((msg->FindString("event", &event) != B_OK) - || (msg->FindInt32("action", &action) != B_OK)) { - err = B_BAD_VALUE; + uint32 flags; + const char *name, *type; + if ((msg->FindString(MEDIA_NAME_KEY, &name) != B_OK) + || (msg->FindString(MEDIA_TYPE_KEY, &type) != B_OK) + || (msg->FindInt32(MEDIA_FLAGS_KEY, (int32 *) &flags) != B_OK)) { + msg->SendReply(B_BAD_VALUE); + return; } - if (action == SYSTEM_BEEP_EVENT_ADD) { - if (msg->FindInt32("flags", &flags) != B_OK) - err = B_BAD_VALUE; + entry_ref *pRef = NULL; + if (GetRefFor(type, name, &pRef) == B_ENTRY_NOT_FOUND) { + entry_ref ref; + SetRefFor(type, name, ref); } - - if (err != B_OK) { - msg->SendReply(err); - return; - } - - switch (action) { - case SYSTEM_BEEP_EVENT_ADD: { - entry_ref ref; - SetRefFor(BMediaFiles::B_SOUNDS, event.String(), ref); - break; - } - case SYSTEM_BEEP_EVENT_INVOKE: { - // TODO play the sound - } - } } Modified: haiku/trunk/src/servers/media/MMediaFilesManager.h =================================================================== --- haiku/trunk/src/servers/media/MMediaFilesManager.h 2007-04-16 18:32:49 UTC (rev 20727) +++ haiku/trunk/src/servers/media/MMediaFilesManager.h 2007-04-16 19:15:46 UTC (rev 20728) @@ -51,7 +51,7 @@ void TimerMessage(); - void HandleSystemBeepEvent(BMessage *msg); + void HandleAddSystemBeepEvent(BMessage *msg); private: static int32 ReadPascalString(BFile &file, char **str); Modified: haiku/trunk/src/servers/media/media_server.cpp =================================================================== --- haiku/trunk/src/servers/media/media_server.cpp 2007-04-16 18:32:49 UTC (rev 20727) +++ haiku/trunk/src/servers/media/media_server.cpp 2007-04-16 19:15:46 UTC (rev 20728) @@ -803,8 +803,8 @@ gFormatManager->MakeFormatFor(*msg); break; - case MEDIA_SERVER_SYSTEM_BEEP_EVENT: - gMMediaFilesManager->HandleSystemBeepEvent(msg); + case MEDIA_SERVER_ADD_SYSTEM_BEEP_EVENT: + gMMediaFilesManager->HandleAddSystemBeepEvent(msg); break; default: inherited::MessageReceived(msg); Modified: haiku/trunk/src/servers/media_addon/main.cpp =================================================================== --- haiku/trunk/src/servers/media_addon/main.cpp 2007-04-16 18:32:49 UTC (rev 20727) +++ haiku/trunk/src/servers/media_addon/main.cpp 2007-04-16 19:15:46 UTC (rev 20728) @@ -43,6 +43,7 @@ #include "Notifications.h" #include "MediaMisc.h" #include "MediaRosterEx.h" +#include "MediaSounds.h" #include "SystemTimeSource.h" #include "MediaFilePlayer.h" @@ -627,9 +628,15 @@ { switch (msg->what) { - case '_TRU': + case MEDIA_ADDON_SERVER_PLAY_MEDIA: { - PlayMediaFile(msg->FindString("be:media_type"), msg->FindString("be:media_name")); + const char *name, *type; + if ((msg->FindString(MEDIA_NAME_KEY, &name) != B_OK) + || (msg->FindString(MEDIA_TYPE_KEY, &type) != B_OK)) { + msg->SendReply(B_ERROR); + } + + PlayMediaFile(type, name); msg->SendReply(B_OK); // XXX don't know which reply is expected return; } From hugosantos at mail.berlios.de Tue Apr 17 03:08:12 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Tue, 17 Apr 2007 03:08:12 +0200 Subject: [Haiku-commits] r20729 - haiku/trunk/src/add-ons/kernel/network/protocols/tcp Message-ID: <200704170108.l3H18CPe003680@sheep.berlios.de> Author: hugosantos Date: 2007-04-17 03:07:58 +0200 (Tue, 17 Apr 2007) New Revision: 20729 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20729&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h Log: support TCP Window Scale on sent segments. Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-16 19:15:46 UTC (rev 20728) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-17 01:07:58 UTC (rev 20729) @@ -61,7 +61,7 @@ // constants for the fFlags field enum { - FLAG_OPTION_WINDOW_SHIFT = 0x01, + FLAG_OPTION_WINDOW_SCALE = 0x01, FLAG_OPTION_TIMESTAMP = 0x02, // TODO: Should FLAG_NO_RECEIVE apply as well to received connections? // That is, what is expected from accept() after a shutdown() @@ -180,9 +180,8 @@ fReceiveQueue(socket->receive.buffer_size), fRoundTripTime(TCP_INITIAL_RTT), fReceivedTSval(0), - fUsingTimestamps(false), fState(CLOSED), - fFlags(0), //FLAG_OPTION_WINDOW_SHIFT), + fFlags(FLAG_OPTION_WINDOW_SCALE | FLAG_OPTION_TIMESTAMP), fError(B_OK), fSpawned(false) { @@ -366,10 +365,6 @@ fSendMax = fInitialSendSequence; fSendQueue.SetInitialSequence(fSendNext + 1); - // try to use timestamps, if the peer doesn't reply with the TS - // option as well we'll stop using them. - fUsingTimestamps = true; - // send SYN status = _SendQueued(); if (status != B_OK) { @@ -693,7 +688,7 @@ if (gStackModule->cancel_timer(&fDelayedAcknowledgeTimer)) { // timer was active, send an ACK now (with the exception above, // we send every other ACK) - return _SendQueued(); + return SendAcknowledge(); } gStackModule->set_timer(&fDelayedAcknowledgeTimer, TCP_DELAYED_ACKNOWLEDGE_TIMEOUT); @@ -808,10 +803,10 @@ else fReceiveMaxSegmentSize = TCP_DEFAULT_MAX_SEGMENT_SIZE; if (segment.has_window_shift) { - fFlags |= FLAG_OPTION_WINDOW_SHIFT; + fFlags |= FLAG_OPTION_WINDOW_SCALE; fSendWindowShift = segment.window_shift; } else { - fFlags &= ~FLAG_OPTION_WINDOW_SHIFT; + fFlags &= ~FLAG_OPTION_WINDOW_SCALE; fReceiveWindowShift = 0; } } @@ -865,10 +860,10 @@ else fReceiveMaxSegmentSize = TCP_DEFAULT_MAX_SEGMENT_SIZE; if (segment.has_window_shift) { - fFlags |= FLAG_OPTION_WINDOW_SHIFT; + fFlags |= FLAG_OPTION_WINDOW_SCALE; fSendWindowShift = segment.window_shift; } else { - fFlags &= ~FLAG_OPTION_WINDOW_SHIFT; + fFlags &= ~FLAG_OPTION_WINDOW_SCALE; fReceiveWindowShift = 0; } @@ -975,19 +970,10 @@ && fReceiveQueue.IsContiguous() && fReceiveQueue.Free() >= buffer->size && !(fFlags & FLAG_NO_RECEIVE)) { - TRACE("Receive(): header prediction receive!"); - // we're on the receiving end of the connection, and this segment - // is the one we were expecting, in-sequence - fReceiveNext += buffer->size; - TRACE("Receive(): receive next = %lu", (uint32)fReceiveNext); - fReceiveQueue.Add(buffer, segment.sequence); - if (segment.flags & TCP_FLAG_PUSH) - fReceiveQueue.SetPushPointer(); - + _AddData(segment, buffer); _NotifyReader(); - - return KEEP | (segment.flags & TCP_FLAG_PUSH ? - IMMEDIATE_ACKNOWLEDGE : ACKNOWLEDGE); + return KEEP | ((segment.flags & TCP_FLAG_PUSH) ? + IMMEDIATE_ACKNOWLEDGE : ACKNOWLEDGE); } } @@ -1104,10 +1090,10 @@ segment.flags = _CurrentFlags(); segment.urgent_offset = 0; - if (fUsingTimestamps) { + if (fOptions & FLAG_OPTION_TIMESTAMP) { segment.has_timestamps = true; segment.TSecr = fReceivedTSval; - segment.TSval = system_time(); + segment.TSval = 0; } uint32 sendWindow = fSendWindow; @@ -1138,8 +1124,13 @@ segment.flags &= ~TCP_FLAG_FINISH; } - segment.advertised_window = min_c(65535, fReceiveQueue.Free()); - // TODO: support shift option! + size_t availableBytes = fReceiveQueue.Free(); + + if (fOptions & FLAG_OPTION_WINDOW_SCALE) + segment.advertised_window = availableBytes >> fReceiveWindowShift; + else + segment.advertised_window = min_c(TCP_MAX_WINDOW, availableBytes); + segment.acknowledge = fReceiveNext; segment.urgent_offset = 0; @@ -1150,7 +1141,6 @@ && !gStackModule->is_timer_active(&fPersistTimer) && !gStackModule->is_timer_active(&fRetransmitTimer)) _StartPersistTimer(); - return B_OK; } @@ -1181,7 +1171,7 @@ && (fOptions & TCP_NOOPT) == 0) { // add connection establishment options segment.max_segment_size = fReceiveMaxSegmentSize; - if ((fFlags & FLAG_OPTION_WINDOW_SHIFT) != 0) { + if (fFlags & FLAG_OPTION_WINDOW_SCALE) { segment.has_window_shift = true; segment.window_shift = fReceiveWindowShift; } @@ -1487,17 +1477,10 @@ bool notify = false; if (buffer->size > 0 && _ShouldReceive()) { - fReceiveQueue.Add(buffer, segment.sequence); - fReceiveNext += buffer->size; + _AddData(segment, buffer); notify = true; - TRACE("Receive(): adding data, receive next = %lu. Now have %lu bytes.", - (uint32)fReceiveNext, fReceiveQueue.Available()); - - if (segment.flags & TCP_FLAG_PUSH) - fReceiveQueue.SetPushPointer(); - } else { + } else action = (action & ~KEEP) | DROP; - } if (segment.flags & TCP_FLAG_FINISH) { segmentLength++; @@ -1550,9 +1533,12 @@ TCPEndpoint::_UpdateTimestamps(tcp_segment_header &segment, size_t segmentLength, bool checkSequence) { - fUsingTimestamps = segment.has_timestamps; + if (segment.has_timestamps) + fOptions |= FLAG_OPTION_TIMESTAMP; + else + fOptions &= ~FLAG_OPTION_TIMESTAMP; - if (fUsingTimestamps) { + if (fOptions & FLAG_OPTION_TIMESTAMP) { tcp_sequence sequence(segment.sequence); if (!checkSequence || (fLastAcknowledgeSent >= sequence @@ -1589,6 +1575,20 @@ } +void +TCPEndpoint::_AddData(tcp_segment_header &segment, net_buffer *buffer) +{ + fReceiveNext += buffer->size; + fReceiveQueue.Add(buffer, segment.sequence); + + TRACE(" _AddData(): adding data, receive next = %lu. Now have %lu bytes.", + (uint32)fReceiveNext, fReceiveQueue.Available()); + + if (segment.flags & TCP_FLAG_PUSH) + fReceiveQueue.SetPushPointer(); +} + + // #pragma mark - timer @@ -1629,7 +1629,7 @@ if (!locker.IsLocked()) return; - endpoint->_SendQueued(true); + endpoint->SendAcknowledge(); } Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h 2007-04-16 19:15:46 UTC (rev 20728) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h 2007-04-17 01:07:58 UTC (rev 20729) @@ -101,6 +101,7 @@ size_t segmentLength, bool checkSequence); void _MarkEstablished(); status_t _WaitForEstablished(RecursiveLocker &lock, bigtime_t timeout); + void _AddData(tcp_segment_header &segment, net_buffer *buffer); static void _TimeWaitTimer(net_timer *timer, void *data); static void _RetransmitTimer(net_timer *timer, void *data); @@ -153,7 +154,6 @@ bool fTracking; uint32 fReceivedTSval; - bool fUsingTimestamps; uint32 fCongestionWindow; uint32 fSlowStartThreshold; From hugosantos at mail.berlios.de Tue Apr 17 03:25:21 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Tue, 17 Apr 2007 03:25:21 +0200 Subject: [Haiku-commits] r20730 - haiku/trunk/src/add-ons/kernel/network/protocols/tcp Message-ID: <200704170125.l3H1PLJ2004539@sheep.berlios.de> Author: hugosantos Date: 2007-04-17 03:25:08 +0200 (Tue, 17 Apr 2007) New Revision: 20730 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20730&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h Log: update Window Scaling variables when a simultaneous open is ACKed. Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-17 01:07:58 UTC (rev 20729) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-17 01:25:08 UTC (rev 20730) @@ -802,13 +802,7 @@ fSendMaxSegmentSize = segment.max_segment_size; else fReceiveMaxSegmentSize = TCP_DEFAULT_MAX_SEGMENT_SIZE; - if (segment.has_window_shift) { - fFlags |= FLAG_OPTION_WINDOW_SCALE; - fSendWindowShift = segment.window_shift; - } else { - fFlags &= ~FLAG_OPTION_WINDOW_SCALE; - fReceiveWindowShift = 0; - } + _CheckWindowScale(segment); } _UpdateTimestamps(segment, 0, false); @@ -859,14 +853,9 @@ fSendMaxSegmentSize = segment.max_segment_size; else fReceiveMaxSegmentSize = TCP_DEFAULT_MAX_SEGMENT_SIZE; - if (segment.has_window_shift) { - fFlags |= FLAG_OPTION_WINDOW_SCALE; - fSendWindowShift = segment.window_shift; - } else { - fFlags &= ~FLAG_OPTION_WINDOW_SCALE; - fReceiveWindowShift = 0; - } + _CheckWindowScale(segment); + if (segment.flags & TCP_FLAG_ACKNOWLEDGE) { _MarkEstablished(); } else { @@ -1394,8 +1383,8 @@ if ((segment.flags & TCP_FLAG_ACKNOWLEDGE) != 0) { // process acknowledged data if (fState == SYNCHRONIZE_RECEIVED) { - // TODO: window scaling! _MarkEstablished(); + _CheckWindowScale(segment); } if (fSendMax < segment.acknowledge || fState == TIME_WAIT) @@ -1589,6 +1578,19 @@ } +void +TCPEndpoint::_CheckWindowScale(tcp_segment_header &segment) +{ + if (segment.has_window_shift) { + fFlags |= FLAG_OPTION_WINDOW_SCALE; + fSendWindowShift = segment.window_shift; + } else { + fFlags &= ~FLAG_OPTION_WINDOW_SCALE; + fReceiveWindowShift = 0; + } +} + + // #pragma mark - timer Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h 2007-04-17 01:07:58 UTC (rev 20729) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h 2007-04-17 01:25:08 UTC (rev 20730) @@ -102,6 +102,7 @@ void _MarkEstablished(); status_t _WaitForEstablished(RecursiveLocker &lock, bigtime_t timeout); void _AddData(tcp_segment_header &segment, net_buffer *buffer); + void _CheckWindowScale(tcp_segment_header &segment); static void _TimeWaitTimer(net_timer *timer, void *data); static void _RetransmitTimer(net_timer *timer, void *data); From hugosantos at mail.berlios.de Tue Apr 17 05:39:34 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Tue, 17 Apr 2007 05:39:34 +0200 Subject: [Haiku-commits] r20731 - haiku/trunk/src/add-ons/kernel/network/protocols/tcp Message-ID: <200704170339.l3H3dYOe011021@sheep.berlios.de> Author: hugosantos Date: 2007-04-17 05:39:24 +0200 (Tue, 17 Apr 2007) New Revision: 20731 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20731&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h Log: reorganized some of the TCP logic so we have common init paths for receive and send. Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-17 01:25:08 UTC (rev 20730) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-17 03:39:24 UTC (rev 20731) @@ -314,7 +314,7 @@ until the connection has been established or refused. */ status_t -TCPEndpoint::Connect(const struct sockaddr *address) +TCPEndpoint::Connect(const sockaddr *address) { TRACE("Connect() on address %s", AddressString(Domain(), address, true).Data()); @@ -329,41 +329,13 @@ } else if (fState != CLOSED) return EISCONN; - // get a net_route if there isn't one - // TODO: get a net_route_info instead! - if (fRoute == NULL) { - fRoute = gDatalinkModule->get_route(Domain(), (sockaddr *)address); - TRACE(" Connect(): Using Route %p", fRoute); - if (fRoute == NULL) - return ENETUNREACH; - } - - // make sure connection does not already exist - status_t status = fManager->SetConnection(this, - (sockaddr *)&socket->address, address, fRoute->interface->address); - if (status < B_OK) { - TRACE(" Connect(): could not add connection: %s!", strerror(status)); + status_t status = _PrepareSendPath(address); + if (status < B_OK) return status; - } - fReceiveMaxSegmentSize = _GetMSS(address); - - // Compute the window shift we advertise to our peer - if it doesn't support - // this option, this will be reset to 0 (when its SYN is received) - fReceiveWindowShift = 0; - while (fReceiveWindowShift < TCP_MAX_WINDOW_SHIFT - && (0xffffUL << fReceiveWindowShift) < socket->receive.buffer_size) { - fReceiveWindowShift++; - } - TRACE(" Connect(): starting 3-way handshake..."); fState = SYNCHRONIZE_SENT; - fInitialSendSequence = system_time() >> 4; - fSendNext = fInitialSendSequence; - fSendUnacknowledged = fInitialSendSequence; - fSendMax = fInitialSendSequence; - fSendQueue.SetInitialSequence(fSendNext + 1); // send SYN status = _SendQueued(); @@ -515,8 +487,7 @@ if (fState == CLOSED) return ENOTCONN; else if (fState == LISTEN) { - // TODO change socket from passive to active. - return EOPNOTSUPP; + return EDESTADDRREQ; } else if (fState == FINISH_SENT || fState == FINISH_ACKNOWLEDGED || fState == CLOSING || fState == WAIT_FOR_FINISH_ACKNOWLEDGE || fState == TIME_WAIT) { @@ -753,7 +724,8 @@ AddressModule()->set_to((sockaddr *)&newSocket->peer, (sockaddr *)&buffer->source); - return ((TCPEndpoint *)newSocket->first_protocol)->Spawn(this, segment, buffer); + return ((TCPEndpoint *)newSocket->first_protocol)->Spawn(this, + segment, buffer); } @@ -765,55 +737,18 @@ fState = SYNCHRONIZE_RECEIVED; fManager = parent->fManager; + fSpawned = true; TRACE("Spawn()"); - fSpawned = true; - - sockaddr *local = (sockaddr *)&socket->address; - sockaddr *peer = (sockaddr *)&socket->peer; - // TODO: proper error handling! - - fRoute = gDatalinkModule->get_route(Domain(), peer); - if (fRoute == NULL) + if (_PrepareSendPath((sockaddr *)&socket->peer) < B_OK) return DROP; - if (fManager->SetConnection(this, local, peer, NULL) < B_OK) - return DROP; + _PrepareReceivePath(parent, segment); - fInitialReceiveSequence = segment.sequence; - fReceiveQueue.SetInitialSequence(segment.sequence + 1); - fAcceptSemaphore = parent->fAcceptSemaphore; - fReceiveMaxSegmentSize = _GetMSS(peer); - // 40 bytes for IP and TCP header without any options - // TODO: make this depending on the RTF_LOCAL flag? - fReceiveNext = segment.sequence + 1; - // account for the extra sequence number for the synchronization - - fInitialSendSequence = system_time() >> 4; - fSendNext = fInitialSendSequence; - fSendUnacknowledged = fSendNext; - fSendMax = fSendNext; - - // set options - if ((parent->fOptions & TCP_NOOPT) == 0) { - if (segment.max_segment_size > 0) - fSendMaxSegmentSize = segment.max_segment_size; - else - fReceiveMaxSegmentSize = TCP_DEFAULT_MAX_SEGMENT_SIZE; - _CheckWindowScale(segment); - } - - _UpdateTimestamps(segment, 0, false); - // send SYN+ACK - status_t status = _SendQueued(); - - fInitialSendSequence = fSendNext; - fSendQueue.SetInitialSequence(fSendNext); - - if (status < B_OK) + if (_SendQueued() < B_OK) return DROP; segment.flags &= ~TCP_FLAG_SYNCHRONIZE; @@ -842,20 +777,8 @@ if ((segment.flags & TCP_FLAG_SYNCHRONIZE) == 0) return DROP; - fInitialReceiveSequence = segment.sequence; - segment.sequence++; + _PrepareReceivePath(NULL, segment); - fSendUnacknowledged = segment.acknowledge; - fReceiveNext = segment.sequence; - fReceiveQueue.SetInitialSequence(fReceiveNext); - - if (segment.max_segment_size > 0) - fSendMaxSegmentSize = segment.max_segment_size; - else - fReceiveMaxSegmentSize = TCP_DEFAULT_MAX_SEGMENT_SIZE; - - _CheckWindowScale(segment); - if (segment.flags & TCP_FLAG_ACKNOWLEDGE) { _MarkEstablished(); } else { @@ -863,8 +786,6 @@ fState = SYNCHRONIZE_RECEIVED; } - _UpdateTimestamps(segment, 0, false); - segment.flags &= ~TCP_FLAG_SYNCHRONIZE; // we handled this flag now, it must not be set for further processing @@ -929,7 +850,7 @@ && advertisedWindow > 0 && advertisedWindow == fSendWindow && fSendNext == fSendMax) { - _UpdateTimestamps(segment, buffer->size, true); + _UpdateTimestamps(segment, buffer->size); if (buffer->size == 0) { // this is a pure acknowledge segment - we're on the sending end @@ -1079,7 +1000,7 @@ segment.flags = _CurrentFlags(); segment.urgent_offset = 0; - if (fOptions & FLAG_OPTION_TIMESTAMP) { + if (fFlags & FLAG_OPTION_TIMESTAMP) { segment.has_timestamps = true; segment.TSecr = fReceivedTSval; segment.TSval = 0; @@ -1115,7 +1036,7 @@ size_t availableBytes = fReceiveQueue.Free(); - if (fOptions & FLAG_OPTION_WINDOW_SCALE) + if (fFlags & FLAG_OPTION_WINDOW_SCALE) segment.advertised_window = availableBytes >> fReceiveWindowShift; else segment.advertised_window = min_c(TCP_MAX_WINDOW, availableBytes); @@ -1166,10 +1087,13 @@ } } - TRACE("SendQueued() flags %x, buffer %p, size %lu, from address %s to %s", - segment.flags, buffer, buffer->size, - AddressString(Domain(), (sockaddr *)&buffer->source, true).Data(), - AddressString(Domain(), (sockaddr *)&buffer->destination, true).Data()); + TRACE("SendQueued() buffer %p (%lu bytes) address %s to %s", + buffer, buffer->size, AddressString(Domain(), + (sockaddr *)&buffer->source, true).Data(), AddressString(Domain(), + (sockaddr *)&buffer->destination, true).Data()); + TRACE(" flags 0x%x, seq %lu, ack %lu, rwnd %hu", + segment.flags, segment.sequence, segment.acknowledge, + segment.advertised_window); status = add_tcp_header(AddressModule(), segment, buffer); if (status != B_OK) { @@ -1382,10 +1306,8 @@ if ((segment.flags & TCP_FLAG_ACKNOWLEDGE) != 0) { // process acknowledged data - if (fState == SYNCHRONIZE_RECEIVED) { + if (fState == SYNCHRONIZE_RECEIVED) _MarkEstablished(); - _CheckWindowScale(segment); - } if (fSendMax < segment.acknowledge || fState == TIME_WAIT) return DROP | IMMEDIATE_ACKNOWLEDGE; @@ -1510,7 +1432,7 @@ if (buffer->size > 0 || (segment.flags & TCP_FLAG_SYNCHRONIZE) != 0) action |= ACKNOWLEDGE; - _UpdateTimestamps(segment, segmentLength, true); + _UpdateTimestamps(segment, segmentLength); TRACE("Receive() Action %ld", action); @@ -1519,18 +1441,13 @@ void -TCPEndpoint::_UpdateTimestamps(tcp_segment_header &segment, size_t segmentLength, - bool checkSequence) +TCPEndpoint::_UpdateTimestamps(tcp_segment_header &segment, + size_t segmentLength) { - if (segment.has_timestamps) - fOptions |= FLAG_OPTION_TIMESTAMP; - else - fOptions &= ~FLAG_OPTION_TIMESTAMP; - - if (fOptions & FLAG_OPTION_TIMESTAMP) { + if (fFlags & FLAG_OPTION_TIMESTAMP) { tcp_sequence sequence(segment.sequence); - if (!checkSequence || (fLastAcknowledgeSent >= sequence + if ((fLastAcknowledgeSent >= sequence && fLastAcknowledgeSent < (sequence + segmentLength))) fReceivedTSval = segment.TSval; } @@ -1579,18 +1496,81 @@ void -TCPEndpoint::_CheckWindowScale(tcp_segment_header &segment) +TCPEndpoint::_PrepareReceivePath(TCPEndpoint *parent, + tcp_segment_header &segment) { - if (segment.has_window_shift) { - fFlags |= FLAG_OPTION_WINDOW_SCALE; - fSendWindowShift = segment.window_shift; - } else { - fFlags &= ~FLAG_OPTION_WINDOW_SCALE; - fReceiveWindowShift = 0; + fInitialReceiveSequence = segment.sequence; + + // count the received SYN + segment.sequence++; + + if (parent == NULL) + fSendUnacknowledged = segment.acknowledge; + fReceiveNext = segment.sequence; + fReceiveQueue.SetInitialSequence(segment.sequence); + + if (parent) { + fOptions = parent->fOptions; + fAcceptSemaphore = parent->fAcceptSemaphore; } + + if ((fOptions & TCP_NOOPT) == 0) { + if (segment.max_segment_size > 0) + fSendMaxSegmentSize = segment.max_segment_size; + + if (segment.has_window_shift) { + fFlags |= FLAG_OPTION_WINDOW_SCALE; + fSendWindowShift = segment.window_shift; + } else { + fFlags &= ~FLAG_OPTION_WINDOW_SCALE; + fReceiveWindowShift = 0; + } + + if (segment.has_timestamps) + fFlags |= FLAG_OPTION_TIMESTAMP; + else + fFlags &= ~FLAG_OPTION_TIMESTAMP; + } } +status_t +TCPEndpoint::_PrepareSendPath(const sockaddr *peer) +{ + if (fRoute == NULL) { + fRoute = gDatalinkModule->get_route(Domain(), peer); + if (fRoute == NULL) + return ENETUNREACH; + } + + // make sure connection does not already exist + status_t status = fManager->SetConnection(this, + (sockaddr *)&socket->address, peer, fRoute->interface->address); + if (status < B_OK) + return status; + + fInitialSendSequence = system_time() >> 4; + fSendNext = fInitialSendSequence; + fSendUnacknowledged = fInitialSendSequence; + fSendMax = fInitialSendSequence; + + // we are counting the SYN here + fSendQueue.SetInitialSequence(fSendNext + 1); + + fReceiveMaxSegmentSize = _GetMSS(peer); + + // Compute the window shift we advertise to our peer - if it doesn't support + // this option, this will be reset to 0 (when its SYN is received) + fReceiveWindowShift = 0; + while (fReceiveWindowShift < TCP_MAX_WINDOW_SHIFT + && (0xffffUL << fReceiveWindowShift) < socket->receive.buffer_size) { + fReceiveWindowShift++; + } + + return B_OK; +} + + // #pragma mark - timer Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h 2007-04-17 01:25:08 UTC (rev 20730) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h 2007-04-17 03:39:24 UTC (rev 20731) @@ -98,11 +98,13 @@ int32 _SegmentReceived(tcp_segment_header& segment, net_buffer *buffer); int32 _Receive(tcp_segment_header& segment, net_buffer *buffer); void _UpdateTimestamps(tcp_segment_header& segment, - size_t segmentLength, bool checkSequence); + size_t segmentLength); void _MarkEstablished(); status_t _WaitForEstablished(RecursiveLocker &lock, bigtime_t timeout); void _AddData(tcp_segment_header &segment, net_buffer *buffer); - void _CheckWindowScale(tcp_segment_header &segment); + void _PrepareReceivePath(TCPEndpoint *parent, + tcp_segment_header &segment); + status_t _PrepareSendPath(const sockaddr *peer); static void _TimeWaitTimer(net_timer *timer, void *data); static void _RetransmitTimer(net_timer *timer, void *data); From geist at mail.berlios.de Tue Apr 17 06:19:46 2007 From: geist at mail.berlios.de (geist at BerliOS) Date: Tue, 17 Apr 2007 06:19:46 +0200 Subject: [Haiku-commits] r20732 - haiku/trunk/src/system/libroot/posix/string/arch/x86 Message-ID: <200704170419.l3H4Jka5013459@sheep.berlios.de> Author: geist Date: 2007-04-17 06:19:45 +0200 (Tue, 17 Apr 2007) New Revision: 20732 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20732&view=rev Modified: haiku/trunk/src/system/libroot/posix/string/arch/x86/arch_string.S Log: set the function attribute on the asm memcpy. This should fix the loader problem some folks were seeing on beos binaries. Modified: haiku/trunk/src/system/libroot/posix/string/arch/x86/arch_string.S =================================================================== --- haiku/trunk/src/system/libroot/posix/string/arch/x86/arch_string.S 2007-04-17 03:39:24 UTC (rev 20731) +++ haiku/trunk/src/system/libroot/posix/string/arch/x86/arch_string.S 2007-04-17 04:19:45 UTC (rev 20732) @@ -3,10 +3,10 @@ ** Distributed under the terms of the NewOS License. */ -.globl memcpy +#define FUNCTION(x) .global x; .type x, at function; x .align 4 -memcpy: +FUNCTION(memcpy): pushl %esi pushl %edi movl 12(%esp),%edi /* dest */ From bonefish at mail.berlios.de Tue Apr 17 07:39:33 2007 From: bonefish at mail.berlios.de (bonefish at BerliOS) Date: Tue, 17 Apr 2007 07:39:33 +0200 Subject: [Haiku-commits] r20733 - haiku/trunk/src/servers/registrar Message-ID: <200704170539.l3H5dXWC029754@sheep.berlios.de> Author: bonefish Date: 2007-04-17 07:39:33 +0200 (Tue, 17 Apr 2007) New Revision: 20733 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20733&view=rev Modified: haiku/trunk/src/servers/registrar/AppInfoList.cpp haiku/trunk/src/servers/registrar/AppInfoList.h haiku/trunk/src/servers/registrar/ShutdownProcess.cpp Log: Fixed incorrect use of the sort() function. It expects a "less than" compare function with bool return value, not a -1/0/1 returning compare function. Fixes bug #1158 (registrar crash on shutdown). Modified: haiku/trunk/src/servers/registrar/AppInfoList.cpp =================================================================== --- haiku/trunk/src/servers/registrar/AppInfoList.cpp 2007-04-17 04:19:45 UTC (rev 20732) +++ haiku/trunk/src/servers/registrar/AppInfoList.cpp 2007-04-17 05:39:33 UTC (rev 20733) @@ -186,15 +186,16 @@ // Sort /*! \brief Sorts the infos in ascending order according to the given compare function. - \param cmpFunc The compare function to be used. + \param lessFunc The compare function (less than) to be used. */ void -AppInfoList::Sort(int (*cmpFunc)(const RosterAppInfo *, const RosterAppInfo *)) +AppInfoList::Sort( + bool (*lessFunc)(const RosterAppInfo *, const RosterAppInfo *)) { int32 count = CountInfos(); if (count > 1) { RosterAppInfo **infos = (RosterAppInfo **)fInfos.Items(); - std::sort(infos, infos + count, cmpFunc); + std::sort(infos, infos + count, lessFunc); } } Modified: haiku/trunk/src/servers/registrar/AppInfoList.h =================================================================== --- haiku/trunk/src/servers/registrar/AppInfoList.h 2007-04-17 04:19:45 UTC (rev 20732) +++ haiku/trunk/src/servers/registrar/AppInfoList.h 2007-04-17 05:39:33 UTC (rev 20733) @@ -57,7 +57,7 @@ Iterator It(); - void Sort(int (*cmpFunc)(const RosterAppInfo *, const RosterAppInfo *)); + void Sort(bool (*lessFunc)(const RosterAppInfo *, const RosterAppInfo *)); private: RosterAppInfo *RemoveInfo(int32 index); Modified: haiku/trunk/src/servers/registrar/ShutdownProcess.cpp =================================================================== --- haiku/trunk/src/servers/registrar/ShutdownProcess.cpp 2007-04-17 04:19:45 UTC (rev 20732) +++ haiku/trunk/src/servers/registrar/ShutdownProcess.cpp 2007-04-17 05:39:33 UTC (rev 20733) @@ -95,14 +95,11 @@ // inverse_compare_by_registration_time static -int +bool inverse_compare_by_registration_time(const RosterAppInfo *info1, const RosterAppInfo *info2) { - bigtime_t cmp = info1->registration_time - info2->registration_time; - if (cmp < 0) - return 1; - return (cmp > 0 ? -1 : 0); + return (info2->registration_time < info1->registration_time); } // throw_error From hugosantos at mail.berlios.de Tue Apr 17 07:55:13 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Tue, 17 Apr 2007 07:55:13 +0200 Subject: [Haiku-commits] r20734 - haiku/trunk/src/add-ons/kernel/network/protocols/tcp Message-ID: <200704170555.l3H5tD3P030764@sheep.berlios.de> Author: hugosantos Date: 2007-04-17 07:55:03 +0200 (Tue, 17 Apr 2007) New Revision: 20734 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20734&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h Log: implemented TCP's slow start and congestion avoidance. Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-17 05:39:33 UTC (rev 20733) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-17 05:55:03 UTC (rev 20734) @@ -116,6 +116,14 @@ } +static inline bool +is_writable(tcp_state state) +{ + return state == SYNCHRONIZE_SENT || state == SYNCHRONIZE_RECEIVED + || state == ESTABLISHED || state == FINISH_RECEIVED; +} + + WaitList::WaitList(const char *name) { fSem = create_sem(0, name); @@ -180,6 +188,8 @@ fReceiveQueue(socket->receive.buffer_size), fRoundTripTime(TCP_INITIAL_RTT), fReceivedTSval(0), + fCongestionWindow(0), + fSlowStartThreshold(0), fState(CLOSED), fFlags(FLAG_OPTION_WINDOW_SCALE | FLAG_OPTION_TIMESTAMP), fError(B_OK), @@ -479,11 +489,11 @@ status_t TCPEndpoint::SendData(net_buffer *buffer) { - TRACE("SendData(buffer %p, size %lu, flags %lx)", - buffer, buffer->size, buffer->flags); - RecursiveLocker lock(fLock); + TRACE("SendData(buffer %p, size %lu, flags %lx) [total %lu bytes]", + buffer, buffer->size, buffer->flags, fSendQueue.Size()); + if (fState == CLOSED) return ENOTCONN; else if (fState == LISTEN) { @@ -510,6 +520,8 @@ fSendQueue.Add(buffer); } + TRACE(" SendData(): %lu bytes used.", fSendQueue.Used()); + if (fState == ESTABLISHED || fState == FINISH_RECEIVED) _SendQueued(); @@ -524,12 +536,10 @@ ssize_t available; - if (fState == FINISH_SENT || fState == FINISH_ACKNOWLEDGED - || fState == CLOSING || fState == WAIT_FOR_FINISH_ACKNOWLEDGE - || fState == TIME_WAIT || fState == LISTEN || fState == CLOSED) + if (is_writable(fState)) + available = fSendQueue.Free(); + else available = EPIPE; - else - available = fSendQueue.Free(); TRACE("SendAvailable(): %li", available); return available; @@ -603,8 +613,7 @@ } } - TRACE(" ReadData(): read %lu bytes, %lu are available.", - numBytes, fReceiveQueue.Available()); + TRACE(" ReadData(): %lu are available.", fReceiveQueue.Available()); if (numBytes < fReceiveQueue.Available()) fReceiveList.Signal(); @@ -745,8 +754,11 @@ if (_PrepareSendPath((sockaddr *)&socket->peer) < B_OK) return DROP; - _PrepareReceivePath(parent, segment); + fOptions = parent->fOptions; + fAcceptSemaphore = parent->fAcceptSemaphore; + _PrepareReceivePath(segment); + // send SYN+ACK if (_SendQueued() < B_OK) return DROP; @@ -777,7 +789,8 @@ if ((segment.flags & TCP_FLAG_SYNCHRONIZE) == 0) return DROP; - _PrepareReceivePath(NULL, segment); + fSendUnacknowledged = segment.acknowledge; + _PrepareReceivePath(segment); if (segment.flags & TCP_FLAG_ACKNOWLEDGE) { _MarkEstablished(); @@ -859,21 +872,11 @@ TRACE("Receive(): header prediction send!"); // and it only acknowledges outstanding data - // TODO: update RTT estimators + _Acknowledged(segment.acknowledge); - fSendQueue.RemoveUntil(segment.acknowledge); - fSendUnacknowledged = segment.acknowledge; - // stop retransmit timer gStackModule->cancel_timer(&fRetransmitTimer); - // notify threads waiting on the socket to become writable again - fSendList.Signal(); - // TODO: real conditional locking needed! - gSocketModule->notify(socket, B_SELECT_WRITE, fSendWindow); - - // if there is data left to be send, send it now - _SendQueued(); return DROP; } } else if (segment.acknowledge == fSendUnacknowledged @@ -1017,7 +1020,12 @@ sendWindow = 1; } - int32 length = min_c(available, sendWindow) - (fSendNext - fSendUnacknowledged); + if (fCongestionWindow > 0) + sendWindow = min_c(sendWindow, fCongestionWindow); + + int32 length = min_c(available, sendWindow) + - (fSendNext - fSendUnacknowledged); + if (length < 0) { // either the window shrank, or we sent a still unacknowledged FIN length = 0; @@ -1091,9 +1099,10 @@ buffer, buffer->size, AddressString(Domain(), (sockaddr *)&buffer->source, true).Data(), AddressString(Domain(), (sockaddr *)&buffer->destination, true).Data()); - TRACE(" flags 0x%x, seq %lu, ack %lu, rwnd %hu", - segment.flags, segment.sequence, segment.acknowledge, - segment.advertised_window); + TRACE(" flags 0x%x, seq %lu, ack %lu, rwnd %hu, cwnd %lu" + ", ssthresh %lu", segment.flags, segment.sequence, + segment.acknowledge, segment.advertised_window, + fCongestionWindow, fSlowStartThreshold); status = add_tcp_header(AddressModule(), segment, buffer); if (status != B_OK) { @@ -1342,12 +1351,8 @@ gStackModule->set_timer(&fRetransmitTimer, 1000000LL); } - fSendUnacknowledged = segment.acknowledge; - fSendQueue.RemoveUntil(segment.acknowledge); + _Acknowledged(segment.acknowledge); - if (fSendNext < fSendUnacknowledged) - fSendNext = fSendUnacknowledged; - if (segment.acknowledge > fSendQueue.LastSequence() && fState > ESTABLISHED) { TRACE("Receive(): FIN has been acknowledged!"); @@ -1496,24 +1501,16 @@ void -TCPEndpoint::_PrepareReceivePath(TCPEndpoint *parent, - tcp_segment_header &segment) +TCPEndpoint::_PrepareReceivePath(tcp_segment_header &segment) { fInitialReceiveSequence = segment.sequence; // count the received SYN segment.sequence++; - if (parent == NULL) - fSendUnacknowledged = segment.acknowledge; fReceiveNext = segment.sequence; fReceiveQueue.SetInitialSequence(segment.sequence); - if (parent) { - fOptions = parent->fOptions; - fAcceptSemaphore = parent->fAcceptSemaphore; - } - if ((fOptions & TCP_NOOPT) == 0) { if (segment.max_segment_size > 0) fSendMaxSegmentSize = segment.max_segment_size; @@ -1531,6 +1528,9 @@ else fFlags &= ~FLAG_OPTION_TIMESTAMP; } + + fCongestionWindow = 2 * fSendMaxSegmentSize; + fSlowStartThreshold = (uint32)segment.advertised_window << fSendWindowShift; } @@ -1571,6 +1571,61 @@ } +void +TCPEndpoint::_Acknowledged(tcp_sequence acknowledge) +{ + size_t previouslyUsed = fSendQueue.Used(); + + fSendQueue.RemoveUntil(acknowledge); + fSendUnacknowledged = acknowledge; + + if (fSendNext < fSendUnacknowledged) + fSendNext = fSendUnacknowledged; + + // TODO: update RTT estimators + + if (fSendQueue.Used() < previouslyUsed) { + // this ACK acknowledged data + + if (is_writable(fState)) { + // notify threads waiting on the socket to become writable again + fSendList.Signal(); + gSocketModule->notify(socket, B_SELECT_WRITE, fSendQueue.Used()); + } + + if (fCongestionWindow < fSlowStartThreshold) + fCongestionWindow += fSendMaxSegmentSize; + } + + if (fCongestionWindow >= fSlowStartThreshold) { + uint32 increment = fSendMaxSegmentSize * fSendMaxSegmentSize; + + if (increment < fCongestionWindow) + increment = 1; + else + increment /= fCongestionWindow; + + fCongestionWindow += increment; + } + + // if there is data left to be send, send it now + _SendQueued(); +} + + +void +TCPEndpoint::_Retransmit() +{ + fSendNext = fSendUnacknowledged; + _SendQueued(); + fSendNext = fSendMax; + + fSlowStartThreshold = max_c((fSendMax - fSendUnacknowledged) / 2, + 2 * fSendMaxSegmentSize); + fCongestionWindow = fSendMaxSegmentSize; +} + + // #pragma mark - timer @@ -1583,9 +1638,7 @@ if (!locker.IsLocked()) return; - endpoint->fSendNext = endpoint->fSendUnacknowledged; - endpoint->_SendQueued(); - endpoint->fSendNext = endpoint->fSendMax; + endpoint->_Retransmit(); } Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h 2007-04-17 05:39:33 UTC (rev 20733) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h 2007-04-17 05:55:03 UTC (rev 20734) @@ -102,9 +102,10 @@ void _MarkEstablished(); status_t _WaitForEstablished(RecursiveLocker &lock, bigtime_t timeout); void _AddData(tcp_segment_header &segment, net_buffer *buffer); - void _PrepareReceivePath(TCPEndpoint *parent, - tcp_segment_header &segment); + void _PrepareReceivePath(tcp_segment_header &segment); status_t _PrepareSendPath(const sockaddr *peer); + void _Acknowledged(tcp_sequence acknowledge); + void _Retransmit(); static void _TimeWaitTimer(net_timer *timer, void *data); static void _RetransmitTimer(net_timer *timer, void *data); From hugosantos at mail.berlios.de Tue Apr 17 10:02:51 2007 From: hugosantos at mail.berlios.de (hugosantos at mail.berlios.de) Date: Tue, 17 Apr 2007 10:02:51 +0200 Subject: [Haiku-commits] r20735 - haiku/trunk/src/add-ons/kernel/network/protocols/tcp Message-ID: <200704170802.l3H82pTt005895@sheep.berlios.de> Author: hugosantos Date: 2007-04-17 10:02:41 +0200 (Tue, 17 Apr 2007) New Revision: 20735 ViewCVS: http://svn.berlios.de/viewcvs/haiku?rev=20735&view=rev Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp Log: TCP: only set FIN after the send queue has been exausted and we are in a state that requires it. Modified: haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp =================================================================== --- haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-17 05:55:03 UTC (rev 20734) +++ haiku/trunk/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.cpp 2007-04-17 08:02:41 UTC (rev 20735) @@ -1037,13 +1037,11 @@ } uint32 segmentLength = min_c((uint32)length, fSendMaxSegmentSize); - if (tcp_sequence(fSendNext + segmentLength) > fSendUnacknowledged + available) { - // we'll still have data in the queue after the next write, so remove the FIN - segment.flags &= ~TCP_FLAG_FINISH; - } + bool wantsFinish = segment.flags & TCP_FLAG_FINISH; + segment.flags