We are using FastReport to generate reports, while we are developing on our Windows machines, it is possible to generate pdf files that are + 10 pages in size, but when we publish this (target runtime - Linux x64) and move it over to our Centos8 instance (running with nginx - on a systemd service), a report that is bigger than +- 2 pdf pages will cause an Out Of Memory exception.
Im wondering what is a possible cause for this? Is it perhaps possible that the systemd service is limited?
Steps I've taken:
contacted FastReport support, they provided us a workaround but this also causes a Out of Memory exception - I think its not their fault, as it works on our development Windows machine - maybe the configuration of the Linux server is't done correctly
tried to add more RAM onto the machine (currently at 16 gb RAM and 16 gb swap - development machine has 16 GB)
tried to trace memory usage with top / htop command, I noticed the service was only using 1% of available RAM
played around with ulimits to try and increase the maximum available resources (currently no edits done here anymore - I decided to remove my changes since I did not feel too comfortable keeping my done changes since i wasnt that familiar with ulimits)
My service (currently using user root to test this - correct me if im wrong, but isnt root able to take all the resources that are available if needed?)
[Unit]
Description=fastreport
[Service]
WorkingDirectory=/var/www/fastreport/
ExecStart=/usr/bin/dotnet /var/www/fastreport/YinaPrintingService.dll
Restart=always
RestartSec=10
SyslogIdentifier=fastreport
User=root
Environment=ASPNETCORE_ENVIRONMENT=Production
Environment=DOTNET_PRINT_TELEMETRY_MESSAGE=false
Environment=ASPNETCORE_URLS=http://localhost:9999;
[Install]
WantedBy=multi-user.target
The error in the journalctl
Sep 07 13:31:44 localhost.localdomain fastreport[5835]: fail: Microsoft.AspNetCore.Server.Kestrel[13]
Sep 07 13:31:44 localhost.localdomain fastreport[5835]: Connection id "0HMBHT8G3SG2D", Request id "0HMBHT8G3SG2D:00000002": An unhandled exception was thrown by the application.
Sep 07 13:31:44 localhost.localdomain fastreport[5835]: System.OutOfMemoryException: Out of memory.
Sep 07 13:31:44 localhost.localdomain fastreport[5835]: at System.Drawing.Graphics.Save()
Sep 07 13:31:44 localhost.localdomain fastreport[5835]: at FastReport.GdiGraphics.Save()
Sep 07 13:31:44 localhost.localdomain fastreport[5835]: at FastReport.TextObject.CalcSize()
Sep 07 13:31:44 localhost.localdomain fastreport[5835]: at FastReport.TextObject.CalcHeight()
Sep 07 13:31:44 localhost.localdomain fastreport[5835]: at FastReport.Table.TableCellData.CalcHeight(Single width)
Sep 07 13:31:44 localhost.localdomain fastreport[5835]: at FastReport.Table.TableBase.CalcHeight()
Sep 07 13:31:44 localhost.localdomain fastreport[5835]: at FastReport.BandBase.CalcHeight()
Sep 07 13:31:44 localhost.localdomain fastreport[5835]: at FastReport.Engine.ReportEngine.PrepareBand(BandBase band, Boolean getData)
Sep 07 13:31:44 localhost.localdomain fastreport[5835]: at FastReport.Engine.ReportEngine.ShowBandToPreparedPages(BandBase band, Boolean getData)
Sep 07 13:31:44 localhost.localdomain fastreport[5835]: at FastReport.Engine.ReportEngine.ShowBand(BandBase band, Boolean getData)
Sep 07 13:31:44 localhost.localdomain fastreport[5835]: at FastReport.Engine.ReportEngine.ShowBand(BandBase band)
Sep 07 13:31:44 localhost.localdomain fastreport[5835]: at FastReport.Engine.ReportEngine.RunDataBand(DataBand dataBand, Int32 rowCount, Boolean keepFirstRow, Boolean keepLastRow)
Sep 07 13:31:44 localhost.localdomain fastreport[5835]: at FastReport.Engine.ReportEngine.RunDataBand(DataBand dataBand)
Sep 07 13:31:44 localhost.localdomain fastreport[5835]: at FastReport.Engine.ReportEngine.RunBands(BandCollection bands)
Sep 07 13:31:44 localhost.localdomain fastreport[5835]: at FastReport.Engine.ReportEngine.RunReportPage(ReportPage page)
Sep 07 13:31:44 localhost.localdomain fastreport[5835]: at FastReport.Engine.ReportEngine.RunReportPages()
Sep 07 13:31:44 localhost.localdomain fastreport[5835]: at FastReport.Engine.ReportEngine.RunReportPages(ReportPage page)
Sep 07 13:31:44 localhost.localdomain fastreport[5835]: at FastReport.Engine.ReportEngine.Run(Boolean runDialogs, Boolean append, Boolean resetDataState, ReportPage page)
Sep 07 13:31:44 localhost.localdomain fastreport[5835]: at FastReport.Engine.ReportEngine.Run(Boolean runDialogs, Boolean append, Boolean resetDataState)
Sep 07 13:31:44 localhost.localdomain fastreport[5835]: at FastReport.Report.Prepare(Boolean append)
Sep 07 13:31:44 localhost.localdomain fastreport[5835]: at YinaPrintingService.Utilities.ProductieLijstTemplateUtility.GetProductieLijstRechts(List`1 dtos) in C:\Users\glenn\Source\Repos\fastreportprinting\YinaPrintingService\Utilities\ProductieLijstTemplateUtility.cs:line 315
Sep 07 13:31:44 localhost.localdomain fastreport[5835]: at YinaPrintingService.Factories.ProductieLijstRechtsFromCodeFactory.GenerateReport(JArray array) in C:\Users\glenn\Source\Repos\fastreportprinting\YinaPrintingService\Factories\ProductieLijstRechtsFromCodeFactory.cs:line 11
Sep 07 13:31:44 localhost.localdomain fastreport[5835]: at YinaPrintingService.Controllers.DocumentController.Index(JArray array, FastReportDocumentTemplate templateName, String printerName, OutputMode outMode) in C:\Users\glenn\Source\Repos\fastreportprinting\YinaPrintingService\Controllers\DocumentController.cs:line 47
Sep 07 13:31:44 localhost.localdomain fastreport[5835]: at lambda_method1(Closure , Object , Object[] )
Sep 07 13:31:44 localhost.localdomain fastreport[5835]: at Microsoft.AspNetCore.Mvc.Infrastructure.ActionMethodExecutor.SyncActionResultExecutor.Execute(IActionResultTypeMapper mapper, ObjectMethodExecutor executor, Object controller, Object[] arguments)
Sep 07 13:31:44 localhost.localdomain fastreport[5835]: at Microsoft.AspNetCore.Mvc.Infrastructure.ControllerActionInvoker.InvokeActionMethodAsync()
Sep 07 13:31:44 localhost.localdomain fastreport[5835]: at Microsoft.AspNetCore.Mvc.Infrastructure.ControllerActionInvoker.Next(State& next, Scope& scope, Object& state, Boolean& isCompleted)
Sep 07 13:31:44 localhost.localdomain fastreport[5835]: at Microsoft.AspNetCore.Mvc.Infrastructure.ControllerActionInvoker.InvokeNextActionFilterAsync()
Sep 07 13:31:44 localhost.localdomain fastreport[5835]: --- End of stack trace from previous location ---
Sep 07 13:31:44 localhost.localdomain fastreport[5835]: at Microsoft.AspNetCore.Mvc.Infrastructure.ControllerActionInvoker.Rethrow(ActionExecutedContextSealed context)
Sep 07 13:31:44 localhost.localdomain fastreport[5835]: at Microsoft.AspNetCore.Mvc.Infrastructure.ControllerActionInvoker.Next(State& next, Scope& scope, Object& state, Boolean& isCompleted)
Sep 07 13:31:44 localhost.localdomain fastreport[5835]: at Microsoft.AspNetCore.Mvc.Infrastructure.ControllerActionInvoker.<InvokeInnerFilterAsync>g__Awaited|13_0(ControllerActionInvoker invoker, Task lastTask, State next, Scope scope, Object state, Boolean isCompleted)
Sep 07 13:31:44 localhost.localdomain fastreport[5835]: at Microsoft.AspNetCore.Mvc.Infrastructure.ResourceInvoker.<InvokeFilterPipelineAsync>g__Awaited|19_0(ResourceInvoker invoker, Task lastTask, State next, Scope scope, Object state, Boolean isCompleted)
Sep 07 13:31:44 localhost.localdomain fastreport[5835]: at Microsoft.AspNetCore.Mvc.Infrastructure.ResourceInvoker.<InvokeAsync>g__Awaited|17_0(ResourceInvoker invoker, Task task, IDisposable scope)
Sep 07 13:31:44 localhost.localdomain fastreport[5835]: at Microsoft.AspNetCore.Routing.EndpointMiddleware.<Invoke>g__AwaitRequestTask|6_0(Endpoint endpoint, Task requestTask, ILogger logger)
Sep 07 13:31:44 localhost.localdomain fastreport[5835]: at FastReport.Web.FastReportMiddleware.Invoke(HttpContext httpContext)
Sep 07 13:31:44 localhost.localdomain fastreport[5835]: at Microsoft.AspNetCore.Authorization.AuthorizationMiddleware.Invoke(HttpContext context)
Sep 07 13:31:44 localhost.localdomain fastreport[5835]: at Micr
Other info:
[root@localhost fastreport]# lscpu
Architecture: x86_64
CPU op-mode(s): 32-bit, 64-bit
Byte Order: Little Endian
CPU(s): 4
On-line CPU(s) list: 0-3
Thread(s) per core: 2
Core(s) per socket: 2
Socket(s): 1
NUMA node(s): 1
Vendor ID: GenuineIntel
BIOS Vendor ID: None
CPU family: 6
Model: 85
Model name: Intel(R) Xeon(R) Silver 4208 CPU @ 2.10GHz
BIOS Model name: None
Stepping: 7
CPU MHz: 2095.079
BogoMIPS: 4190.15
Hypervisor vendor: Microsoft
Virtualization type: full
L1d cache: 32K
L1i cache: 32K
L2 cache: 1024K
L3 cache: 11264K
NUMA node0 CPU(s): 0-3
Flags: fpu vme de pse tsc msr pae mce cx8 apic sep mtrr pge mca cmov pat pse36 clflush mmx fxsr sse sse2 ss ht syscall nx pdpe1gb rdtscp lm constant_tsc rep_good nopl xtopology cpuid pni pclmulqdq ssse3 fma cx16 pcid sse4_1 sse4_2 movbe popcnt aes xsave avx f16c rdrand hypervisor lahf_lm abm 3dnowprefetch invpcid_single ssbd ibrs ibpb stibp ibrs_enhanced fsgsbase bmi1 hle avx2 smep bmi2 erms invpcid mpx avx512f avx512dq rdseed adx smap clflushopt clwb avx512cd avx512bw avx512vl xsaveopt xsavec xgetbv1 xsaves avx512_vnni md_clear flush_l1d arch_capabilities
[root@localhost fastreport]# free -m
total used free shared buff/cache available
Mem: 15401 1466 13469 16 465 13650
Swap: 16055 0 16055
[root@localhost fastreport]# uname -a
Linux localhost.localdomain 4.18.0-338.el8.x86_64 #1 SMP Fri Aug 27 17:32:14 UTC 2021 x86_64 x86_64 x86_64 GNU/Linux
OutOfMemoryException
s are often caused by heap fragmentation, not by really running out of memory.System.Drawing
. You really should not use these APIs in a server application, much less on .NET Core. It could be leaking handles, too, leading to a different kind of resource exhaustion. However, that’s better suited for Stack Overflow.