Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

If there's no memory available, is this properly returned by the allocating functions? #87

Open
mrquincle opened this issue Dec 13, 2019 · 4 comments
Assignees

Comments

@mrquincle
Copy link

There are calls to malloc as well as new. In the past we used our own allocation function that returned NULL when memory could not be allocated. It is wise to check that this functionality is still operational.

@mrquincle
Copy link
Author

Check, this is not working correctly.

void print_memory() {                                                                                                   
    int blockSize = 256;                                                                                                
    int i = 1;                                                                                                          
                                                                                                                        
    LOGd("Checking memory with blocksize %d char ...", blockSize);                                                      
    while (true) {                                                                                                      
        char *p = (char *) malloc(i * blockSize);                                                                       
        if (p == NULL) {                                                                                                
            break;                                                                                                      
        } else {                                                                                                        
            LOGd("%d @ 0x%08X", i * blockSize, p);                                                                      
        }                                                                                                               
        free(p);                                                                                                        
        ++i;                                                                                                            
    }                                                                                                                   
    LOGd("Ok for %d char", (i - 1) * blockSize);                                                                        
}                                                                                                                       

This will lead to a fault (reboot) rather than malloc returning NULL.

@mrquincle mrquincle self-assigned this Dec 13, 2019
@mrquincle
Copy link
Author

Which malloc/calloc is used?

/source/conf/cmake/CMakeLists.txt:			LIST(APPEND NORDIC_SOURCE "${MESH_SDK_DIR}/mesh/core/src/mesh_mem_stdlib.c")

Here mesh_mem_malloc returns malloc from stdlib.

In source/CMakeLists.txt you see:

# Use of newlib-nano                                                                                                    
SET(OPTIMIZED_NEWLIB "--specs=nano.specs")            

If we search for the implementation of _sbrk we'll get (if we use -Wl,Map=${PROJECT_NAME}.map) something like:

$> cat crownstone.map | grep -w _sbrk
gcc_arm_none_eabi/lib/thumb/v7e-m+fp/hard/libg_nano.a(lib_a-sbrkr.o) (_sbrk)
 .text._sbrk    0x000000000004cdcc       0x1c libnosys.a(sbrk.o)
                0x000000000004cdcc                _sbrk

Indeed the nano lib implementation is used for _sbrk and malloc (in libg_nano.a) as well as new (in libstdc++_nano.a).

@mrquincle
Copy link
Author

Next question, but on topic. :-) How to solve this?

  • Implement our own _sbrk function. Rather than throwing a hardfault, just return indicating that nothing could be allocated. This can be done in cs_Syscalls.c.

mrquincle pushed a commit that referenced this issue Dec 16, 2019
+ Implement _sbrk that has access to the correct heap/stack variables.

Fixes issue #87.

Might need some more extended love to check all memory conditions. Also,
somehow indicating that there is something fishy going on on a
Crownstone would be good as well. Perhaps this information can be stored
somehow on flash without the need for a call to malloc.
@mrquincle mrquincle added the bug label Dec 17, 2019
@mrquincle
Copy link
Author

Is this still there?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

1 participant