https://llvm.org/bugs/show_bug.cgi?id=26605
Bug ID: 26605 Summary: FreeBSD projects/clang380-import for TARGET_ARCH=powerpc : clang 3.8.0 sometimes mishandles va_list overflow_arg_area vs. reg_save_area Product: clang Version: 3.8 Hardware: Other OS: FreeBSD Status: NEW Severity: normal Priority: P Component: C++ Assignee: unassignedclangb...@nondot.org Reporter: mar...@dsl-only.net CC: dgre...@apple.com, llvm-bugs@lists.llvm.org Classification: Unclassified In a projects/clang380-import context libxo code use by "ls -l -n /" gets a segmentation violation (SEGV) for TARGET_ARCH=powerpc for buildworld/installworld. The later simplified code reproduces the problem. The issue is complicated alignment/placement handling of va_list content between overflow_arg_area and reg_save_area that can happen when things larger than 4 bytes in size are involved in the mix, such as intmax_t. It can be that only 4 bytes are left in reg_save_area when the next things is, say, 8 bytes in size. The next thing after that can be 4 bytes in size --which place does the 4 byte item go and which is it extracted from? The code generated is not consistent with itself. The following short program demonstrates the problem. #include <stdarg.h> // for va_list, va_start, va_arg, va_end #include <stdint.h> // for intmax_t intmax_t va_test (char *s, ...) { va_list vap; va_start(vap, s); char* t0 = va_arg(vap, char*); unsigned int o0 = va_arg(vap, unsigned int); int c0 = va_arg(vap, int); unsigned int u0 = va_arg(vap, unsigned int); int c1 = va_arg(vap, int); char * t1 = va_arg(vap, char*); intmax_t j0 = va_arg(vap, intmax_t); // This spans into overflow_arg_area. int c2 = va_arg(vap, int); // A copy was put in the // overflow_arg_area because of the // above. // But this tries to extract from the // last 4 bytes of the reg_save_area. // It does not increment the // overflow_arg_area position pointer // past the copy that is there. char * t2 = va_arg(vap, char*); // The lack of increment before makes // this extraction off by 4 bytes. char t2fc = *t2; // <<< This gets SEGV. t2 actually got what should be // the c2 value. intmax_t j1 = va_arg(vap, intmax_t); va_end(vap); return (intmax_t) ((s-t2)+(t0-t1)+o0+u0+j0+j1+c0+c1+c2+t2fc); // Avoid any optimize-away for lack of use. } int main(void) { char s[1025] = "test string for this"; char* t0 = s + 5; unsigned int o0 = 3; int c0 = 1; unsigned int u0 = 1; int c1 = 3; char * t1 = s + 12; intmax_t j0 = 314159265358979323; int c2 = 4; char * t2 = s + 16; intmax_t j1 = ~314159265358979323; intmax_t result = va_test(s,t0,o0,c0,u0,c1,t1,j0,c1,t2,j1); return (int) (result - (intmax_t) ((s-t2)+(t0-t1)+o0+u0+j0+j1+c0+c1+c2+*t2)); // Avoid any optimize-away for lack of use. } Context: # freebsd-version -ku; uname -aKU 11.0-CURRENT 11.0-CURRENT FreeBSD FBSDG4C1 11.0-CURRENT FreeBSD 11.0-CURRENT #3 r295351M: Sat Feb 6 16:27:58 PST 2016 markmi@FreeBSDx64:/usr/obj/clang_gcc421/powerpc.powerpc/usr/src/sys/GENERICvtsc-NODEBUG powerpc 1100097 1100097 -- You are receiving this mail because: You are on the CC list for the bug.
_______________________________________________ llvm-bugs mailing list llvm-bugs@lists.llvm.org http://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-bugs