Thread: How to use an array of FILE pointers in a seperate function?

  1. #1
    Registered User
    Join Date
    Apr 2019
    Posts
    114

    How to use an array of FILE pointers in a seperate function?

    I know my pointer game is crap. I can use them, and most situations I encounter, call for something I have done before.

    I have come across a new problem with my pointers and would like to figure this out. I know I can do it another way, but in my mind it would be sloppy, and I'd really like to fully understand pointers.

    Here is the code (thus far):
    Code:
    // Declare includes.
    #include <errno.h>
    #include <stdio.h>
    #include <stdlib.h>
    #include <string.h>
    
    // Declare defines.
    #define BUFFER_SIZE              500
    #define MUSIC_LIST_FILE            "full_music_list"
    #define SYSTEM_PLAYLIST_FOLDER     "/Shared/Playlists/System/"
    
    // Declare function prototypes.
    void create_files (FILE **lists, int total);
    
    int main (void)
    {
    // Declare variables.
        FILE *lists = NULL;
        FILE *fp = fopen(MUSIC_LIST_FILE, "r");
        int list_total = 19;
    
    // Create lists and file pointers.
        if(fp != NULL)
            create_files(&lists, list_total);
    
    // Exit cleanly.
        exit(EXIT_SUCCESS);
    }
    
    void create_files (FILE **lists, int total)
    {
    // Declare variables.
        char buffer[BUFFER_SIZE] = {0};
        int counter = {0};
    
    // Create enough entries for all the files.
        if((*lists = malloc(sizeof(FILE) * total)) == NULL)
        {
            fprintf(stderr, "%s error: malloc failed\n", __func__);
            exit(EXIT_FAILURE);
        }
    
        for(counter = 0; counter < total; counter++)
        {
    // Create filename.
            sprintf(buffer, "%sPlaylist.%02d.pls", SYSTEM_PLAYLIST_FOLDER, counter);
    
    // Create file pointer.
            if(((*lists)[counter] = fopen(buffer, "w")) == NULL)
            {
                fprintf(stderr, "%s error: fopen failed (%s) (%s)\n", __func__, strerror(errno), buffer);
                exit(EXIT_FAILURE);
            }
        }
    }
    And here is the error I get:
    Code:
    create_music_lists.c:49:27: error: incompatible types when assigning to type ‘FILE’ from type ‘FILE *’
       49 |   if(((*lists)[counter] = fopen(buffer, "w")) == NULL)
          |                           ^~~~~
    compilation terminated due to -Wfatal-errors.
    Why is it complaining that I'm putting a `FILE *` into a `FILE`. The only declarations I have are for `FILE *`. Can someone please help me understand this enough to get it working?

  2. #2
    Registered User
    Join Date
    Dec 2017
    Posts
    1,628
    In main, lists needs to be FILE**.
    That makes it a pointer that can point to an array of FILE*.

    And you need to pass it to create_files as a FILE***.
    The extra level of indirection allows you to modify the pointer in main.
    Code:
    #include <errno.h>
    #include <stdio.h>
    #include <stdlib.h>
    #include <string.h>
     
    #define MAX_FILENAME             500
    #define MUSIC_LIST_FILE          "full_music_list"
    #define SYSTEM_PLAYLIST_FOLDER   "/Shared/Playlists/System/"
     
    void create_files(FILE ***lists, int total);
     
    int main()
    {
        FILE **lists = NULL;
        FILE *fp = fopen(MUSIC_LIST_FILE, "r");
        int list_total = 19;
     
        if (fp == NULL)
        {
            perror("Cannot open " MUSIC_LIST_FILE);
            exit(EXIT_FAILURE);
        }
     
        create_files(&lists, list_total);
     
        exit(0);
    }
     
    void create_files(FILE ***lists, int total)
    {
        *lists = malloc(sizeof(FILE*) * total);  // note it's sizeof(FILE*) here
     
        if (*lists == NULL)
        {
            fprintf(stderr, "%s error: malloc failed\n", __func__);
            exit(EXIT_FAILURE);
        }
     
        for (int counter = 0; counter < total; counter++)
        {
            char filename[MAX_FILENAME] = { 0 };
            sprintf(filename, "%sPlaylist.%02d.pls", SYSTEM_PLAYLIST_FOLDER, counter);
     
            (*lists)[counter] = fopen(filename, "w");
     
            if ((*lists)[counter] == NULL)
            {
                fprintf(stderr, "%s error: fopen failed (%s) (%s)\n", __func__, strerror(errno), filename);
                exit(EXIT_FAILURE);
            }
        }
    }
    Last edited by john.c; 07-29-2022 at 07:44 PM.
    A little inaccuracy saves tons of explanation. - H.H. Munro

  3. #3
    Registered User
    Join Date
    Apr 2019
    Posts
    114
    Tyvm, it seems the problem, other than what was mentioned, was my malloc of `FILE` instead of `FILE *`.

  4. #4
    Registered User
    Join Date
    Dec 2017
    Posts
    1,628
    Quote Originally Posted by Yonut View Post
    Tyvm, it seems the problem, other than what was mentioned, was my malloc of `FILE` instead of `FILE *`.
    Although that is an error (I mentioned it in a comment in the code), it wouldn't have caused a problem since a FILE struct is larger than a pointer. It would've just wasted a little space.
    A little inaccuracy saves tons of explanation. - H.H. Munro

  5. #5
    and the hat of int overfl Salem's Avatar
    Join Date
    Aug 2001
    Location
    The edge of the known universe
    Posts
    39,659
    Bear in mind that the number of files you can have open at once is relatively small (compared say to the amount of memory you can allocate).

    File Handling | Microsoft Docs
    How to Use Ulimit Command in Linux [Control System Resource]
    These limits can be altered, but beware of permissions necessary to raise limits.

    A handful of files in a single directory shouldn't be a problem.

    But you wouldn't want to scale this up to span an entire file system.
    If you dance barefoot on the broken glass of undefined behaviour, you've got to expect the occasional cut.
    If at first you don't succeed, try writing your phone number on the exam paper.

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. Replies: 43
    Last Post: 05-23-2013, 03:01 PM
  2. Passing pointers to functions in seperate source files
    By derekeverett in forum C Programming
    Replies: 12
    Last Post: 10-08-2009, 07:15 AM
  3. extern Global array in seperate .h file
    By rocketman03 in forum C++ Programming
    Replies: 1
    Last Post: 09-30-2009, 06:03 AM
  4. File Pointers in Seperate Functions
    By Sn0mAN in forum C Programming
    Replies: 6
    Last Post: 07-04-2007, 06:45 AM
  5. seperate function
    By s_jsstevens in forum C Programming
    Replies: 8
    Last Post: 04-30-2007, 01:12 PM

Tags for this Thread