sysmem.c 2.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687
  1. /**
  2. ******************************************************************************
  3. * @file sysmem.c
  4. * @author Generated by STM32CubeMX
  5. * @brief System Memory calls file
  6. *
  7. * For more information about which C functions
  8. * need which of these lowlevel functions
  9. * please consult the Newlib or Picolibc libc manual
  10. ******************************************************************************
  11. * @attention
  12. *
  13. * Copyright (c) 2025 STMicroelectronics.
  14. * All rights reserved.
  15. *
  16. * This software is licensed under terms that can be found in the LICENSE file
  17. * in the root directory of this software component.
  18. * If no LICENSE file comes with this software, it is provided AS-IS.
  19. *
  20. ******************************************************************************
  21. */
  22. /* Includes */
  23. #include <errno.h>
  24. #include <stdint.h>
  25. #include <stddef.h>
  26. /**
  27. * Pointer to the current high watermark of the heap usage
  28. */
  29. static uint8_t *__sbrk_heap_end = NULL;
  30. /**
  31. * @brief _sbrk() allocates memory to the newlib heap and is used by malloc
  32. * and others from the C library
  33. *
  34. * @verbatim
  35. * ############################################################################
  36. * # .data # .bss # newlib heap # MSP stack #
  37. * # # # # Reserved by _Min_Stack_Size #
  38. * ############################################################################
  39. * ^-- RAM start ^-- _end _estack, RAM end --^
  40. * @endverbatim
  41. *
  42. * This implementation starts allocating at the '_end' linker symbol
  43. * The '_Min_Stack_Size' linker symbol reserves a memory for the MSP stack
  44. * The implementation considers '_estack' linker symbol to be RAM end
  45. * NOTE: If the MSP stack, at any point during execution, grows larger than the
  46. * reserved size, please increase the '_Min_Stack_Size'.
  47. *
  48. * @param incr Memory size
  49. * @return Pointer to allocated memory
  50. */
  51. void *_sbrk(ptrdiff_t incr)
  52. {
  53. extern uint8_t _end; /* Symbol defined in the linker script */
  54. extern uint8_t _estack; /* Symbol defined in the linker script */
  55. extern uint32_t _Min_Stack_Size; /* Symbol defined in the linker script */
  56. const uint32_t stack_limit = (uint32_t)&_estack - (uint32_t)&_Min_Stack_Size;
  57. const uint8_t *max_heap = (uint8_t *)stack_limit;
  58. uint8_t *prev_heap_end;
  59. /* Initialize heap end at first call */
  60. if (NULL == __sbrk_heap_end)
  61. {
  62. __sbrk_heap_end = &_end;
  63. }
  64. /* Protect heap from growing into the reserved MSP stack */
  65. if (__sbrk_heap_end + incr > max_heap)
  66. {
  67. errno = ENOMEM;
  68. return (void *)-1;
  69. }
  70. prev_heap_end = __sbrk_heap_end;
  71. __sbrk_heap_end += incr;
  72. return (void *)prev_heap_end;
  73. }
  74. #if defined(__PICOLIBC__)
  75. // Picolibc expects syscalls without the leading underscore.
  76. // This creates a strong alias so that
  77. // calls to `sbrk()` are resolved to our `_sbrk()` implementation.
  78. __strong_reference(_sbrk, sbrk);
  79. #endif