rem: panic("port %id: head > cap %d", ports[slot].id, ports[slot].capacity);
add: panic("port %ld: head > cap %ld", ports[slot].id, ports[slot].capacity);
context: write_port_etc(port_id id,	int32 msg_code,	const void *msg_buffer,	size_t buffer_size,	uint32 flags,	bigtime_t timeout){	int slot;	int state;	int res;	sem_id cached_semid;	int h;	cbuf* msg_store;	int c1, c2;	int err;		if(ports_active == false)		return B_BAD_PORT_ID;	if(id < 0)		return B_BAD_PORT_ID;	// mask irrelevant flags	flags = flags & (PORT_FLAG_USE_USER_MEMCPY | B_CAN_INTERRUPT | B_TIMEOUT);	slot = id % MAX_PORTS;		// check buffer_size	if (buffer_size > PORT_MAX_MESSAGE_SIZE)		return EINVAL;	state = disable_interrupts();	GRAB_PORT_LOCK(ports[slot]);	if(ports[slot].id != id) {		RELEASE_PORT_LOCK(ports[slot]);		restore_interrupts(state);		dprintf("write_port_etc: invalid port_id %d\n", id);		return B_BAD_PORT_ID;	}	if (ports[slot].closed) {		RELEASE_PORT_LOCK(ports[slot]);		restore_interrupts(state);		dprintf("write_port_etc: port %d closed\n", id);		return B_BAD_PORT_ID;	}		// store sem_id in local variable 	cached_semid = ports[slot].write_sem;	RELEASE_PORT_LOCK(ports[slot]);	restore_interrupts(state);		// XXX -> possible race condition if port gets deleted (->sem deleted too), 	// and queue is full therefore sem_id is cached in local variable up here		// get 1 entry from the queue, block if needed	// assumes flags	res = acquire_sem_etc(cached_semid, 1,						flags & (B_TIMEOUT | B_CAN_INTERRUPT), timeout);	// XXX: possible race condition if port written by two threads...	//      both threads will write in 2 different slots allocated above, simultaneously	// 		slot is a thread-local variable	if (res == B_BAD_PORT_ID || res == EINTR) {		/* somebody deleted the port or the sem while we were waiting */		return B_BAD_PORT_ID;	}	if (res == B_TIMED_OUT) {		// timed out, or, if timeout=0, 'would block'		return B_TIMED_OUT;	}	if (res != B_NO_ERROR) {		dprintf("write_port_etc: res unknown error %d\n", res);		return res;	}	if (buffer_size > 0) {		msg_store = cbuf_get_chain(buffer_size);		if (msg_store == NULL)			return ENOMEM;		if (flags & PORT_FLAG_USE_USER_MEMCPY) {			// copy from user memory			if ((err = cbuf_user_memcpy_to_chain(msg_store, 0, msg_buffer, buffer_size)) < 0)				return err; // memory exception		} else			// copy from kernel memory			if ((err = cbuf_memcpy_to_chain(msg_store, 0, msg_buffer, buffer_size)) < 0)				return err; // memory exception	} else {		msg_store = NULL;	}	// attach copied message to queue	state = disable_interrupts();	GRAB_PORT_LOCK(ports[slot]);	h = ports[slot].head;	if (h < 0)		panic("port %id: head < 0", ports[slot].id);	if (h >= ports[slot].capacity)		panic("port %id: head > cap %d", ports[slot].id, ports[slot].capacity);	ports[slot].msg_queue[h].msg_code	= msg_code;	ports[slot].msg_queue[h].data_cbuf	= msg_store;	ports[slot].msg_queue[h].data_len	= buffer_size;	ports[slot].head = (ports[slot].head + 1) % ports[slot].capacity;	ports[slot].total_count++;	// store sem_id in local variable 	cached_semid = ports[slot].read_sem;	RELEASE_PORT_LOCK(ports[slot]);	restore_interrupts(state);	get_sem_count(ports[slot].read_sem, &c1);	get_sem_count(ports[slot].write_sem, &c2);	// release sem, allowing read (might reschedule)	release_sem(cached_semid);	return B_NO_ERROR;}