1%% 2%% %CopyrightBegin% 3%% 4%% Copyright Ericsson AB 2014-2020. All Rights Reserved. 5%% 6%% Licensed under the Apache License, Version 2.0 (the "License"); 7%% you may not use this file except in compliance with the License. 8%% You may obtain a copy of the License at 9%% 10%% http://www.apache.org/licenses/LICENSE-2.0 11%% 12%% Unless required by applicable law or agreed to in writing, software 13%% distributed under the License is distributed on an "AS IS" BASIS, 14%% WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 15%% See the License for the specific language governing permissions and 16%% limitations under the License. 17%% 18%% %CopyrightEnd% 19%% 20%% %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% 21%% This test suite uses the following external programs: 22%% snmpget From packet 'snmp' (in Ubuntu 12.04) 23%% snmpd From packet 'snmpd' (in Ubuntu 12.04) 24%% snmptrapd From packet 'snmpd' (in Ubuntu 12.04) 25%% They originate from the Net-SNMP applications, see: 26%% http://net-snmp.sourceforge.net/ 27 28 29-module(snmp_to_snmpnet_SUITE). 30 31-export([ 32 suite/0, all/0, groups/0, 33 init_per_suite/1, end_per_suite/1, 34 init_per_group/2, end_per_group/2, 35 init_per_testcase/2, end_per_testcase/2, 36 37 erlang_agent_netsnmp_get/0, erlang_agent_netsnmp_get/1, 38 erlang_agent_netsnmp_inform/0, erlang_agent_netsnmp_inform/1, 39 erlang_manager_netsnmp_get/0, erlang_manager_netsnmp_get/1 40 41 ]). 42 43-include("snmp_test_lib.hrl"). 44-include_lib("common_test/include/ct.hrl"). 45-include_lib("snmp/include/STANDARD-MIB.hrl"). 46 47-define(AGENT_ENGINE_ID, "ErlangSnmpAgent"). 48-define(MANAGER_ENGINE_ID, "ErlangSnmpManager"). 49-define(AGENT_PORT, 4000). 50-define(MANAGER_PORT, 8989). 51-define(DEFAULT_MAX_MESSAGE_SIZE, 484). 52 53expected(?sysDescr_instance = Oid, get) -> 54 OidStr = oid_str(Oid), 55 iolist_to_binary([OidStr | " = STRING: \"Erlang SNMP agent\""]). 56 57 58%%-------------------------------------------------------------------- 59%% Common Test interface functions ----------------------------------- 60%%-------------------------------------------------------------------- 61 62suite() -> [{ct_hooks,[ts_install_cth]}]. 63 64all() -> 65 [ 66 {group, ipv4}, 67 {group, ipv6}, 68 {group, ipv4_ipv6} 69 ]. 70 71groups() -> 72 [ 73 {ipv4, [], ipv4_cases()}, 74 {ipv6, [], ipv6_cases()}, 75 {ipv4_ipv6, [], ipv4_ipv6_cases()}, 76 77 {snmpget, [], snmpget_cases()}, 78 {snmptrapd, [], snmptrapd_cases()}, 79 {snmpd_mt, [], snmpd_mt_cases()}, 80 {snmpd, [], snmpd_cases()} 81 ]. 82 83ipv4_cases() -> 84 [ 85 {group, snmpget}, 86 {group, snmptrapd}, 87 {group, snmpd_mt}, 88 {group, snmpd} 89 ]. 90 91ipv6_cases() -> 92 [ 93 {group, snmpget}, 94 {group, snmptrapd}, 95 {group, snmpd_mt}, 96 {group, snmpd} 97 ]. 98 99ipv4_ipv6_cases() -> 100 [ 101 {group, snmpget}, 102 {group, snmptrapd}, 103 {group, snmpd_mt}, 104 {group, snmpd} 105 ]. 106 107snmpget_cases() -> 108 [ 109 erlang_agent_netsnmp_get 110 ]. 111 112snmptrapd_cases() -> 113 [ 114 erlang_agent_netsnmp_inform 115 ]. 116 117snmpd_mt_cases() -> 118 [ 119 erlang_manager_netsnmp_get 120 ]. 121 122snmpd_cases() -> 123 [ 124 erlang_manager_netsnmp_get 125 ]. 126 127 128 129%% 130%% ----- 131%% 132 133init_per_suite(Config0) -> 134 ?IPRINT("init_per_suite -> entry with" 135 "~n Config: ~p", [Config0]), 136 137 case netsnmp_init(Config0) of 138 {skip, _} = SKIP -> 139 SKIP; 140 141 Config1 -> 142 case ?LIB:init_per_suite(Config1) of 143 {skip, _} = SKIP -> 144 SKIP; 145 146 Config2 when is_list(Config2) -> 147 snmp_test_sys_monitor:start(), 148 149 ?IPRINT("init_per_suite -> end when" 150 "~n Config: ~p", [Config2]), 151 152 Config2 153 end 154 end. 155 156netsnmp_init(Config) -> 157 case has_netsnmp() of 158 true -> 159 case proper_netsnmp_version() of 160 true -> 161 [{agent_port, ?AGENT_PORT}, 162 {manager_port, ?MANAGER_PORT} | Config]; 163 false -> 164 {skip, "Buggy NetSNMP"} 165 end; 166 false -> 167 {skip, "No NetSNMP"} 168 end. 169 170has_netsnmp() -> 171 netsnmp_check("NET-SNMP"). 172 173proper_netsnmp_version() -> 174 not netsnmp_check("5.4|5.6.2.1"). 175 176netsnmp_check(RE) -> 177 case re:run(os:cmd("snmpd -v"), RE, [{capture, first}]) of 178 nomatch -> 179 false; 180 {match, _} -> 181 true 182 end. 183 184 185end_per_suite(Config) -> 186 ?IPRINT("end_per_suite -> entry with" 187 "~n Config: ~p", [Config]), 188 189 snmp_test_sys_monitor:stop(), 190 ?LIB:end_per_suite(Config), 191 192 ?IPRINT("end_per_suite -> end"), 193 194 Config. 195 196%% 197%% ----- 198%% 199 200init_per_group(ipv4, Config) -> 201 init_per_group_ip([inet], Config); 202init_per_group(ipv6, Config) -> 203 case os:type() of 204 {unix, netbsd} -> 205 {skip, "Host *may* not *properly* support IPV6"}; 206 _ -> 207 init_per_group_ipv6([inet6], Config) 208 end; 209init_per_group(ipv4_ipv6, Config) -> 210 case os:type() of 211 {unix, netbsd} -> 212 {skip, "Host *may* not *properly* support IPV6"}; 213 _ -> 214 init_per_group_ipv6([inet, inet6], Config) 215 end; 216init_per_group(snmpget = Exec, Config) -> 217 %% From Ubuntu package snmp 218 init_per_group_agent(Exec, Config); 219init_per_group(snmptrapd = Exec, Config) -> 220 %% From Ubuntu package snmpd 221 init_per_group_agent(Exec, Config); 222init_per_group(snmpd_mt, Config) -> 223 %% From Ubuntu package snmp 224 init_per_group_manager( 225 snmpd, 226 [{manager_net_if_module, snmpm_net_if_mt} | Config]); 227init_per_group(snmpd = Exec, Config) -> 228 %% From Ubuntu package snmp 229 init_per_group_manager( 230 Exec, 231 [{manager_net_if_module, snmpm_net_if} | Config]); 232 233init_per_group(_, Config) -> 234 Config. 235 236init_per_group_ipv6(Families, Config) -> 237 case ?HAS_SUPPORT_IPV6() of 238 true -> 239 init_per_group_ip(Families, Config); 240 false -> 241 {skip, "Host does not support IPv6"} 242 end. 243 244init_per_group_ip(Families, Config) -> 245 AgentPort = ?config(agent_port, Config), 246 ManagerPort = ?config(manager_port, Config), 247 Transports = 248 [begin 249 Addr = ?LIB:localhost(Family), 250 {domain(Family), {Addr, AgentPort}} 251 end || Family <- Families], 252 Targets = 253 [begin 254 Addr = ?LIB:localhost(Family), 255 {domain(Family), {Addr, ManagerPort}} 256 end || Family <- Families], 257 [{transports, Transports}, {targets, Targets} | Config]. 258 259init_per_group_agent(Exec, Config) -> 260 Versions = [v2], 261 Dir = ?config(priv_dir, Config), 262 Transports = ?config(transports, Config), 263 Targets = ?config(targets, Config), 264 agent_config(Dir, Transports, Targets, Versions), 265 find_executable(Exec, [{snmp_versions, Versions} | Config]). 266 267init_per_group_manager(Exec, Config) -> 268 Versions = [v2], 269 Dir = ?config(priv_dir, Config), 270 Targets = ?config(targets, Config), 271 manager_config(Dir, Targets), 272 find_executable(Exec, [{snmp_versions, Versions} | Config]). 273 274 275end_per_group(_GroupName, Config) -> 276 Config. 277 278 279 280%% 281%% ----- 282%% 283 284init_per_testcase(_Case, Config) -> 285 ?IPRINT("init_per_testcase -> entry with" 286 "~n Config: ~p", [Config]), 287 288 snmp_test_global_sys_monitor:reset_events(), 289 290 Dog = ct:timetrap(?SECS(20)), 291 application:stop(snmp), 292 application:unload(snmp), 293 Config1 = [{watchdog, Dog} | Config], 294 295 ?IPRINT("init_per_testcase -> done when" 296 "~n Config: ~p", [Config1]), 297 298 Config1. 299 300end_per_testcase(_, Config) -> 301 302 ?IPRINT("end_per_testcase -> entry with" 303 "~n Config: ~p", [Config]), 304 305 ?IPRINT("system events during test: " 306 "~n ~p", [snmp_test_global_sys_monitor:events()]), 307 308 case application:stop(snmp) of 309 ok -> 310 ok; 311 E1 -> 312 ct:pal("application:stop(snmp) -> ~p", [E1]) 313 end, 314 case application:unload(snmp) of 315 ok -> 316 ok; 317 E2 -> 318 ct:pal("application:unload(snmp) -> ~p", [E2]) 319 end, 320 321 ?IPRINT("end_per_testcase -> done with" 322 "~n Config: ~p", [Config]), 323 324 Config. 325 326find_executable(Exec, Config) -> 327 ExecStr = atom_to_list(Exec), 328 case os:find_executable(ExecStr) of 329 false -> 330 %% The sbin dirs are not in the PATH on all platforms... 331 find_sys_executable( 332 Exec, ExecStr, 333 [["usr", "local", "sbin"], 334 ["usr", "sbin"], 335 ["sbin"]], 336 Config); 337 Path -> 338 [{Exec, Path} | Config] 339 end. 340 341find_sys_executable(_Exec, ExecStr, [], _Config) -> 342 {skip, ExecStr ++ " not found"}; 343find_sys_executable(Exec, ExecStr, [Dir | Dirs], Config) -> 344 case os:find_executable(filename:join(["/" | Dir] ++ [ExecStr])) of 345 false -> 346 find_sys_executable(Exec, ExecStr, Dirs, Config); 347 Path -> 348 [{Exec, Path} | Config] 349 end. 350 351start_agent(Config) -> 352 ok = application:load(snmp), 353 ok = application:set_env(snmp, agent, agent_app_env(Config)), 354 ok = application:start(snmp). 355 356%% stop_agent(_Config) -> 357%% case application:stop(snmp) of 358%% ok -> 359%% ok; 360%% E1 -> 361%% ct:pal("application:stop(snmp) -> ~p", [E1]) 362%% end, 363%% case application:unload(snmp) of 364%% ok -> 365%% ok; 366%% E2 -> 367%% ct:pal("application:unload(snmp) -> ~p", [E2]) 368%% end. 369 370start_manager(Config) -> 371 ok = application:load(snmp), 372 ok = application:set_env(snmp, manager, manager_app_env(Config)), 373 ok = application:start(snmp). 374 375%% stop_manager(_Config) -> 376%% case application:stop(snmp) of 377%% ok -> 378%% ok; 379%% E1 -> 380%% ct:pal("application:stop(snmp) -> ~p", [E1]) 381%% end, 382%% case application:unload(snmp) of 383%% ok -> 384%% ok; 385%% E2 -> 386%% ct:pal("application:unload(snmp) -> ~p", [E2]) 387%% end. 388 389 390 391%%-------------------------------------------------------------------- 392%% Test Cases -------------------------------------------------------- 393%%-------------------------------------------------------------------- 394erlang_agent_netsnmp_get() -> 395 [{doc,"Test that we can access erlang snmp agent " 396 "from snmpnet manager"}]. 397 398erlang_agent_netsnmp_get(Config) when is_list(Config) -> 399 Transports = ?config(transports, Config), 400 start_agent(Config), 401 Oid = ?sysDescr_instance, 402 Expected = expected(Oid, get), 403 try 404 begin 405 [Expected = snmpget(Oid, Transport, Config) 406 || Transport <- Transports], 407 ok 408 end 409 catch 410 throw:{skip, _} = SKIP -> 411 SKIP 412 end. 413 414 415%%-------------------------------------------------------------------- 416erlang_manager_netsnmp_get() -> 417 [{doc,"Test that the erlang snmp manager can access snmpnet agent"}]. 418 419erlang_manager_netsnmp_get(Config) when is_list(Config) -> 420 Community = "happy-testing", 421 SysDescr = "Net-SNMP agent", 422 TargetName = "Target Net-SNMP agent", 423 Transports = ?config(transports, Config), 424 case start_snmpd(Community, SysDescr, Config) of 425 {skip, _} = SKIP -> 426 SKIP; 427 ProgHandle -> 428 start_manager(Config), 429 snmp_manager_user:start_link(self(), test_user), 430 [snmp_manager_user:register_agent( 431 TargetName++domain_suffix(Domain), 432 [{reg_type, target_name}, 433 {tdomain, Domain}, {taddress, Addr}, 434 {community, Community}, {engine_id, "EngineId"}, 435 {version, v2}, {sec_model, v2c}, {sec_level, noAuthNoPriv}]) 436 || {Domain, Addr} <- Transports], 437 Results = 438 [snmp_manager_user:sync_get2( 439 TargetName++domain_suffix(Domain), 440 [?sysDescr_instance], []) 441 || {Domain, _} <- Transports], 442 ct:pal("sync_get -> ~p", [Results]), 443 snmp_manager_user:stop(), 444 stop_program(ProgHandle), 445 [{ok, 446 {noError, 0, 447 [{varbind, ?sysDescr_instance, 'OCTET STRING', SysDescr,1}] }, 448 _} = R || R <- Results], 449 ok 450 end. 451 452 453%%-------------------------------------------------------------------- 454erlang_agent_netsnmp_inform() -> 455 [{doc, "TBD"}]. 456 457erlang_agent_netsnmp_inform(Config) when is_list(Config) -> 458 DataDir = ?config(data_dir, Config), 459 Mib = "TestTrapv2", 460 461 start_agent(Config), 462 ok = snmpa:load_mib(snmp_master_agent, filename:join(DataDir, Mib)), 463 464 case start_snmptrapd(Mib, Config) of 465 {skip, _} = SKIP -> 466 SKIP; 467 ProgHandle -> 468 snmpa:send_notification( 469 snmp_master_agent, testTrapv22, {erlang_agent_test, self()}), 470 receive 471 {snmp_targets, erlang_agent_test, Addresses} -> 472 ct:pal("Notification sent to: ~p~n", [Addresses]), 473 erlang_agent_netsnmp_inform_responses(Addresses) 474 end, 475 stop_program(ProgHandle) 476 end. 477 478erlang_agent_netsnmp_inform_responses([]) -> 479 receive 480 {snmp_notification, erlang_agent_test, _} = Unexpected -> 481 ct:pal("Unexpected response: ~p", [Unexpected]), 482 erlang_agent_netsnmp_inform_responses([]) 483 after 0 -> 484 ok 485 end; 486erlang_agent_netsnmp_inform_responses([Address | Addresses]) -> 487 receive 488 {snmp_notification, erlang_agent_test, 489 {got_response, Address}} -> 490 ct:pal("Got response from: ~p~n", [Address]), 491 erlang_agent_netsnmp_inform_responses(Addresses); 492 {snmp_notification, erlang_agent_test, 493 {no_response, _} = NoResponse} -> 494 ct:fail(NoResponse) 495 end. 496 497%%-------------------------------------------------------------------- 498%% Internal functions ------------------------------------------------ 499%%-------------------------------------------------------------------- 500 501snmpget(Oid, Transport, Config) -> 502 Versions = ?config(snmp_versions, Config), 503 504 Args = 505 ["-c", "public", net_snmp_version(Versions), 506 "-m", ":", 507 "-Cf", 508 net_snmp_addr_str(Transport), 509 oid_str(Oid)], 510 case start_program(snmpget, Args, none, Config) of 511 {skip, _} = SKIP -> 512 throw(SKIP); 513 ProgHandle -> 514 {_, line, Line} = get_program_output(ProgHandle), 515 stop_program(ProgHandle), 516 Line 517 end. 518 519start_snmptrapd(Mibs, Config) -> 520 DataDir = ?config(data_dir, Config), 521 MibDir = filename:join(code:lib_dir(snmp), "mibs"), 522 Targets = ?config(targets, Config), 523 SnmptrapdArgs = 524 ["-f", "-Lo", "-C", 525 "-m", Mibs, 526 "-M", MibDir++":"++DataDir, 527 "--disableAuthorization=yes", 528 "--snmpTrapdAddr=" ++ net_snmp_addr_str(Targets)], 529 {ok, StartCheckMP} = re:compile("NET-SNMP version ", [anchored]), 530 start_program(snmptrapd, SnmptrapdArgs, StartCheckMP, Config). 531 532start_snmpd(Community, SysDescr, Config) -> 533 DataDir = ?config(data_dir, Config), 534 Targets = ?config(targets, Config), 535 Transports = ?config(transports, Config), 536 Port = mk_port_number(), 537 CommunityArgs = 538 ["--rocommunity"++domain_suffix(Domain)++"=" 539 ++Community++" "++inet_parse:ntoa(Ip) 540 || {Domain, {Ip, _}} <- Targets], 541 542 SnmpdArgs = 543 ["-f", "-r", %"-Dverbose", 544 "-c", filename:join(DataDir, "snmpd.conf"), 545 "-C", 546 "-Lo", 547 "-m", ":", 548 "--sysDescr="++SysDescr, 549 "--agentXSocket=tcp:localhost:"++integer_to_list(Port)] 550 ++ CommunityArgs 551 ++ [net_snmp_addr_str(Transports)], 552 {ok, StartCheckMP} = re:compile("NET-SNMP version ", [anchored]), 553 start_program(snmpd, SnmpdArgs, StartCheckMP, Config). 554 555start_program(Prog, Args, StartCheckMP, Config) -> 556 ct:pal("Starting program: ~w ~p", [Prog, Args]), 557 Path = ?config(Prog, Config), 558 DataDir = ?config(data_dir, Config), 559 StartWrapper = filename:join(DataDir, "start_stop_wrapper"), 560 Parent = self(), 561 %% process_flag(trap_exit, true), 562 {Pid, Mon} = 563 spawn_monitor( 564 fun () -> 565 run_program(Parent, StartWrapper, [Path | Args]) 566 end), 567 start_check(Pid, Mon, StartCheckMP). 568 569start_check(Pid, Mon, none) -> 570 {Pid, Mon}; 571start_check(Pid, Mon, StartCheckMP) -> 572 receive 573 {Pid, line, Line} -> 574 case re:run(Line, StartCheckMP, [{capture, none}]) of 575 match -> 576 {Pid, Mon}; 577 nomatch -> 578 start_check(Pid, Mon, StartCheckMP) 579 end; 580 {'DOWN', Mon, _, _Pid, {skip, Reason} = SKIP} -> 581 ct:pal("Received DOWN from ~p" 582 "~n Skip Reason: ~p", [_Pid, Reason]), 583 SKIP; 584 {'DOWN', Mon, _, _, Reason} -> 585 ct:fail("Prog ~p start failed: ~p", [Pid, Reason]) 586 end. 587 588get_program_output({Pid, Mon}) -> 589 receive 590 {Pid, _, _} = Msg -> 591 Msg; 592 {'DOWN', Mon, _, _, Reason} -> 593 ct:fail("Prog ~p crashed: ~p", [Pid, Reason]) 594 end. 595 596stop_program({Pid, _} = Handle) -> 597 Pid ! {self(), stop}, 598 wait_program_stop(Handle). 599 600wait_program_stop({Pid, Mon}) -> 601 receive 602 {Pid, exit, ExitStatus} -> 603 receive 604 {'DOWN', Mon, _, _, _} -> 605 ExitStatus 606 end; 607 {'DOWN', Mon, _, _, Reason} -> 608 ct:fail("Prog stop: ~p", [Reason]) 609 end. 610 611run_program(Parent, StartWrapper, ProgAndArgs) -> 612 [Prog | _] = ProgAndArgs, 613 Port = 614 open_port( 615 {spawn_executable, StartWrapper}, 616 [{args, ProgAndArgs}, binary, stderr_to_stdout, {line, 80}, 617 exit_status]), 618 ct:pal("Prog ~p started: ~p", [Port, Prog]), 619 run_program_loop(Parent, Port, []). 620 621run_program_loop(Parent, Port, Buf) -> 622 receive 623 {Parent, stop} -> 624 true = port_command(Port, <<"stop\n">>), 625 ct:pal("Prog ~p stop", [Port]), 626 run_program_loop(Parent, Port, Buf); 627 {Port, {data, {Flag, Data}}} -> 628 case Flag of 629 eol -> 630 Line = iolist_to_binary(lists:reverse(Buf, Data)), 631 ct:pal("Prog ~p output: ~s", [Port, Line]), 632 %% There are potentially many different fail outputs, 633 %% but for now we test for just this one: illegal option 634 IOpt = "illegal option", 635 case string:find(binary_to_list(Line), IOpt) of 636 nomatch -> 637 Parent ! {self(), line, Line}, 638 run_program_loop(Parent, Port, []); 639 Line2 -> 640 %% Try to extract the actual illegal option string 641 IOpt2 = 642 case string:take( 643 string:prefix(Line2, IOpt), [$-, $ ]) of 644 {_, Str} when length(Str) > 0 -> 645 Str; 646 _X -> 647 Line2 648 end, 649 ct:pal("Force program ~p stop", [Port]), 650 true = port_command(Port, <<"stop\n">>), 651 (catch port_close(Port)), 652 exit({skip, {illegal_option, IOpt2}}) 653 end; 654 noeol -> 655 run_program_loop(Parent, Port, [Data | Buf]) 656 end; 657 {Port, {exit_status, ExitStatus}} -> 658 ct:pal("Prog ~p exit: ~p", [Port, ExitStatus]), 659 catch port_close(Port), 660 Parent ! {self(), exit, ExitStatus}; 661 Unexpected -> 662 ct:pal("run_program_loop Unexpected: ~p", [Unexpected]), 663 run_program_loop(Parent, Port, Buf) 664 end. 665 666 667agent_app_env(Config) -> 668 Dir = ?config(priv_dir, Config), 669 Vsns = ?config(snmp_versions, Config), 670 [{versions, Vsns}, 671 {agent_type, master}, 672 {agent_verbosity, trace}, 673 {db_dir, Dir}, 674 {audit_trail_log, [{type, read_write}, 675 {dir, Dir}, 676 {size, {10240, 10}}]}, 677 {config, [{dir, Dir}, 678 {force_load, true}, 679 {verbosity, trace}]}, 680 {local_db, [{repair, true}, 681 {verbosity, silence}]}, 682 {mib_server, [{verbosity, silence}]}, 683 {symbolic_store, [{verbosity, silence}]}, 684 {note_store, [{verbosity, silence}]}, 685 {net_if, [{verbosity, trace}]}]. 686 687manager_app_env(Config) -> 688 Dir = ?config(priv_dir, Config), 689 Vsns = ?config(snmp_versions, Config), 690 NetIfModule = ?config(manager_net_if_module, Config), 691 [{versions, Vsns}, 692 {audit_trail_log, [{type, read_write}, 693 {dir, Dir}, 694 {size, {10240, 10}}]}, 695 {net_if, [{module, NetIfModule}]}, 696 {config, [{dir, Dir}, 697 {db_dir, Dir}, 698 {verbosity, trace}]} 699 ]. 700 701oid_str([1 | Ints]) -> 702 "iso." ++ oid_str_tl(Ints); 703oid_str(Ints) -> 704 oid_str_tl(Ints). 705 706oid_str_tl([]) -> 707 ""; 708oid_str_tl([Int]) -> 709 integer_to_list(Int); 710oid_str_tl([Int | Ints]) -> 711 integer_to_list(Int) ++ "." ++ oid_str_tl(Ints). 712 713agent_config(Dir, Transports, Targets, Versions) -> 714 EngineID = ?AGENT_ENGINE_ID, 715 MMS = ?DEFAULT_MAX_MESSAGE_SIZE, 716 ok = snmp_config:write_agent_snmp_conf(Dir, Transports, EngineID, MMS), 717 ok = snmp_config:write_agent_snmp_context_conf(Dir), 718 ok = snmp_config:write_agent_snmp_community_conf(Dir), 719 ok = 720 snmp_config:write_agent_snmp_standard_conf( 721 Dir, "snmp_to_snmpnet_SUITE"), 722 ok = 723 snmp_config:write_agent_snmp_target_addr_conf( 724 Dir, Targets, Versions), 725 ok = snmp_config:write_agent_snmp_target_params_conf(Dir, Versions), 726 ok = snmp_config:write_agent_snmp_notify_conf(Dir, inform), 727 ok = snmp_config:write_agent_snmp_vacm_conf(Dir, Versions, none). 728 729manager_config(Dir, Targets) -> 730 EngineID = ?MANAGER_ENGINE_ID, 731 MMS = ?DEFAULT_MAX_MESSAGE_SIZE, 732 ok = snmp_config:write_manager_snmp_conf(Dir, Targets, MMS, EngineID). 733 734net_snmp_version([v3 | _]) -> 735 "-v3"; 736net_snmp_version([v2 | _]) -> 737 "-v2c"; 738net_snmp_version([v1 | _]) -> 739 "-v1". 740 741domain(inet) -> 742 transportDomainUdpIpv4; 743domain(inet6) -> 744 transportDomainUdpIpv6. 745 746net_snmp_addr_str([Target | Targets]) -> 747 net_snmp_addr_str(Target) ++ 748 case Targets of 749 [] -> 750 []; 751 [_ | _] -> 752 "," ++ net_snmp_addr_str(Targets) 753 end; 754net_snmp_addr_str({transportDomainUdpIpv4, {Addr, Port}}) -> 755 "udp:" ++ 756 inet_parse:ntoa(Addr) ++ ":" ++ 757 integer_to_list(Port); 758net_snmp_addr_str({transportDomainUdpIpv6, {Addr, Port}}) -> 759 "udp6:[" ++ 760 inet_parse:ntoa(Addr) ++ "]:" ++ 761 integer_to_list(Port). 762 763domain_suffix(transportDomainUdpIpv4) -> 764 ""; 765domain_suffix(transportDomainUdpIpv6) -> 766 "6". 767 768mk_port_number() -> 769 {ok, Socket} = gen_udp:open(0, [{reuseaddr, true}]), 770 {ok, PortNum} = inet:port(Socket), 771 ok = gen_udp:close(Socket), 772 PortNum. 773 774