Skip to content

Commit bee69b1

Browse files
authored
Merge pull request #137 from mssonicbld/sonicbld/202205-merge
[code sync] Merge code from sonic-net/sonic-buildimage:202205 to 202205
2 parents d7278e4 + ef2294f commit bee69b1

File tree

9 files changed

+152
-69
lines changed

9 files changed

+152
-69
lines changed

files/build_templates/snmp.service.j2

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@ StartLimitIntervalSec=1200
1010
StartLimitBurst=3
1111

1212
[Service]
13+
ExecStartPre=/bin/bash -c 'end=$((SECONDS+20));while [ $SECONDS -lt $end ];do if /usr/bin/pgrep intfmgrd >/dev/null;then break;else sleep 1;fi;done'
1314
ExecStartPre=/usr/local/bin/{{docker_container_name}}.sh start
1415
ExecStart=/usr/local/bin/{{docker_container_name}}.sh wait
1516
ExecStop=/usr/local/bin/{{docker_container_name}}.sh stop

src/sonic-sairedis

src/tacacs/bash_tacplus/bash_tacplus.c

Lines changed: 35 additions & 35 deletions
Original file line numberDiff line numberDiff line change
@@ -14,8 +14,8 @@
1414
/* Remote user gecos prefix, which been assigned by nss_tacplus */
1515
#define REMOTE_USER_GECOS_PREFIX "remote_user"
1616

17-
/* Default value for _SC_GETPW_R_SIZE_MAX */
18-
#define DEFAULT_SC_GETPW_R_SIZE_MAX 1024
17+
/* Default value for getpwent */
18+
#define DEFAULT_GETPWENT_SIZE_MAX 4096
1919

2020
/* Return value for is_local_user method */
2121
#define IS_LOCAL_USER 0
@@ -31,6 +31,7 @@
3131
/* Output syslog to mock method when build with UT */
3232
#if defined (BASH_PLUGIN_UT)
3333
#define syslog mock_syslog
34+
#define getpwent_r mock_getpwent_r
3435
#endif
3536

3637
/* Tacacs+ log format */
@@ -42,7 +43,7 @@
4243
/* Tacacs+ config file timestamp string length */
4344
#define CONFIG_FILE_TIME_STAMP_LEN 100
4445

45-
/*
46+
/*
4647
Convert log to a string because va args resoursive issue:
4748
http://www.c-faq.com/varargs/handoff.html
4849
*/
@@ -199,7 +200,7 @@ int tacacs_authorization(
199200
continue;
200201
}
201202

202-
// increase connected servers
203+
// increase connected servers
203204
connected_servers++;
204205
result = send_authorization_message(server_fd, user, tty, host, task_id, cmd, args, argc);
205206
close(server_fd);
@@ -279,15 +280,15 @@ void load_tacacs_config()
279280
}
280281

281282
output_debug("TACACS+ control flag: 0x%x\n", tacacs_ctrl);
282-
283+
283284
if (tacacs_ctrl & AUTHORIZATION_FLAG_TACACS) {
284285
output_debug("TACACS+ per-command authorization enabled.\n");
285286
}
286287

287288
if (tacacs_ctrl & AUTHORIZATION_FLAG_LOCAL) {
288289
output_debug("Local per-command authorization enabled.\n");
289290
}
290-
291+
291292
if (tacacs_ctrl & PAM_TAC_DEBUG) {
292293
output_debug("TACACS+ debug enabled.\n");
293294
}
@@ -350,40 +351,39 @@ int is_local_user(char *user)
350351
}
351352

