syscalls.c 6.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312
  1. /*
  2. * newlib_stubs.c
  3. *
  4. * Created on: 2 Nov 2010
  5. * Author: nanoage.co.uk
  6. */
  7. #include <errno.h>
  8. #include <sys/stat.h>
  9. #include <sys/times.h>
  10. #include <sys/unistd.h>
  11. #include "stm32f4xx_usart.h"
  12. #include "stm32f4xx.h"
  13. #include "rtc.h"
  14. #include "lwip/sockets.h"
  15. #ifdef SWOTRACE
  16. /* Set STDIO_USART to 255 as flag that trace output on SWO pin used instead */
  17. #define STDIO_USART 255
  18. #else
  19. /* Set USART number */
  20. #define STDIO_USART 1 /* Disable UART stdio */
  21. #endif /* SWOTRACE */
  22. #ifndef STDOUT_USART
  23. #define STDOUT_USART STDIO_USART
  24. #endif
  25. #ifndef STDERR_USART
  26. #define STDERR_USART STDIO_USART
  27. #endif
  28. #ifndef STDIN_USART
  29. #define STDIN_USART STDIO_USART
  30. #endif
  31. #undef errno
  32. extern int errno;
  33. /* Variable to receive characters on SWO */
  34. volatile int32_t ITM_RxBuffer;
  35. /*
  36. environ
  37. A pointer to a list of environment variables and their values.
  38. For a minimal environment, this empty list is adequate:
  39. */
  40. char *__env[1] = { 0 };
  41. char **environ = __env;
  42. int _write(int file, char *ptr, int len);
  43. void _exit(int status) {
  44. _write(1, "exit", 4);
  45. while (1) {
  46. ;
  47. }
  48. }
  49. int _close(int file) {
  50. return -1;
  51. }
  52. /*
  53. execve
  54. Transfer control to a new process. Minimal implementation (for a system without processes):
  55. */
  56. int _execve(char *name, char **argv, char **env) {
  57. errno = ENOMEM;
  58. return -1;
  59. }
  60. /*
  61. fork
  62. Create a new process. Minimal implementation (for a system without processes):
  63. */
  64. int _fork() {
  65. errno = EAGAIN;
  66. return -1;
  67. }
  68. /*
  69. fstat
  70. Status of an open file. For consistency with other minimal implementations in these examples,
  71. all files are regarded as character special devices.
  72. The `sys/stat.h' header file required is distributed in the `include' subdirectory for this C library.
  73. */
  74. int _fstat(int file, struct stat *st) {
  75. st->st_mode = S_IFCHR;
  76. return 0;
  77. }
  78. /*
  79. getpid
  80. Process-ID; this is sometimes used to generate strings unlikely to conflict with other processes. Minimal implementation, for a system without processes:
  81. */
  82. int _getpid() {
  83. return 1;
  84. }
  85. /*
  86. isatty
  87. Query whether output stream is a terminal. For consistency with the other minimal implementations,
  88. */
  89. int _isatty(int file) {
  90. switch (file){
  91. case STDOUT_FILENO:
  92. case STDERR_FILENO:
  93. case STDIN_FILENO:
  94. return 1;
  95. default:
  96. //errno = ENOTTY;
  97. errno = EBADF;
  98. return 0;
  99. }
  100. }
  101. /*
  102. kill
  103. Send a signal. Minimal implementation:
  104. */
  105. int _kill(int pid, int sig) {
  106. errno = EINVAL;
  107. return (-1);
  108. }
  109. /*
  110. link
  111. Establish a new name for an existing file. Minimal implementation:
  112. */
  113. int _link(char *old, char *new) {
  114. errno = EMLINK;
  115. return -1;
  116. }
  117. /*
  118. lseek
  119. Set position in a file. Minimal implementation:
  120. */
  121. int _lseek(int file, int ptr, int dir) {
  122. return 0;
  123. }
  124. /*
  125. sbrk
  126. Increase program data space.
  127. Malloc and related functions depend on this
  128. */
  129. caddr_t _sbrk(int incr) {
  130. extern char _ebss; // Defined by the linker
  131. extern char __bss_end__;
  132. static char *heap_end;
  133. char *prev_heap_end;
  134. if (heap_end == 0) {
  135. //heap_end = &_ebss;
  136. heap_end = &__bss_end__;
  137. }
  138. prev_heap_end = heap_end;
  139. char * stack = (char*) __get_MSP();
  140. if (heap_end + incr > stack)
  141. {
  142. _write (STDERR_FILENO, "Heap and stack collision\n", 25);
  143. errno = ENOMEM;
  144. return (caddr_t) -1;
  145. //abort ();
  146. }
  147. heap_end += incr;
  148. return (caddr_t) prev_heap_end;
  149. }
  150. /*
  151. read
  152. Read a character to a file. `libc' subroutines will use this system routine for input from all files, including stdin
  153. Returns -1 on error or blocks until the number of characters have been read.
  154. */
  155. int _read(int file, char *ptr, int len) {
  156. int n;
  157. int num = 0;
  158. switch (file) {
  159. case STDIN_FILENO:
  160. for (n = 0; n < len; n++) {
  161. #if STDIN_USART == 1
  162. while ((USART1->SR & USART_FLAG_RXNE) == (uint16_t)RESET) {}
  163. char c = (char)(USART1->DR & (uint16_t)0x01FF);
  164. #elif STDIN_USART == 2
  165. while ((USART2->SR & USART_FLAG_RXNE) == (uint16_t) RESET) {}
  166. char c = (char) (USART2->DR & (uint16_t) 0x01FF);
  167. #elif STDIN_USART == 3
  168. while ((USART3->SR & USART_FLAG_RXNE) == (uint16_t)RESET) {}
  169. char c = (char)(USART3->DR & (uint16_t)0x01FF);
  170. #elif STDIN_USART == 255
  171. /* TODO Test this feature */
  172. char c = (char)ITM_ReceiveChar();
  173. #elif STDIN_USART == 0
  174. /* Return NULL */
  175. char c = '\0';
  176. #endif
  177. *ptr++ = c;
  178. num++;
  179. }
  180. break;
  181. default:
  182. errno = EBADF;
  183. return -1;
  184. }
  185. return num;
  186. }
  187. /*
  188. stat
  189. Status of a file (by name). Minimal implementation:
  190. int _EXFUN(stat,( const char *__path, struct stat *__sbuf ));
  191. */
  192. int _stat(const char *filepath, struct stat *st) {
  193. st->st_mode = S_IFCHR;
  194. return 0;
  195. }
  196. /*
  197. times
  198. Timing information for current process. Minimal implementation:
  199. */
  200. clock_t _times(struct tms *buf) {
  201. return -1;
  202. }
  203. /*
  204. unlink
  205. Remove a file's directory entry. Minimal implementation:
  206. */
  207. int _unlink(char *name) {
  208. errno = ENOENT;
  209. return -1;
  210. }
  211. /*
  212. wait
  213. Wait for a child process. Minimal implementation:
  214. */
  215. int _wait(int *status) {
  216. errno = ECHILD;
  217. return -1;
  218. }
  219. /*
  220. write
  221. Write a character to a file. `libc' subroutines will use this system routine for output to all files, including stdout
  222. Returns -1 on error or number of bytes sent
  223. */
  224. int _write(int file, char *ptr, int len) {
  225. int n;
  226. switch (file) {
  227. case STDOUT_FILENO: /*stdout*/
  228. for (n = 0; n < len; n++) {
  229. #if STDOUT_USART == 1
  230. while ((USART1->SR & USART_FLAG_TC) == (uint16_t)RESET) {}
  231. USART1->DR = (*ptr++ & (uint16_t)0x01FF);
  232. #elif STDOUT_USART == 2
  233. while ((USART2->SR & USART_FLAG_TC) == (uint16_t) RESET) {
  234. }
  235. USART2->DR = (*ptr++ & (uint16_t) 0x01FF);
  236. #elif STDOUT_USART == 3
  237. while ((USART3->SR & USART_FLAG_TC) == (uint16_t)RESET) {}
  238. USART3->DR = (*ptr++ & (uint16_t)0x01FF);
  239. #elif STDOUT_USART == 255
  240. ITM_SendChar(*ptr++ & (uint16_t)0x00FF);
  241. #endif
  242. }
  243. break;
  244. case STDERR_FILENO: /* stderr */
  245. for (n = 0; n < len; n++) {
  246. #if STDERR_USART == 1
  247. while ((USART1->SR & USART_FLAG_TC) == (uint16_t)RESET) {}
  248. USART1->DR = (*ptr++ & (uint16_t)0x01FF);
  249. #elif STDERR_USART == 2
  250. while ((USART2->SR & USART_FLAG_TC) == (uint16_t) RESET) {
  251. }
  252. USART2->DR = (*ptr++ & (uint16_t) 0x01FF);
  253. #elif STDERR_USART == 3
  254. while ((USART3->SR & USART_FLAG_TC) == (uint16_t)RESET) {}
  255. USART3->DR = (*ptr++ & (uint16_t)0x01FF);
  256. #elif STDERR_USART == 255
  257. ITM_SendChar(*ptr++ & (uint16_t)0x00FF);
  258. #endif
  259. }
  260. break;
  261. default:
  262. errno = EBADF;
  263. return -1;
  264. }
  265. return len;
  266. }
  267. #ifndef BT6702_SERVICE
  268. int _gettimeofday( struct timeval *tv, void *tzvp )
  269. {
  270. tv->tv_sec = RTC_GetUnixTime(); // convert to seconds
  271. tv->tv_usec = 0; // get remaining microseconds
  272. return 0; // return non-zero for error
  273. }
  274. #endif