Thread: Trying to modify array in a shared library function

  1. #1
    Registered User
    Join Date
    May 2013
    Posts
    4

    Trying to modify array in a shared library function

    Really straight forward, but I'm trying to build a shared object and I'm testing it as I'm writing it (with a test exectuable I built using dlopen()). I've gotten to where I can print something from the shared object but when I pass an array I want modified it misbehaves.

    Here is the shared object's source code:

    Code:
    #include <stdio.h>
    #include <stdlib.h>
    #include <libconfig.h>
    #include <sys/stat.h>
    #include <sys/acl.h>
    #include <dlfcn.h>
    #include <string.h>
    #include <libgen.h>
    #include <grp.h>
    #include <unistd.h>
    
    
    int** scratch_modArr ( int ** givenList ){
    
    
            int numgroups=3;
    
    
            *givenList=(int*)malloc(  numgroups * sizeof(int) * 6 );
            **givenList=500;
    
    
            printf("modArr Ping: %d\n", (*givenList)[0]);
    
    
            return givenList;
    
    
    }
    
    
    void scratch_ping(){
            printf("main ping\n");
    }
    And the test executable's code:

    Code:
    #include <stdio.h>
    #include <dlfcn.h>
    
    
    int main (){
    
    
            void *(*scratch_ping)();
            int **(*scratch_modArr)();
            void *libHandle;
            int newArr[1]= {1};
    
    
            libHandle=dlopen("./libscratch.so", RTLD_LAZY);
            scratch_ping=dlsym(libHandle, "scratch_ping");
            scratch_modArr=dlsym(libHandle, "scratch_modArr");
    
    
            printf("Before Call: %d\n", newArr[0]);
    
    
            (*scratch_ping)();
            (*scratch_modArr)(newArr);
    
    
            printf("After Call: %d\n", newArr[0]);
    
    
            return 0;
    }
    This is the executable's command line output:

    Code:
    [root@thatch scratch]# ./scratch-test
    Before Call: 1
    main ping
    modArr Ping: 500
    After Call: 7986464
    [root@thatch scratch]#
    Obviously, something's gone awry. My assumption was that malloc gave me a new segment of memory which killed off my old pointer. But I'm not sure how to modify the return type on the functions so that it can do that.
    Last edited by JulietBoy; 05-23-2013 at 11:37 AM. Reason: incomplete sentence

  2. #2
    Registered User
    Join Date
    May 2012
    Posts
    1,066
    Code:
    int** scratch_modArr ( int ** givenList ){   // in shared library
    ...
    int **(*scratch_modArr)();   // in executable
    Shouldn't you also declare the correct input parameter in your executable?

    Bye, Andreas

  3. #3
    Registered User
    Join Date
    May 2013
    Posts
    4
    Quote Originally Posted by AndiPersti View Post
    Code:
    int** scratch_modArr ( int ** givenList ){   // in shared library
    ...
    int **(*scratch_modArr)();   // in executable
    Shouldn't you also declare the correct input parameter in your executable?

    Bye, Andreas
    Thanks for the quick response!

    I made the updates but now I'm getting the following error when I try to compile:

    Code:
    [root@thatch scratch]# make
    cc scratch-test.c -o scratch-test -ldl
    scratch-test.c: In function ‚main‚:
    scratch-test.c:18: error: incompatible types when assigning to type ‚int[1]‚ from type ‚int **‚
    make: *** [scratch-test] Error 1
    [root@thatch scratch]#
    This is line 18 from the executable:

    Code:
     newArr=(*scratch_modArr)(newArr);
    My understanding is that with "int **" I should be returning the array itself, so since I don't ever re-define newArr in the executable, it should be alright to just pass it back to newArr. Is that not correct?
    Last edited by JulietBoy; 05-23-2013 at 12:59 PM. Reason: clarity

  4. #4
    Registered User
    Join Date
    May 2013
    Posts
    4
    Another question related to this, I was under the impression that in C arrays are pointers. When I typecast to either "int*" or "int**" it tells me that same thing about newArr being int[1]. Are they somehow different data types?

  5. #5
    Registered User
    Join Date
    Aug 2005
    Location
    Austria
    Posts
    1,990
    C doesn't allow to assign to arrays. And no I don't want another discussion about arrays and pointers
    Kurt

  6. #6
    Registered User
    Join Date
    May 2013
    Posts
    4
    Is there an already existing thread you can point me to?

  7. #7
    C++ Witch laserlight's Avatar
    Join Date
    Oct 2003
    Location
    Singapore
    Posts
    28,341
    Quote Originally Posted by JulietBoy
    Another question related to this, I was under the impression that in C arrays are pointers. When I typecast to either "int*" or "int**" it tells me that same thing about newArr being int[1]. Are they somehow different data types?
    In C, arrays are not pointers, though in most contexts, an array will be converted to a pointer to its first element.
    Quote Originally Posted by Bjarne Stroustrup (2000-10-14)
    I get maybe two dozen requests for help with some sort of programming or design problem every day. Most have more sense than to send me hundreds of lines of code. If they do, I ask them to find the smallest example that exhibits the problem and send me that. Mostly, they then find the error themselves. "Finding the smallest program that demonstrates the error" is a powerful debugging tool.
    Look up a C++ Reference and learn How To Ask Questions The Smart Way

  8. #8
    Registered User
    Join Date
    May 2012
    Posts
    1,066
    Quote Originally Posted by JulietBoy View Post
    Is there an already existing thread you can point me to?
    I'd rather recommend reading through section 6 of the C-FAQ and optionally working through this tutorial.

    It looks like you just want to create a new dynamic array in scratch_modArr(). So why not simply declare it like
    Code:
    int *scratch_modArr(void)
    and later use it like
    Code:
    int *new_array = scratch_modArr();
    I've also noticed another type mismatch in your code:
    Code:
    void scratch_ping(){  // in shared library
    ...
    void *(*scratch_ping)();  // in executable
    scratch_ping() is defined as returning void but in your executable you have a pointer to a function returning void*, i.e. a pointer to void.

    Code:
    scratch_ping=dlsym(libHandle, "scratch_ping");
    scratch_modArr=dlsym(libHandle, "scratch_modArr");
    Assigning the return value of dlsym (void *) to a function pointer is undefined in the C Standard. See also the example and rationale on the man page.

    Bye, Andreas

  9. #9
    Registered User
    Join Date
    Mar 2010
    Posts
    583
    You definitely can't pretend that arrays are pointers when doing this sort of thing. You can't modify an array to point to something else. If you forget the shared object stuff:
    Code:
      int arr[10];
      arr = malloc(16); // Compiler says NO!
    Your code...

    Code:
            *givenList=(int*)malloc(  numgroups * sizeof(int) * 6 );
            **givenList=500;
     
            printf("modArr Ping: %d\n", (*givenList)[0]);
    So this looks like it's meant to... allocate some memory, and store a number? You must make sure whatever is passed as an argument is actually writable, e.g.:

    Code:
    int newArrStore[1]= {1};  // Local array store
    int *newArr = newArrStore; // Pointer to local array story
    (*scratch_modArr)(&newArr);  // Pass address of pointer
    I think it's a lot clearer to just use the return value. Return an int* and assign it to newArr.

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. modify function pass it array
    By a.mlw.walker in forum C Programming
    Replies: 12
    Last Post: 08-01-2011, 04:03 AM
  2. Replies: 1
    Last Post: 04-17-2011, 10:45 AM
  3. shared library for QNX
    By ReeV in forum C Programming
    Replies: 3
    Last Post: 05-06-2009, 10:58 AM
  4. Shared Library Not Executing Function
    By Osiris990 in forum Linux Programming
    Replies: 8
    Last Post: 01-14-2008, 12:06 PM
  5. Shared Library
    By Kinasz in forum Linux Programming
    Replies: 5
    Last Post: 10-07-2002, 09:25 AM