Skip to content

Commit

Permalink
feat: Support for the SYSCLOCK system variable
Browse files Browse the repository at this point in the history
  • Loading branch information
slavek-kucera authored Dec 19, 2022
1 parent be0169c commit 6116699
Show file tree
Hide file tree
Showing 12 changed files with 368 additions and 55 deletions.
1 change: 1 addition & 0 deletions clients/vscode-hlasmplugin/CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@
- Quick fixes for typos in instruction and macro names added to the code actions
- Endevor and CICS preprocessor statements highlighting and parsing
- Instruction suggestions are included in the completion list
- Support for the SYSCLOCK system variable

#### Fixed
- LSP requests on virtual files are evaluated in the correct workspace context
Expand Down
30 changes: 8 additions & 22 deletions language_server/src/logger.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -12,36 +12,22 @@
* Broadcom, Inc. - initial API and implementation
*/

#include "logger.h"

#include <cstdlib>
#define __STDC_WANT_LIB_EXT1__ 1
#include <iostream>
#include <time.h>
#include <string>

#include "logger.h"
#include "utils/time.h"

using namespace hlasm_plugin::language_server;

std::string current_time()
{
std::string curr_time;
// Current date/time based on current time
time_t now = time(0);
// Convert current time to string

#if __STDC_LIB_EXT1__ || _MSVC_LANG
char cstr[50];
ctime_s(cstr, sizeof cstr, &now);
curr_time.assign(cstr);
#else
curr_time.assign(ctime(&now));
#endif

// Last charactor of currentTime is "\n", so remove it
if (!curr_time.empty())
curr_time.pop_back();

return curr_time;
auto t = hlasm_plugin::utils::timestamp::now();
if (!t.has_value())
return "<unknown time>";
else
return t->to_string();
}

void logger::log(std::string_view data)
Expand Down
53 changes: 27 additions & 26 deletions parser_library/src/context/hlasm_context.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,7 @@
#include "lexing/lexer.h"
#include "lexing/tools.h"
#include "using.h"
#include "utils/time.h"

namespace hlasm_plugin::parser_library::context {

Expand Down Expand Up @@ -129,7 +130,7 @@ macro_data_ptr create_macro_data(std::vector<std::string> value)

macro_data_ptr create_macro_data(std::unique_ptr<macro_param_data_single_dynamic> value) { return value; }

template<typename SYSTEM_VARIABLE_TYPE, typename DATA>
template<typename SYSTEM_VARIABLE_TYPE = system_variable, typename DATA>
std::pair<id_index, sys_sym_ptr> create_system_variable(id_index id, DATA mac_data, bool is_global)
{
return { id, std::make_shared<SYSTEM_VARIABLE_TYPE>(id, create_macro_data(std::move(mac_data)), is_global) };
Expand All @@ -143,15 +144,13 @@ void hlasm_context::add_system_vars_to_scope(code_scope& scope)
{
auto sect_name = ord_ctx.current_section() ? ord_ctx.current_section()->name : id_index();

scope.system_variables.insert(
create_system_variable<system_variable, std::string>(id_index("SYSECT"), sect_name.to_string(), false));
scope.system_variables.insert(create_system_variable(id_index("SYSECT"), sect_name.to_string(), false));
}

{
std::string value = left_pad(std::to_string(SYSNDX_), 4, '0');

scope.system_variables.insert(
create_system_variable<system_variable>(id_index("SYSNDX"), std::move(value), false));
scope.system_variables.insert(create_system_variable(id_index("SYSNDX"), std::move(value), false));
}

{
Expand All @@ -178,8 +177,7 @@ void hlasm_context::add_system_vars_to_scope(code_scope& scope)
}
}

scope.system_variables.insert(
create_system_variable<system_variable>(id_index("SYSSTYP"), std::move(value), false));
scope.system_variables.insert(create_system_variable(id_index("SYSSTYP"), std::move(value), false));
}