352353
struct passwd pwd;
353-
struct passwd *pwdresult;
354-
char *buf;
355-
size_t bufsize = sysconf(_SC_GETPW_R_SIZE_MAX);
356-
if (bufsize == -1) {
357-
bufsize = DEFAULT_SC_GETPW_R_SIZE_MAX;
358-
}
354+
struct passwd *ppwd;
355+
char buf[DEFAULT_GETPWENT_SIZE_MAX];
356+
int pwdresult;
357+
int result = ERROR_CHECK_LOCAL_USER;
358+
setpwent();
359+
while (1) {
360+
pwdresult = getpwent_r(&pwd, buf, sizeof(buf), &ppwd);
361+
if (pwdresult) {
362+
// no more pw entry
363+
break;
364+
}
359365

360-
buf = malloc(bufsize);
361-
if (buf == NULL) {
362-
output_error("failed to allocate getpwnam_r buffer.\n");
363-
return ERROR_CHECK_LOCAL_USER;
364-
}
366+
if (strcmp(ppwd->pw_name, user) != 0) {
367+
continue;
368+
}
365369

366-
int s = getpwnam_r(user, &pwd, buf, bufsize, &pwdresult);
367-
int result = IS_LOCAL_USER;
368-
if (pwdresult == NULL) {
369-
if (s == 0)
370-
output_error("get user information user failed, user: %s not found\n", user);
370+
// compare passwd entry, for remote user pw_gecos will start as 'remote_user'
371+
if (strncmp(ppwd->pw_gecos, REMOTE_USER_GECOS_PREFIX, strlen(REMOTE_USER_GECOS_PREFIX)) == 0) {
372+
output_debug("user: %s, UID: %d, GECOS: %s is remote user.\n", user, ppwd->pw_uid, ppwd->pw_gecos);
373+
result = IS_REMOTE_USER;
374+
}
371375
else {
372-
output_error("get user information failed, user: %s, errorno: %d\n", user, s);
376+
output_debug("user: %s, UID: %d, GECOS: %s is local user.\n", user, ppwd->pw_uid, ppwd->pw_gecos);
377+
result = IS_LOCAL_USER;
373378
}
374-
375-
result = ERROR_CHECK_LOCAL_USER;
376-
}
377-
else if (strncmp(pwd.pw_gecos, REMOTE_USER_GECOS_PREFIX, strlen(REMOTE_USER_GECOS_PREFIX)) == 0) {
378-
output_debug("user: %s, UID: %d, GECOS: %s is remote user.\n", user, pwd.pw_uid, pwd.pw_gecos);
379-
result = IS_REMOTE_USER;
379+
break;
380380
}
381-
else {
382-
output_debug("user: %s, UID: %d, GECOS: %s is local user.\n", user, pwd.pw_uid, pwd.pw_gecos);
383-
result = IS_LOCAL_USER;
381+
endpwent();
382+
383+
if (result == ERROR_CHECK_LOCAL_USER) {
384+
output_error("get user information user failed, user: %s not found\n", user);
384385
}
385386

386-
free(buf);
387387
return result;
388388
}
389389

@@ -482,7 +482,7 @@ int on_shell_execve (char *user, int shell_level, char *cmd, char **argv)
482482
}
483483
}
484484

485-
// return 0, so bash will continue run user command and will check user permission with linux permission check.
485+
// return 0, so bash will continue run user command and will check user permission with linux permission check.
486486
output_debug("start local authorization for command %s with given arguments\n", cmd);
487487
return 0;
488-
}
488+
}

src/tacacs/bash_tacplus/unittest/mock_helper.c

Lines changed: 41 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@
33
#include <stdio.h>
44
#include <stdlib.h>
55
#include <string.h>
6+
#include <pwd.h>
67
#include <CUnit/CUnit.h>
78
#include <CUnit/Basic.h>
89

@@ -65,13 +66,13 @@ void initialize_tacacs_servers()
6566
getaddrinfo(buffer, "49", &hints, &servers);
6667
tac_srv[idx].addr = &(tac_srv_addr[idx]);
6768
memcpy(tac_srv[idx].addr, servers, sizeof(struct addrinfo));
68-
69+
6970
tac_srv[idx].addr->ai_addr = &(tac_sock_addr[idx]);
7071
memcpy(tac_srv[idx].addr->ai_addr, servers->ai_addr, sizeof(struct sockaddr));
71-
72+
7273
snprintf(tac_srv[idx].key, sizeof(tac_srv[idx].key), "key%d", idx);
7374
freeaddrinfo(servers);
74-
75+
7576
debug_printf("MOCK: initialize_tacacs_servers with index: %d, address: %p\n", idx, tac_srv[idx].addr);
7677
}
7778
}
@@ -119,7 +120,7 @@ void tac_free_attrib(struct tac_attrib **attr)
119120
{
120121
memory_allocate_count--;
121122
debug_printf("MOCK: tac_free_attrib memory count: %d\n", memory_allocate_count);
122-
123+
123124
// the mock code here only free first allocated memory, because the mock tac_add_attrib implementation not allocate new memory.
124125
free(*attr);
125126
}
@@ -133,7 +134,7 @@ int tac_author_send(int tac_fd, const char *user, char *tty, char *host,struct t
133134
// send auth message failed
134135
return -1;
135136
}
136-
137+
137138
return 0;
138139
}
139140

@@ -146,7 +147,7 @@ int tac_author_read(int tac_fd, struct areply *reply)
146147
{
147148
return -1;
148149
}
149-
150+
150151
if (TEST_SCEANRIO_CONNECTION_SEND_DENINED_RESULT == test_scenario)
151152
{
152153
reply->status = AUTHOR_STATUS_FAIL;
@@ -155,15 +156,15 @@ int tac_author_read(int tac_fd, struct areply *reply)
155156
{
156157
reply->status = AUTHOR_STATUS_PASS_REPL;
157158
}
158-
159+
159160
return 0;
160161
}
161162

