diff --git a/flang/include/flang/Runtime/extensions.h b/flang/include/flang/Runtime/extensions.h index b34edb94ada43..d8ddd8069e202 100644 --- a/flang/include/flang/Runtime/extensions.h +++ b/flang/include/flang/Runtime/extensions.h @@ -33,7 +33,7 @@ void FORTRAN_PROCEDURE_NAME(getarg)( std::int32_t &n, std::int8_t *arg, std::int64_t length); // GNU extension subroutine GETLOG(C). -void FORTRAN_PROCEDURE_NAME(getlog)(std::byte *name, std::int64_t length); +void FORTRAN_PROCEDURE_NAME(getlog)(char *name, std::int64_t length); } // extern "C" #endif // FORTRAN_RUNTIME_EXTENSIONS_H_ diff --git a/flang/runtime/extensions.cpp b/flang/runtime/extensions.cpp index 352da8f11d9d5..1b3ccc6c298ab 100644 --- a/flang/runtime/extensions.cpp +++ b/flang/runtime/extensions.cpp @@ -15,6 +15,7 @@ #include "flang/Runtime/command.h" #include "flang/Runtime/descriptor.h" #include "flang/Runtime/io-api.h" +#include "flang/Runtime/memory.h" #include #ifdef _WIN32 @@ -47,8 +48,7 @@ extern "C" { namespace Fortran::runtime { -void GetUsernameEnvVar( - const char *envName, std::byte *arg, std::int64_t length) { +void GetUsernameEnvVar(const char *envName, char *arg, std::int64_t length) { Descriptor name{*Descriptor::Create( 1, std::strlen(envName) + 1, const_cast(envName), 0)}; Descriptor value{*Descriptor::Create(1, length, arg, 0)}; @@ -98,7 +98,7 @@ void FORTRAN_PROCEDURE_NAME(getarg)( } // CALL GETLOG(USRNAME) -void FORTRAN_PROCEDURE_NAME(getlog)(std::byte *arg, std::int64_t length) { +void FORTRAN_PROCEDURE_NAME(getlog)(char *arg, std::int64_t length) { #if _REENTRANT || _POSIX_C_SOURCE >= 199506L int nameMaxLen; #ifdef LOGIN_NAME_MAX @@ -108,17 +108,19 @@ void FORTRAN_PROCEDURE_NAME(getlog)(std::byte *arg, std::int64_t length) { if (nameMaxLen == -1) nameMaxLen = _POSIX_LOGIN_NAME_MAX + 1; #endif - std::vector str(nameMaxLen); + Terminator terminator{__FILE__, __LINE__}; + char *str{static_cast(AllocateMemoryOrCrash(terminator, nameMaxLen))}; + str[nameMaxLen] = '\0'; - int error{getlogin_r(str.data(), nameMaxLen)}; + int error{getlogin_r(str, nameMaxLen)}; if (error == 0) { // no error: find first \0 in string then pad from there - CopyAndPad(reinterpret_cast(arg), str.data(), length, - std::strlen(str.data())); + CopyAndPad(arg, str, length, std::strlen(str)); } else { // error occur: get username from environment variable GetUsernameEnvVar("LOGNAME", arg, length); } + FreeMemory((void *)str); #elif _WIN32 // Get username from environment to avoid link to Advapi32.lib GetUsernameEnvVar("USERNAME", arg, length); diff --git a/flang/unittests/Runtime/CommandTest.cpp b/flang/unittests/Runtime/CommandTest.cpp index a0f14c519412a..c0c0b21556e82 100644 --- a/flang/unittests/Runtime/CommandTest.cpp +++ b/flang/unittests/Runtime/CommandTest.cpp @@ -9,10 +9,12 @@ #include "flang/Runtime/command.h" #include "gmock/gmock.h" #include "gtest/gtest.h" +#include "../../runtime/terminator.h" #include "flang/Runtime/descriptor.h" #include "flang/Runtime/execute.h" #include "flang/Runtime/extensions.h" #include "flang/Runtime/main.h" +#include "flang/Runtime/memory.h" #include #include @@ -682,8 +684,7 @@ TEST_F(EnvironmentVariables, GetlogGetName) { const int charLen{3}; char input[charLen]{"\0\0"}; - FORTRAN_PROCEDURE_NAME(getlog) - (reinterpret_cast(input), charLen); + FORTRAN_PROCEDURE_NAME(getlog)(input, charLen); EXPECT_NE(input[0], '\0'); } @@ -699,12 +700,13 @@ TEST_F(EnvironmentVariables, GetlogPadSpace) { if (charLen == -1) charLen = _POSIX_LOGIN_NAME_MAX + 2; #endif - std::vector input(charLen); + Terminator terminator{__FILE__, __LINE__}; + char *input{(char *)AllocateMemoryOrCrash(terminator, charLen)}; - FORTRAN_PROCEDURE_NAME(getlog) - (reinterpret_cast(input.data()), charLen); + FORTRAN_PROCEDURE_NAME(getlog)(input, charLen); EXPECT_EQ(input[charLen - 1], ' '); + FreeMemory((void *)input); } #endif @@ -715,8 +717,7 @@ TEST_F(EnvironmentVariables, GetlogEnvGetName) { << "Environment variable USERNAME does not exist"; char input[]{"XXXXXXXXX"}; - FORTRAN_PROCEDURE_NAME(getlog) - (reinterpret_cast(input), sizeof(input)); + FORTRAN_PROCEDURE_NAME(getlog)(input, sizeof(input)); CheckCharEqStr(input, "loginName"); } @@ -728,8 +729,7 @@ TEST_F(EnvironmentVariables, GetlogEnvBufferShort) { << "Environment variable USERNAME does not exist"; char input[]{"XXXXXX"}; - FORTRAN_PROCEDURE_NAME(getlog) - (reinterpret_cast(input), sizeof(input)); + FORTRAN_PROCEDURE_NAME(getlog)(input, sizeof(input)); CheckCharEqStr(input, "loginN"); } @@ -741,8 +741,7 @@ TEST_F(EnvironmentVariables, GetlogEnvPadSpace) { << "Environment variable USERNAME does not exist"; char input[]{"XXXXXXXXXX"}; - FORTRAN_PROCEDURE_NAME(getlog) - (reinterpret_cast(input), sizeof(input)); + FORTRAN_PROCEDURE_NAME(getlog)(input, sizeof(input)); CheckCharEqStr(input, "loginName "); }