{
Expand All @@ -191,14 +189,13 @@ void hlasm_context::add_system_vars_to_scope(code_scope& scope)
}

scope.system_variables.insert(
create_system_variable<system_variable>(id_index("SYSLOC"), std::move(location_counter_name), false));
create_system_variable(id_index("SYSLOC"), std::move(location_counter_name), false));
}

{
std::string value = std::to_string(scope_stack_.size() - 1);

scope.system_variables.insert(
create_system_variable<system_variable>(id_index("SYSNEST"), std::move(value), false));
scope.system_variables.insert(create_system_variable(id_index("SYSNEST"), std::move(value), false));
}

{
Expand All @@ -217,13 +214,18 @@ void hlasm_context::add_system_vars_to_scope(code_scope& scope)
}

{
scope.system_variables.insert(
create_system_variable<system_variable>(id_index("SYSIN_DSN"), asm_options_.sysin_dsn, false));
scope.system_variables.insert(create_system_variable(id_index("SYSIN_DSN"), asm_options_.sysin_dsn, false));
}

{
scope.system_variables.insert(
create_system_variable<system_variable>(id_index("SYSIN_MEMBER"), asm_options_.sysin_member, false));
create_system_variable(id_index("SYSIN_MEMBER"), asm_options_.sysin_member, false));
}

