fin.exe memory allocation grows

beno.pulverbeno.pulver Member Posts: 31
Good morning,

We archive reports/documents as PDF and create a link file for the external archiving system. The whole process is done in a batchjob (codeunit) which calls for each table record the corresponding report.

My problem is now, that the allocated memory of the client (fin.exe) grows and grows and grows. After less than 1'000 printed reports, the fin.exe gots more than 200 MB. That causes of course problems, because after a while there is no more RAM available!

I detected, that reports with bitmaps use around 180 K and a creation of an automation (CREATE) use another 300 K. So each printed report uses around 500 K and the used memory is not given back, it remains.

I already changed the REPORT.RUNMODAL to a call of a report variable and did CLEAR the variable. I did also delete the automation (CLEAR).
But all this did not help.

Do you have any idea, how I can avoid the growing allocation of memory???

Thank you very much, Beno

Answers

  • sresre Member Posts: 62
    Just a blind guess: Might be that a COMMIT could help. I guess you have a table that helps you to keep track of the items which have to be processed and where you delete the entries or set a flag of some kind.

    Could be that all the information is cached until you update the database with a COMMIT. But as mentioned before: Not really sure if this has anything to do with it.

    Sascha
  • ta5ta5 Member Posts: 1,164
    Do you use "myReport.runmodal" or report.runmodal("myReport")?
    Could be a difference in things like that.

    Thomas
  • beno.pulverbeno.pulver Member Posts: 31
    Hello again,

    thank you for your replies.

    I have added a COMMIT. But it did not realy help.
    The different reports are called wiht "REPORT.RUNMODAL(ReportID,FALSE,FALSE,SalesInvHeader);"

    Like I said, there are two reasons for the growth. One is the bitmaps in the printed reports and one is the create automation (even if it is cleared before and afterwards).

    Best regards, Beno.
  • kinekine Member Posts: 12,562
    1) Try to create the automation only once if possible, e.. through single instance codeunit
    2) Using global or local variables can be different, all depends on the scope of the variable etc.
    Kamil Sacek
    MVP - Dynamics NAV
    My BLOG
    NAVERTICA a.s.
  • beno.pulverbeno.pulver Member Posts: 31
    Hello Kamil,

    thank you very much. Here some details and questions to your proposals:

    I've created a batch codeunit which calls another codeunit like following example:

    Codeunit A calls function AA.
    In function AA of codeunit A all necessary tables/records to be printed are read.
    Function AA of codeunit A calls the function BA in codeunit B with information of the read record.
    Function BA in codeunit B calls function BB and function BC.

    Function BB performs a CLEAR of the automation,
    a CREATE of the automation,
    the processing of the automation and finally
    a CLEAR of the automation
    The automation is declared as global variable. After the CREATE, the memory grows up to 360 K.
    After the CLEAR there is still 300 K. And that everytime the CREATE/CLEAR is executed. That means
    for every report to be printed/archived the memory grows 300 K.

    Function BC prints the report (e.g. an invoice) as PDF. The printing is performed with
    "REPORT.RUNMODAL(ReportID,FALSE,FALSE,SalesInvHeader);"
    Most of the reports contain bitmaps. For reports with bitmaps the memory grows another 180 k, everytime.
    For reports without bitmaps, the memory does not grow at all.

    And here 4 questions:

    1. As far as I understand, I should not CREATE everythime the automation? That must be done with the check ISCLEAR, or?
    2. Which part of the code should be transfered to a single instance codeunit and what would be the benefit?
    3. What do you mean with the global and local variables?
    4. Do you also have a proposal for bitmaps?

    Thank you very much for your help!!!!
    Beno
  • kinekine Member Posts: 12,562
    1) Yes create the automation only once if possible using ISCLEAR to check if it is already created
    2) You can move code regarding the automation into the singleinstance codeunit to create the automation only once per client run and call all functions of the automation through this codeunit (I do not know which functionality is the automation doing to give you more details).
    3) You can define variables ad global (defined for whole object, e.g. codeunit) or local (defined for the function only). The local variables are released right after the function finish. Global variables are released after the scope of the object ends. E.g. in connection with RecordRef datatype variable is better to use local variable which will be - created, initilaized (open some record), used, closed, released - during some function call than using one global variable which will be - created, initialized (open), used, closed, open, used, closed, ...., released, because there can be memory leak by each opening of the variable. If the variable is defined as local, and if my knowledge is correct, local variables are allocated in the memory stack, these local variables will be released from the stack right after the function finish. Global variables are allocated in memory heap and it can lead to memory leak if the heap is not correctly used.
    4) Regarding the bitmaps all depends again on how you are using them (BLOB field, etc.)
    Kamil Sacek
    MVP - Dynamics NAV
    My BLOG
    NAVERTICA a.s.
  • beno.pulverbeno.pulver Member Posts: 31
    Kamil, THANK YOU!!!

    your proposal to put the code of the automation in another "single instance" codeunit was great!
    Without this change, the fin.exe allocated 72 MB of RAM after 145 printed docments.
    With the proposed change, the fin.exe allocated 31 MB of RAM after 145 printed documents and did not increase very much.

    The only problem is still the bitmap in the reports. The bitmap is stored as BLOB in a table. While printing the reports, the value is retrieved with
    recCompanyInfoG.CALCFIELDS("Gray Bar in CI Forms");.
    In the coresponding section there is a PictureBox, the SourceExpr is recCompanyInfoG."Gray Bar in CI Forms".

    The printing of such reports allocates still some memory to the fin.exe.

    So if you also have a solution for that... But already the first proposal was great!

    Thank you, Beno
  • kinekine Member Posts: 12,562
    With the bitmap, if it is just fixed bitmap, still same, you can use same way as for the automation. Just add into the singleinstance codeunit function, which will read the record into variable and calcfiled the value only once, and after that will just return the record to the calling process through the parameters. It means you can call something like mycu.GetMyPicture(recCompanyInfoG) and you are done.
    Kamil Sacek
    MVP - Dynamics NAV
    My BLOG
    NAVERTICA a.s.
  • kinekine Member Posts: 12,562
    And of course, there will be some RAM increase because the client cache is allocated dynamically and NAV can take more than 100MB for this cache if there is enough free mem.
    Kamil Sacek
    MVP - Dynamics NAV
    My BLOG
    NAVERTICA a.s.
Sign In or Register to comment.