dosutils: add Novell-style REVOKE and REMOVE trustee tools
Implement REVOKE and REMOVE for the Client32 DOS utilities. REVOKE now supports Novell-style syntax: REVOKE rightslist* [FOR path] FROM [USER|GROUP] name [options] and removes rights from explicit trustee assignments. It scans the trustee list first, updates the trustee rights mask, and deletes the trustee entry when no rights remain. REMOVE now supports Novell-style syntax: REMOVE [USER | GROUP] name [FROM path] [option] and deletes explicit trustee assignments for users or groups. Both tools support USER/GROUP lookup, /FILES, /SUBDIRS, /SUBDIRECTORIES, wildcard file targets, recursive directory handling, Novell-style help text and summary output. Missing trustee entries are reported with Novell-style "No trustee for the specified ..." messages. Add shared trustee helpers and Client32 NCP87 trustee scan/delete support. Also adjust GRANT ALL so it matches Novell behavior by not granting Supervisor implicitly; Supervisor must be granted explicitly.
This commit is contained in:
182
c32ncp.c
182
c32ncp.c
@@ -37,6 +37,14 @@ static uint32 c32_get_dword_lh(uint8 *p)
|
||||
((uint32)p[3] << 24));
|
||||
}
|
||||
|
||||
static uint32 c32_get_dword_hl(uint8 *p)
|
||||
{
|
||||
return(((uint32)p[0] << 24) |
|
||||
((uint32)p[1] << 16) |
|
||||
((uint32)p[2] << 8) |
|
||||
(uint32)p[3]);
|
||||
}
|
||||
|
||||
static UI c32_build_handle_path(uint8 *buf, uint8 dhandle,
|
||||
uint16 dirbase, uint8 style,
|
||||
int count,
|
||||
@@ -593,3 +601,177 @@ int c32_ncp87_add_trustee_rights(const char *path_name,
|
||||
return(0);
|
||||
}
|
||||
|
||||
|
||||
|
||||
int c32_ncp87_find_trustee_rights(const char *path_name,
|
||||
uint16 dir_handle,
|
||||
uint32 object_id,
|
||||
uint16 *rights_out,
|
||||
uint16 *actual_out,
|
||||
uint16 *handle_lo_out,
|
||||
uint16 *handle_hi_out)
|
||||
{
|
||||
uint16 handle_lo, handle_hi;
|
||||
uint8 hdr[16];
|
||||
uint8 path[0x140];
|
||||
uint8 rep0[0x120];
|
||||
uint8 rep1[0x120];
|
||||
uint8 rawout[32];
|
||||
uint16 raw_ret_ax, raw_ret_dx;
|
||||
uint16 actual_lo;
|
||||
uint32 seq = 0;
|
||||
UI path_len;
|
||||
int rc;
|
||||
|
||||
if (rights_out) *rights_out = 0;
|
||||
if (actual_out) *actual_out = 0;
|
||||
if (handle_lo_out) *handle_lo_out = 0;
|
||||
if (handle_hi_out) *handle_hi_out = 0;
|
||||
|
||||
if (!rights_out)
|
||||
return(1);
|
||||
|
||||
rc = c32_get_ncp_handle(&handle_lo, &handle_hi);
|
||||
if (rc)
|
||||
return(10 + rc);
|
||||
|
||||
for (;;) {
|
||||
uint16 count;
|
||||
uint16 i;
|
||||
uint8 *tp;
|
||||
uint32 next_seq;
|
||||
|
||||
memset(hdr, 0, sizeof(hdr));
|
||||
hdr[0] = 5; /* NCP87 subfunction 5: scan trustees */
|
||||
hdr[1] = 0; /* DOS namespace */
|
||||
hdr[2] = 0; /* reserved */
|
||||
c32_put_word_lh(hdr + 3, 0x8006); /* SA_ALL: files/subdirs + system + hidden */
|
||||
c32_put_dword_lh(hdr + 5, seq); /* search sequence, starts at zero */
|
||||
|
||||
path_len = c32_build_handle_path_from_dos_path(path,
|
||||
(uint8)dir_handle,
|
||||
0, 0,
|
||||
path_name);
|
||||
|
||||
memset(rep0, 0, sizeof(rep0));
|
||||
memset(rep1, 0, sizeof(rep1));
|
||||
memset(rawout, 0, sizeof(rawout));
|
||||
|
||||
C32_NCP87_Raw5_Probe(handle_lo, handle_hi,
|
||||
hdr, 9,
|
||||
path, path_len,
|
||||
rep0, sizeof(rep0),
|
||||
rep1, sizeof(rep1),
|
||||
rawout);
|
||||
|
||||
raw_ret_ax = c32_get_word_lh(rawout + 14);
|
||||
raw_ret_dx = c32_get_word_lh(rawout + 16);
|
||||
actual_lo = c32_get_word_lh(rawout + 18);
|
||||
|
||||
if (actual_out) *actual_out = actual_lo;
|
||||
if (handle_lo_out) *handle_lo_out = handle_lo;
|
||||
if (handle_hi_out) *handle_hi_out = handle_hi;
|
||||
|
||||
if (raw_ret_ax != 0 || raw_ret_dx != 0)
|
||||
return(0xff); /* Client32 returns an error when no trustees are present. */
|
||||
|
||||
next_seq = c32_get_dword_lh(rep0 + 0);
|
||||
count = c32_get_word_lh(rep0 + 4);
|
||||
|
||||
if (count > 20)
|
||||
count = 20;
|
||||
|
||||
tp = rep0 + 6;
|
||||
for (i = 0; i < count; i++) {
|
||||
uint32 tid = c32_get_dword_hl(tp);
|
||||
uint16 trights = c32_get_word_lh(tp + 4);
|
||||
|
||||
if (tid == object_id || c32_get_dword_lh(tp) == object_id) {
|
||||
*rights_out = trights;
|
||||
return(0);
|
||||
}
|
||||
|
||||
tp += 6;
|
||||
}
|
||||
|
||||
if (next_seq == 0xffffffffUL || next_seq == seq)
|
||||
break;
|
||||
|
||||
seq = next_seq;
|
||||
}
|
||||
|
||||
return(0xff); /* no trustee found / no more entries */
|
||||
}
|
||||
|
||||
int c32_ncp87_delete_trustee_rights(const char *path_name,
|
||||
uint16 dir_handle,
|
||||
uint32 object_id,
|
||||
uint16 *actual_out,
|
||||
uint16 *handle_lo_out,
|
||||
uint16 *handle_hi_out)
|
||||
{
|
||||
uint16 handle_lo, handle_hi;
|
||||
uint8 hdr[16];
|
||||
uint8 reqpath[0x180];
|
||||
uint8 rep0[0x20];
|
||||
uint8 rep1[0x20];
|
||||
uint8 rawout[32];
|
||||
uint16 raw_ret_ax, raw_ret_dx;
|
||||
uint16 actual_lo;
|
||||
UI path_struct_len;
|
||||
UI reqpath_len;
|
||||
uint8 *tp;
|
||||
int rc;
|
||||
|
||||
if (actual_out) *actual_out = 0;
|
||||
if (handle_lo_out) *handle_lo_out = 0;
|
||||
if (handle_hi_out) *handle_hi_out = 0;
|
||||
|
||||
rc = c32_get_ncp_handle(&handle_lo, &handle_hi);
|
||||
if (rc)
|
||||
return(10 + rc);
|
||||
|
||||
memset(hdr, 0, sizeof(hdr));
|
||||
hdr[0] = 11; /* NCP87 subfunction 11: delete trustee */
|
||||
hdr[1] = 0; /* DOS namespace */
|
||||
hdr[2] = 0; /* reserved */
|
||||
c32_put_word_lh(hdr + 3, 1); /* one trustee */
|
||||
|
||||
memset(reqpath, 0, sizeof(reqpath));
|
||||
path_struct_len = c32_build_handle_path_from_dos_path(reqpath,
|
||||
(uint8)dir_handle,
|
||||
0, 0,
|
||||
path_name);
|
||||
|
||||
if (path_struct_len > 307)
|
||||
return(2);
|
||||
|
||||
tp = reqpath + 307;
|
||||
c32_put_dword_hl(tp, object_id); tp += 4;
|
||||
c32_put_word_lh(tp, 0); tp += 2;
|
||||
reqpath_len = (UI)(tp - reqpath);
|
||||
|
||||
memset(rep0, 0, sizeof(rep0));
|
||||
memset(rep1, 0, sizeof(rep1));
|
||||
memset(rawout, 0, sizeof(rawout));
|
||||
|
||||
C32_NCP87_Raw5_Probe(handle_lo, handle_hi,
|
||||
hdr, 5,
|
||||
reqpath, reqpath_len,
|
||||
rep0, sizeof(rep0),
|
||||
rep1, sizeof(rep1),
|
||||
rawout);
|
||||
|
||||
raw_ret_ax = c32_get_word_lh(rawout + 14);
|
||||
raw_ret_dx = c32_get_word_lh(rawout + 16);
|
||||
actual_lo = c32_get_word_lh(rawout + 18);
|
||||
|
||||
if (actual_out) *actual_out = actual_lo;
|
||||
if (handle_lo_out) *handle_lo_out = handle_lo;
|
||||
if (handle_hi_out) *handle_hi_out = handle_hi;
|
||||
|
||||
if (raw_ret_ax != 0 || raw_ret_dx != 0)
|
||||
return(20);
|
||||
|
||||
return(0);
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user