No announcement yet.

file_Closed command

  • Filter
  • Time
  • Show
Clear All
new posts

  • file_Closed command

    I've got multiple image index gci files that i load up and I figured its probably good practice to close the index after finished. so I started doing a file_Close(index);

    so example
    tmp2 := file_LoadImageControl("SCROLLBG.DAT", "SCROLLBG.GCI", 1);
    do some stuff

    then il go load a new image, do some stuff and close.

    problem is, when testing it out, the first images in tmp2 load fine, but once they get closed and i load the next image index, it returns null... I've got no idea why, ive tried adding/removing file_Mount / file_Unmount as well but nothing seems to affect it. The strange thing is that even though the next image index wont load, I can still play a wave file...

  • #2

    file_LoadImageControl returns a pointer to a structure allocation. It does not return a file so you can't use file_Close(). Remove the file_Close() and you should be ok.

    If you are worried about losing memory then just use this:

    func ShowMem()
    gfx_MoveTo(30,30);//Adjust these values to a good
    //place for your app.
    //txt_MoveCursor(0,0);//Or you can use this method of
    //locating the output.
    print([DEC5Z] mem_Heap());
    //pause(3000);//Enable this line if you need time to
    //see the value.

    Call this function in your code before and after sections to check if you are losing memory. Note that it shows the largest block of memory available at the time, not total memory.

    I have found this very helpful in locating memory leaks, etc.


    • #3

      ya i definitely get a decrease. After I load a function from my home screen function, then return to the homescreen, the largest chunk from before was 3166, after the function returns to home, the largest chunk is 1658..if I attempt to load the function again (which does not work correctly when loaded a second time) the after chunk decreases to 536...


      • #4

        Check this thread on the same subject.

        You obviously have a memory leak, now you just have to find it. Make sure you are deallocating any memory allocated, using mem_Free(), before you return from any called function.

        Good luck!


        • #5

          Hi tas thanks for the reply. Is that thread relevent even though I never use file_Run.. im just using one main program, however it is quite big at 7594bytes.


          • #6

            So in an attempt to test things out, I split my program into a HOME.4XE (the main program) and a new window program NEW.4FN. I am trying to call NEW.4FN and pass a variable m to it, but its not seeming to work. Its possible I am passing it wrong. I have tried by simply putting file_Run("NEW.4FN", m) and I also tried making a 2 item array arglist[2] := [2, m] then a pointer argptr := *arglist and did file_Run("NEW.4FN", argptr);

            Then in NEW.4FN I have:
            func main(var f)
            gfx_Set(SCREEN_MODE,LANDSCAPE); // put device into landscape mode
            file_Run("HOME.4XE", 0);

            NewWindow() is in the NEW.4FN file...

            so the problem is the NEW.4FN never is passed the argument m... do you know what the correct syntax for doing this is?


            • #7

              Hi mike64b,Sorry, I assumed you were calling external functions. 7594 bytes should not have a problem running provided you aren't opening a lot of files at the same time and/or allocating a lot of RAM.
              I am using a uOLED 32028-P1T module running PmmC 2.2 and I am using 4DGL Workshop 3 version

              I have found it best to split the program into externally called functions when my main program reaches about 8000 bytes.

              The main program should be compiled to flash.

              In the main program:
              • Check for uSD and mount the file system.
              • Declare a global variable, ArgList[n], where n is the number of arguments plus 1. Plus 1 because the first argument in the list is the COUNT of arguments to be passed.
              • Set an argument list for passing arguments to called functions.
              • Call the function and pass the argument list.
              • DO NOT UNMOUNT THE FILE SYSTEM before calling the new program.
                The called program should be compiled as a 4FN file and stored on the uSD card.

                In the called program:
                Assign the passed arguments into copies of the original global vars.Change any values you need to.Pass back the changed values into the passed arguments.Return to the calling program.
              As this is a bit complex here is a more detailed example:

              The main program:

              #platform "uOLED-32028-P1_GFX2"

              #STACK 300

              //stack must be large enough to be
              //shared with called program.
              #MODE RUNFLASH //This is a 'top down' main program //and must be run from FLASH.

              //Global variables in main function:
              AString[20]; //20 words, 40 chars.
              ArgList[5]; //An array of arguments to pass to the //called function. Size is number of args plus 1.

              func SetArgList()//ALL args in one list so any //program can change the global values!
              ArgList[0] := 4;//Number of arguments in the //list.
              ArgList[1] := AString;//pass string as buffer //name.
              ArgList[2] := AWordWhichCantBeChanged;//If you //just pass the word, you can't change it in //called program.
              ArgList[3] := &AWordWhichCanBeChanged;//You must //pass the ADDRESS of word variables to be able to //change it in the called program.
              ArgList[4] := ABuffer;//pass as buffer name.

              SetArgList();//Set up the arg list, passing all //necessary values on.


              The called program:

              #platform "uOLED-32028-P1_GFX2"

              //Declare the global variables exactly as in the main program:





              func main(var arg1, var arg2, var arg3, var arg4)//Note arg0 //(the count) is not listed!

              var i;

              to(AString);print([STR] arg1);//Assign string to local string //this way.

              AWordWhichCantBeChanged := arg2;

              AWordWhichCanBeChanged := *arg3;//Since address of var was //passed, must dereference to get actual value.

              //Now to load the buffer:

              i := 0;

              while(i < 50)

              ABuffer[i] := arg4[i];




              //Now to return to the calling program:

              to(arg1); print([STR]AString);//This rewrites the original //string in the calling program.

              *arg2 := AWordWhichCantBeChanged;//This won't change the //original value because it wasn't passed in properly.

              *arg3 := AWordWhichCanBeChanged;//This will change the main //program variable.

              i := 0;



              • #8

                When releasing an image control, you just release the memory it was using - there is no file to close eg:-

                tmp2 := file_LoadImageControl("SCROLLBG.DAT", "SCROLLBG.GCI", 1);
                do some stuff
                file_Close(tmp2); // THIS IS INCORRECT

                Should be:
                tmp2 := file_LoadImageControl("SCROLLBG.DAT", "SCROLLBG.GCI", 1);
                do some stuff
                mem_Free(tmp2); // fre the memory that image control was using


                • #9

                  Hey guys I fixed a lot of my problems by using these methods of splitting things up. However a strange issue remains, In the main calling program, I set the text height to 2, then when I call the called program, I also set the text height to 2, it displays fine, but once I return to the calling program, the text is still height 2 but seems to become bold..

                  I fixed it by adding TEXT_BOLD(OFF); however it seems strange since i have not used the text_Bold command anywhere... seems its some random bug?