mono / mono.posix

POSIX/Unix interface for Mono, .NET and .NET Core. Provides functionality for managed code to access POSIX/Unix features not accessible via the BCL. This repository supersedes the older code in https://github.com/mono/mono
MIT License
42 stars 10 forks source link

Missing LARGE_FILE_SOURCE on 32-bit Arm #49

Open kenkendk opened 3 months ago

kenkendk commented 3 months ago

Simple Program.cs:

var p = "bigfile.bin";
if (File.Exists(p))
    File.Delete(p);

// Larger than 4GiB to trigger 32-bit overflow
using (var s = new FileStream(p, FileMode.Create, FileAccess.Write, FileShare.None))
    s.SetLength(1024 * 1024 * 1024 * 5L);

var fi = new FileInfo(p);
Console.WriteLine(fi.Length);

// Fails without large file support, works with it
var ret = Mono.Unix.Native.Syscall.lstat(p, out var stat);
if (ret != 0)
    throw new Exception($"lstat failed: {ret}");

Console.WriteLine(stat.st_size);

And the test.csproj file:

<Project Sdk="Microsoft.NET.Sdk">

  <PropertyGroup>
    <OutputType>Exe</OutputType>
    <TargetFramework>net8.0</TargetFramework>
  </PropertyGroup>

  <ItemGroup>
    <PackageReference Include="Mono.Unix" Version="7.1.0-final.1.21458.1" />
  </ItemGroup>

</Project>

Running this program on 32-bit Linux gives:

> ./test
5368709120
Unhandled exception. System.Exception: lstat failed: -1
   at Program.<Main>$(String[] args) in /test/Program.cs:line 15
Aborted

The cause is overflow in the file size because it has not been compiled with -DLARGE_FILE_SOURCE=1.

I have a "kind-of" fix here: https://github.com/mono/mono.posix/commit/424ee24b5e1a1e5c1de74f415eafc70890952e30

This should add the required directives to the compiler, but when I build with the latest Ubuntu, these options are enabled by default. I am not sure what system the NuGet packages were built with, but I think an OS update would fix it. I can make a PR with my changes, but they may not be needed.

Running with my own build gives this output:

5368709120
5368709120