162163
/* Mock tac_connect_single method */
163164
int tac_connect_single(const struct addrinfo *address, const char *key, struct addrinfo *source_address, int timeout, char *vrfname)
164165
{
165166
debug_printf("MOCK: tac_connect_single with address: %p\n", address);
166-
167+
167168
switch (test_scenario)
168169
{
169170
case TEST_SCEANRIO_CONNECTION_ALL_FAILED:
@@ -183,7 +184,7 @@ char *tac_ntop(const struct sockaddr *address)
183184
return tac_natop_result_buffer;
184185
}
185186
}
186-
187+
187188
return "UnknownTestAddress";
188189
}
189190

@@ -198,12 +199,41 @@ void mock_syslog(int priority, const char *format, ...)
198199
{
199200
// set mock message data to buffer for UT.
200201
memset(mock_syslog_message_buffer, 0, sizeof(mock_syslog_message_buffer));
201-
202+
202203
va_list args;
203204
va_start (args, format);
204205
// save message to buffer to UT check later
205206
vsnprintf(mock_syslog_message_buffer, sizeof(mock_syslog_message_buffer), format, args);
206207
va_end (args);
207-
208+
208209
debug_printf("MOCK: syslog: %s\n", mock_syslog_message_buffer);
210+
}
211+
212+
int mock_getpwent_r(struct passwd *restrict pwbuf,
213+
char *buf, size_t buflen,
214+
struct passwd **restrict pwbufp)
215+
{
216+
static char* test_user = "test_user";
217+
static char* root_user = "root";
218+
static char* empty_gecos = "";
219+
static char* remote_gecos = "remote_user";
220+
*pwbufp = pwbuf;
221+
switch (test_scenario)
222+
{
223+
case TEST_SCEANRIO_CONNECTION_SEND_SUCCESS_RESULT:
224+
case TEST_SCEANRIO_CONNECTION_SEND_DENINED_RESULT:
225+
case TEST_SCEANRIO_IS_LOCAL_USER_REMOTE:
226+
pwbuf->pw_name = test_user;
227+
pwbuf->pw_gecos = remote_gecos;
228+
pwbuf->pw_uid = 1000;
229+
return 0;
230+
case TEST_SCEANRIO_IS_LOCAL_USER_ROOT:
231+
pwbuf->pw_name = root_user;
232+
pwbuf->pw_gecos = empty_gecos;
233+
pwbuf->pw_uid = 0;
234+
return 0;
235+
case TEST_SCEANRIO_IS_LOCAL_USER_NOT_FOUND:
236+
return 1;
237+
}
238+
return 1;
209239
}

src/tacacs/bash_tacplus/unittest/mock_helper.h

Lines changed: 10 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -24,11 +24,16 @@
2424
/* Mock syslog buffer */
2525
extern char mock_syslog_message_buffer[1024];
2626

27-
#define TEST_SCEANRIO_CONNECTION_ALL_FAILED 1
28-
#define TEST_SCEANRIO_CONNECTION_SEND_FAILED_RESULT 2
29-
#define TEST_SCEANRIO_CONNECTION_SEND_SUCCESS_READ_FAILED 3
30-
#define TEST_SCEANRIO_CONNECTION_SEND_DENINED_RESULT 4
31-
#define TEST_SCEANRIO_CONNECTION_SEND_SUCCESS_RESULT 5
27+
#define TEST_SCEANRIO_CONNECTION_ALL_FAILED 1
28+
#define TEST_SCEANRIO_CONNECTION_SEND_FAILED_RESULT 2
29+
#define TEST_SCEANRIO_CONNECTION_SEND_SUCCESS_READ_FAILED 3
30+
#define TEST_SCEANRIO_CONNECTION_SEND_DENINED_RESULT 4
31+
#define TEST_SCEANRIO_CONNECTION_SEND_SUCCESS_RESULT 5
32+
#define TEST_SCEANRIO_LOAD_CHANGED_TACACS_CONFIG 6
33+
#define TEST_SCEANRIO_IS_LOCAL_USER_UNKNOWN 7
34+
#define TEST_SCEANRIO_IS_LOCAL_USER_NOT_FOUND 8
35+
#define TEST_SCEANRIO_IS_LOCAL_USER_ROOT 9
36+
#define TEST_SCEANRIO_IS_LOCAL_USER_REMOTE 10
3237

3338
/* Set test scenario for test*/
3439
void set_test_scenario(int scenario);

0 commit comments

Comments
 (0)