POK
buffersend.c
1 /*
2  * POK header
3  *
4  * The following file is a part of the POK project. Any modification should
5  * made according to the POK licence. You CANNOT use this file or a part of
6  * this file is this part of a file for your own project
7  *
8  * For more information on the POK licence, please see our LICENCE FILE
9  *
10  * Please follow the coding guidelines described in doc/CODING_GUIDELINES
11  *
12  * Copyright (c) 2007-2009 POK team
13  *
14  * Created by julien on Thu Jan 15 23:34:13 2009
15  */
16 
17 #include <core/dependencies.h>
18 
19 #ifdef POK_NEEDS_MIDDLEWARE
20 #ifdef POK_NEEDS_BUFFERS
21 
22 #include <errno.h>
23 #include <types.h>
24 #include <core/event.h>
25 #include <core/time.h>
26 #include <libc/string.h>
27 #include <middleware/buffer.h>
28 
29 extern pok_buffer_t pok_buffers[POK_CONFIG_NB_BUFFERS];
30 extern char pok_buffers_data[1024];
31 
32 pok_ret_t pok_buffer_send (const pok_buffer_id_t id,
33  const void* data,
34  const pok_port_size_t len,
35  const uint64_t timeout)
36 {
37  pok_ret_t ret;
38 
39  if (id > POK_CONFIG_NB_BUFFERS)
40  {
41  return POK_ERRNO_EINVAL;
42  }
43 
44  if (pok_buffers[id].ready == FALSE)
45  {
46  return POK_ERRNO_EINVAL;
47  }
48 
49  if (data == NULL)
50  {
51  return POK_ERRNO_EINVAL;
52  }
53 
54  if (len <= 0)
55  {
56  return POK_ERRNO_EINVAL;
57  }
58 
59  if (len > (pok_buffers[id].size * pok_buffers[id].msgsize))
60  {
61  return POK_ERRNO_EINVAL;
62  }
63 
64  pok_event_lock (pok_buffers[id].lock);
65 
66  while (pok_buffers[id].full)
67  {
68  if (timeout == 0)
69  {
70  pok_event_unlock (pok_buffers[id].lock);
71  return POK_ERRNO_FULL;
72  }
73  else
74  {
75  ret = pok_event_wait (pok_buffers[id].lock, timeout);
76  if (ret != POK_ERRNO_OK)
77  {
78  pok_event_unlock (pok_buffers[id].lock);
79  return ret;
80  }
81  }
82  }
83 
84  memcpy (&pok_buffers_data[pok_buffers[id].index + pok_buffers[id].off_e], data, len);
85  pok_buffers[id].off_e = (pok_buffers[id].off_e + len ) % pok_buffers[id].size;
86 
87  if (pok_buffers[id].off_e == pok_buffers[id].off_b)
88  {
89  pok_buffers[id].full = TRUE;
90  }
91 
92  pok_buffers[id].empty = FALSE;
93 
94  pok_event_unlock (pok_buffers[id].lock);
95 
96  pok_event_broadcast (pok_buffers[id].lock);
97 
98  return POK_ERRNO_OK;
99 }
100 
101 #endif /* POK_NEEDS_BUFFERS */
102 #endif