static void *thread_producer(void *d) { (void)d; l4shmc_chunk_t p_one; l4shmc_signal_t s_one, s_done; l4shmc_area_t shmarea; l4_debugger_set_object_name(pthread_getl4cap(pthread_self()), "prod"); // attach this thread to the shm object CHK(l4shmc_attach("testshm", &shmarea)); // add a chunk CHK(l4shmc_add_chunk(&shmarea, "one", 1024, &p_one)); // add a signal CHK(l4shmc_add_signal(&shmarea, "prod", &s_one)); // connect chunk and signal CHK(l4shmc_connect_chunk_signal(&p_one, &s_one)); CHK(l4shmc_attach_signal_to(&shmarea, "done", pthread_getl4cap(pthread_self()), 10000, &s_done)); printf("PRODUCER: ready\n"); while (1) { while (l4shmc_chunk_try_to_take(&p_one)) printf("Uh, should not happen!\n"); //l4_thread_yield(); set_some_data(); memcpy(l4shmc_chunk_ptr(&p_one), some_data, sizeof(some_data)); CHK(l4shmc_chunk_ready_sig(&p_one, sizeof(some_data))); printf("PRODUCER: Sent data %s\n", some_data); CHK(l4shmc_wait_signal(&s_done)); l4_sleep(5000); } l4_sleep_forever(); return NULL; }
static void *thread_consume(void *d) { (void)d; l4shmc_area_t shmarea; l4shmc_chunk_t p_one; l4shmc_signal_t s_one, s_done; // attach to shared memory area CHK(l4shmc_attach("testshm", &shmarea)); // get chunk 'one' CHK(l4shmc_get_chunk(&shmarea, "one", &p_one)); // add a signal CHK(l4shmc_add_signal(&shmarea, "done", &s_done)); // attach signal to this thread CHK(l4shmc_attach_signal_to(&shmarea, "prod", pthread_l4_cap(pthread_self()), 10000, &s_one)); // connect chunk and signal CHK(l4shmc_connect_chunk_signal(&p_one, &s_one)); while (1) { CHK(l4shmc_wait_chunk(&p_one)); printf("CONSUMER: Received from chunk one: %s\n", (char *)l4shmc_chunk_ptr(&p_one)); memset(l4shmc_chunk_ptr(&p_one), 0, l4shmc_chunk_size(&p_one)); CHK(l4shmc_chunk_consumed(&p_one)); CHK(l4shmc_trigger(&s_done)); } return NULL; }
static int __init l4ser_shm_init_port(int num, const char *name) { int irq; struct chunk_head *ch; struct l4ser_shm_uart_port *p = &l4ser_shm_port[num]; L4XV_V(f); if (p->inited) return 0; p->inited = 1; if (shmsize < PAGE_SIZE) shmsize = PAGE_SIZE; pr_info("l4ser_shm: Requesting, role %s, Shmsize %d Kbytes\n", p->create ? "Creator" : "User", shmsize >> 10); L4XV_L(f); if (p->create) { if (l4shmc_create(name, shmsize)) { L4XV_U(f); pr_err("l4ser_shm/%s: Failed to create shm\n", p->name); return -ENOMEM; } } if (l4shmc_attach_to(name, WAIT_TIMEOUT, &p->shmcarea)) { L4XV_U(f); pr_err("l4ser_shm/%s: Failed to attach to shm\n", p->name); return -ENOMEM; } if (l4shmc_add_chunk(&p->shmcarea, p->create ? "joe" : "bob", chunk_size(&p->shmcarea), &p->tx_chunk)) goto unlock; if (l4shmc_add_signal(&p->shmcarea, p->create ? "joe" : "bob", &p->tx_sig)) goto unlock; if (l4shmc_connect_chunk_signal(&p->tx_chunk, &p->tx_sig)) goto unlock; /* Now get the receiving side */ if (l4shmc_get_chunk_to(&p->shmcarea, p->create ? "bob" : "joe", WAIT_TIMEOUT, &p->rx_chunk)) goto unlock; if (l4shmc_get_signal_to(&p->shmcarea, p->create ? "bob" : "joe", WAIT_TIMEOUT, &p->rx_sig)) goto unlock; if (l4shmc_connect_chunk_signal(&p->rx_chunk, &p->rx_sig)) goto unlock; L4XV_U(f); if ((irq = l4x_register_irq(l4shmc_signal_cap(&p->rx_sig))) < 0) return -ENOMEM; ch = (struct chunk_head *)l4shmc_chunk_ptr(&p->tx_chunk); ch->next_offs_to_write = 0; ch->next_offs_to_read = 0; ch->writer_blocked = 0; p->tx_ring_size = l4shmc_chunk_capacity(&p->tx_chunk) - sizeof(struct chunk_head); p->rx_ring_size = l4shmc_chunk_capacity(&p->rx_chunk) - sizeof(struct chunk_head); p->tx_ring_start = (char *)l4shmc_chunk_ptr(&p->tx_chunk) + sizeof(struct chunk_head); p->rx_ring_start = (char *)l4shmc_chunk_ptr(&p->rx_chunk) + sizeof(struct chunk_head); p->port.uartclk = 3686400; p->port.ops = &l4ser_shm_pops; p->port.fifosize = 8; p->port.line = num; p->port.iotype = UPIO_MEM; p->port.membase = (void *)1; p->port.mapbase = 1; p->port.flags = UPF_BOOT_AUTOCONF; p->port.irq = irq; return 0; unlock: L4XV_U(f); return -ENOMEM; }