{
scope.system_variables.insert(create_system_variable(id_index("SYSCLOCK"),
utils::timestamp::now().value_or(utils::timestamp(1900, 1, 1)).to_string(),
false));
}
}
}
Expand All @@ -242,36 +244,35 @@ void hlasm_context::add_global_system_vars(code_scope& scope)
if (!is_in_macro())
{
{
auto tmp_now = std::time(0);
auto now = std::localtime(&tmp_now);
auto now = utils::timestamp::now().value_or(utils::timestamp(1900, 1, 1));

std::string datc_val;
std::string date_val;
datc_val.reserve(8);
date_val.reserve(8);
auto year = std::to_string(now->tm_year + 1900);
auto year = std::to_string(now.year());
datc_val.append(year);

if (now->tm_mon + 1 < 10)
if (now.month() < 10)
{
datc_val.push_back('0');
date_val.push_back('0');
}

datc_val.append(std::to_string(now->tm_mon + 1));
datc_val.append(std::to_string(now.month() + 1));

date_val.append(std::to_string(now->tm_mon + 1));
date_val.append(std::to_string(now.month() + 1));
date_val.push_back('/');

if (now->tm_mday < 10)
if (now.day() < 10)
{
datc_val.push_back('0');
date_val.push_back('0');
}

datc_val.append(std::to_string(now->tm_mday));
datc_val.append(std::to_string(now.day()));

date_val.append(std::to_string(now->tm_mday));
date_val.append(std::to_string(now.day()));
date_val.push_back('/');
date_val.append(year.c_str() + 2);

Expand All @@ -287,13 +288,13 @@ void hlasm_context::add_global_system_vars(code_scope& scope)

{
std::string value;
if (now->tm_hour < 10)
if (now.hour() < 10)
value.push_back('0');
value.append(std::to_string(now->tm_hour));
value.append(std::to_string(now.hour()));
value.push_back(':');
if (now->tm_min < 10)
if (now.minute() < 10)
value.push_back('0');
value.append(std::to_string(now->tm_min));
value.append(std::to_string(now.minute()));

globals_.insert(create_system_variable<system_variable>(id_index("SYSTIME"), std::move(value), true));
}
Expand Down
10 changes: 3 additions & 7 deletions parser_library/src/processing/instruction_sets/ca_processor.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@
#include "expressions/conditional_assembly/terms/ca_symbol.h"
#include "semantics/operand_impls.h"
#include "semantics/range_provider.h"
#include "utils/time.h"

using namespace hlasm_plugin::parser_library;
using namespace processing;
Expand Down Expand Up @@ -582,14 +583,9 @@ void ca_processor::process_AREAD(const semantics::complete_statement& stmt)
constexpr const auto since_midnight = []() -> std::chrono::nanoseconds {
using namespace std::chrono;

const auto now = system_clock::now();
const auto now = utils::timestamp::now().value_or(utils::timestamp());

const auto now_t = system_clock::to_time_t(now);
const auto tm = *std::localtime(&now_t);

const auto subsecond = now - std::chrono::floor<std::chrono::seconds>(now);

return hours(tm.tm_hour) + minutes(tm.tm_min) + seconds(tm.tm_sec) + subsecond;
return hours(now.hour()) + minutes(now.minute()) + seconds(now.second()) + microseconds(now.microsecond());
};

std::string value_to_set;
Expand Down
50 changes: 50 additions & 0 deletions parser_library/test/context/system_variable_test.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,8 @@
* Broadcom, Inc. - initial API and implementation
*/

#include <regex>

#include "gtest/gtest.h"

#include "../common_testing.h"
Expand Down Expand Up @@ -450,3 +452,51 @@ TEST(system_variable, mnote_sys_variables)
EXPECT_EQ(get_var_vector<C_t>(a.hlasm_ctx(), "RES"), expected_res);
EXPECT_EQ(get_var_vector<C_t>(a.hlasm_ctx(), "HRES"), expected_hres);
}

TEST(system_variable, sysclock)
{
std::string input = R"(
MACRO
MAC2
GBLC &VAL3
&VAL3 SETC '&SYSCLOCK'
MEND
*
MACRO
MAC
GBLC &VAR,&VAL1,&VAL2
&T1 SETC T'&SYSCLOCK
&K1 SETA K'&SYSCLOCK
&VAR SETC '&T1 &K1'
&VAL1 SETC '&SYSCLOCK'
&I SETA 1000
.LOOP ANOP ,
&I SETA &I-1
AIF (&I GT 0).LOOP
MAC2
&VAL2 SETC '&SYSCLOCK'
MEND
*
GBLC &VAR,&VAL1,&VAL2,&VAL3
MAC
END
)";

analyzer a(input);
a.analyze();
a.collect_diags();
EXPECT_TRUE(a.diags().empty());

EXPECT_EQ(get_var_value<C_t>(a.hlasm_ctx(), "VAR"), "U 26");

auto val1 = get_var_value<C_t>(a.hlasm_ctx(), "VAL1");
auto val2 = get_var_value<C_t>(a.hlasm_ctx(), "VAL2");
auto val3 = get_var_value<C_t>(a.hlasm_ctx(), "VAL3");

ASSERT_TRUE(val1 && val2 && val3);

EXPECT_EQ(val1, val2);
EXPECT_NE(val1, val3);

EXPECT_TRUE(std::regex_match(val1.value(), std::regex(R"(\d\d\d\d-\d\d-\d\d \d\d:\d\d:\d\d\.\d\d\d\d\d\d)")));
}
2 changes: 2 additions & 0 deletions parser_library/test/debugging/debugger_test.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -260,6 +260,7 @@ struct frame_vars_ignore_sys_vars : public frame_vars
this->locals["&SYSMAC"];
this->locals["&SYSIN_DSN"];
this->locals["&SYSIN_MEMBER"];
this->locals["&SYSCLOCK"];
}
};

Expand Down Expand Up @@ -516,6 +517,7 @@ TEST(debugger, test)
{ "&SYSIN_DSN", "" },
{ "&SYSIN_MEMBER", "" },
{ "&VAR", "13" },
{ "&SYSCLOCK", test_var_value() },
},
{} // empty ord symbols
));
Expand Down
1 change: 1 addition & 0 deletions utils/include/utils/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@ target_sources(hlasm_utils PUBLIC
resource_location.h
similar.h
string_operations.h
time.h
truth_table.h
unicode_text.h
)
Loading

0 comments on commit 6116699

Please sign in to comment.