The branch, master has been updated via df96f18... testprogs/win32: add prepare_dcpromo tool from efe65cd... s4/dsdb-test: fix usage comment
http://gitweb.samba.org/?p=samba.git;a=shortlog;h=master - Log ----------------------------------------------------------------- commit df96f18e8ff3400d1bb7e9743498936ad32ee005 Author: Stefan Metzmacher <me...@samba.org> Date: Mon May 31 10:02:38 2010 +0200 testprogs/win32: add prepare_dcpromo tool This tool can set the DOMAIN-SID and nextRid counter in the local SAM on windows servers (tested with w2k8r2) dcpromo will use this values for the ad domain it creates. This might be useful for upgrades from a Samba3 domain. metze ----------------------------------------------------------------------- Summary of changes: testprogs/win32/prepare_dcpromo/GNUmakefile | 21 + testprogs/win32/prepare_dcpromo/NMakefile | 16 + testprogs/win32/prepare_dcpromo/prepare_dcpromo.c | 1074 +++++++++++++++++++++ 3 files changed, 1111 insertions(+), 0 deletions(-) create mode 100755 testprogs/win32/prepare_dcpromo/GNUmakefile create mode 100755 testprogs/win32/prepare_dcpromo/NMakefile create mode 100755 testprogs/win32/prepare_dcpromo/prepare_dcpromo.c Changeset truncated at 500 lines: diff --git a/testprogs/win32/prepare_dcpromo/GNUmakefile b/testprogs/win32/prepare_dcpromo/GNUmakefile new file mode 100755 index 0000000..1c95613 --- /dev/null +++ b/testprogs/win32/prepare_dcpromo/GNUmakefile @@ -0,0 +1,21 @@ +INCLUDES=-I. +CFLAGS=$(INCLUDES) +LIBS=-ladvapi32 + +PREPARE_DCPROMO = prepare_dcpromo.exe + +all: $(PREPARE_DCPROMO) + +MINGW_CC = i586-mingw32msvc-cc +CC = $(MINGW_CC) + +.SUFFIXES: .c .obj .exe + +.c.obj: + $(CC) $(CFLAGS) -c $< -o $@ + +.obj.exe: + $(CC) $(CFLAGS) -o $@ $< $(LIBS) + +clean: + rm -f *~ *.obj *.exe diff --git a/testprogs/win32/prepare_dcpromo/NMakefile b/testprogs/win32/prepare_dcpromo/NMakefile new file mode 100755 index 0000000..6f810ee --- /dev/null +++ b/testprogs/win32/prepare_dcpromo/NMakefile @@ -0,0 +1,16 @@ +# +# use nmake /f NMakefile [<target>] +# +INCLUDES=-I +CFLAGS=$(INCLUDES) -Zi -nologo -Dsnprintf=sprintf_s +LIBS=advapi32.lib + +PREPARE_DCPROMO = prepare_dcpromo.exe + +all: $(PREPARE_DCPROMO) + +clean: + del *~ *.obj *.exe + +prepare_dcpromo.exe: prepare_dcpromo.obj + $(CC) $(CFLAGS) -o prepare_dcpromo.exe prepare_dcpromo.obj $(LIBS) diff --git a/testprogs/win32/prepare_dcpromo/prepare_dcpromo.c b/testprogs/win32/prepare_dcpromo/prepare_dcpromo.c new file mode 100755 index 0000000..91b819b --- /dev/null +++ b/testprogs/win32/prepare_dcpromo/prepare_dcpromo.c @@ -0,0 +1,1074 @@ +/* + Copyright (C) Stefan Metzmacher <me...@samba.org> 2010 + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see <http://www.gnu.org/licenses/>. + Published to the public domain + */ + +/* + * This tool can set the DOMAIN-SID and nextRid counter in + * the local SAM on windows servers (tested with w2k8r2) + * + * dcpromo will use this values for the ad domain it creates. + * + * This might be useful for upgrades from a Samba3 domain. + */ + +#include <windows.h> +#include <stdio.h> +#include <stdlib.h> +#include <ctype.h> + +/* Convert a binary SID to a character string */ +static DWORD SidToString(const SID *sid, + char **string) +{ + DWORD id_auth; + int i, ofs, maxlen; + char *result; + + if (!sid) { + return ERROR_INVALID_SID; + } + + maxlen = sid->SubAuthorityCount * 11 + 25; + + result = (char *)malloc(maxlen); + if (result == NULL) { + return ERROR_NOT_ENOUGH_MEMORY; + } + + /* + * BIG NOTE: this function only does SIDS where the identauth is not + * >= ^32 in a range of 2^48. + */ + + id_auth = sid->IdentifierAuthority.Value[5] + + (sid->IdentifierAuthority.Value[4] << 8) + + (sid->IdentifierAuthority.Value[3] << 16) + + (sid->IdentifierAuthority.Value[2] << 24); + + ofs = snprintf(result, maxlen, "S-%u-%lu", + (unsigned int)sid->Revision, (unsigned long)id_auth); + + for (i = 0; i < sid->SubAuthorityCount; i++) { + ofs += snprintf(result + ofs, maxlen - ofs, "-%lu", + (unsigned long)sid->SubAuthority[i]); + } + + *string = result; + return ERROR_SUCCESS; +} + +static DWORD StringToSid(const char *str, + SID *sid) +{ + const char *p; + char *q; + DWORD x; + + if (!sid) { + return ERROR_INVALID_PARAMETER; + } + + /* Sanity check for either "S-" or "s-" */ + + if (!str + || (str[0]!='S' && str[0]!='s') + || (str[1]!='-')) + { + return ERROR_INVALID_PARAMETER; + } + + /* Get the SID revision number */ + + p = str+2; + x = (DWORD)strtol(p, &q, 10); + if (x==0 || !q || *q!='-') { + return ERROR_INVALID_SID; + } + sid->Revision = (BYTE)x; + + /* Next the Identifier Authority. This is stored in big-endian + in a 6 byte array. */ + + p = q+1; + x = (DWORD)strtol(p, &q, 10); + if (!q || *q!='-') { + return ERROR_INVALID_SID; + } + sid->IdentifierAuthority.Value[5] = (x & 0x000000ff); + sid->IdentifierAuthority.Value[4] = (x & 0x0000ff00) >> 8; + sid->IdentifierAuthority.Value[3] = (x & 0x00ff0000) >> 16; + sid->IdentifierAuthority.Value[2] = (x & 0xff000000) >> 24; + sid->IdentifierAuthority.Value[1] = 0; + sid->IdentifierAuthority.Value[0] = 0; + + /* now read the the subauthorities */ + + p = q +1; + sid->SubAuthorityCount = 0; + while (sid->SubAuthorityCount < 6) { + x=(DWORD)strtoul(p, &q, 10); + if (p == q) + break; + if (q == NULL) { + return ERROR_INVALID_SID; + } + sid->SubAuthority[sid->SubAuthorityCount++] = x; + + if ((*q!='-') || (*q=='\0')) + break; + p = q + 1; + } + + /* IF we ended early, then the SID could not be converted */ + + if (q && *q!='\0') { + return ERROR_INVALID_SID; + } + + return ERROR_SUCCESS; +} + +#define MIN(a,b) ((a)<(b)?(a):(b)) +static void print_asc(const unsigned char *buf,int len) +{ + int i; + for (i=0;i<len;i++) + printf("%c", isprint(buf[i])?buf[i]:'.'); +} + +static void dump_data(const unsigned char *buf1,int len) +{ + const unsigned char *buf = (const unsigned char *)buf1; + int i=0; + if (len<=0) return; + + printf("[%03X] ",i); + for (i=0;i<len;) { + printf("%02X ",(int)buf[i]); + i++; + if (i%8 == 0) printf(" "); + if (i%16 == 0) { + print_asc(&buf[i-16],8); printf(" "); + print_asc(&buf[i-8],8); printf("\n"); + if (i<len) printf("[%03X] ",i); + } + } + if (i%16) { + int n; + n = 16 - (i%16); + printf(" "); + if (n>8) printf(" "); + while (n--) printf(" "); + n = MIN(8,i%16); + print_asc(&buf[i-(i%16)],n); printf( " " ); + n = (i%16) - n; + if (n>0) print_asc(&buf[i-n],n); + printf("\n"); + } +} + +static DWORD calc_tmp_HKLM_SECURITY_SD(SECURITY_DESCRIPTOR *old_sd, + SID *current_user_sid, + SECURITY_DESCRIPTOR **_old_parent_sd, + SECURITY_DESCRIPTOR **_old_child_sd, + SECURITY_DESCRIPTOR **_new_parent_sd, + SECURITY_DESCRIPTOR **_new_child_sd) +{ + LONG status; + DWORD cbSecurityDescriptor = 0; + SECURITY_DESCRIPTOR *old_parent_sd = NULL; + SECURITY_DESCRIPTOR *old_child_sd = NULL; + SECURITY_DESCRIPTOR *new_parent_sd = NULL; + SECURITY_DESCRIPTOR *new_child_sd = NULL; + BOOL ok; + ACL *old_Dacl = NULL; + ACL *new_Dacl = NULL; + ACL_SIZE_INFORMATION dacl_info; + DWORD i = 0; + SECURITY_DESCRIPTOR *AbsoluteSD = NULL; + DWORD dwAbsoluteSDSize = 0; + DWORD dwRelativeSDSize = 0; + DWORD dwDaclSize = 0; + ACL *Sacl = NULL; + DWORD dwSaclSize = 0; + SID *Owner = NULL; + DWORD dwOwnerSize = 0; + SID *PrimaryGroup = NULL; + DWORD dwPrimaryGroupSize = 0; + ACCESS_ALLOWED_ACE *ace = NULL; + + ok = MakeAbsoluteSD(old_sd, + NULL, + &dwAbsoluteSDSize, + NULL, + &dwDaclSize, + NULL, + &dwSaclSize, + NULL, + &dwOwnerSize, + NULL, + &dwPrimaryGroupSize); + if (!ok) { + status = GetLastError(); + } + if (status != ERROR_INSUFFICIENT_BUFFER) { + printf("LINE:%u: Error: %d (0x%X)\n", __LINE__, status, status); + return status; + } + + AbsoluteSD = (SECURITY_DESCRIPTOR *)malloc(dwAbsoluteSDSize+1024); + if (AbsoluteSD == NULL) { + printf("LINE:%u: Error: no memory\n", __LINE__); + return ERROR_NOT_ENOUGH_MEMORY; + } + old_Dacl = (ACL *)malloc(dwDaclSize + 1024); + if (old_Dacl == NULL) { + printf("LINE:%u: Error: no memory\n", __LINE__); + return ERROR_NOT_ENOUGH_MEMORY; + } + Sacl = (ACL *)malloc(dwSaclSize); + if (Sacl == NULL) { + printf("LINE:%u: Error: no memory\n", __LINE__); + return ERROR_NOT_ENOUGH_MEMORY; + } + Owner = (SID *)malloc(dwOwnerSize); + if (Owner == NULL) { + printf("LINE:%u: Error: no memory\n", __LINE__); + return ERROR_NOT_ENOUGH_MEMORY; + } + PrimaryGroup = (SID *)malloc(dwPrimaryGroupSize); + if (PrimaryGroup == NULL) { + printf("LINE:%u: Error: no memory\n", __LINE__); + return ERROR_NOT_ENOUGH_MEMORY; + } + + ok = MakeAbsoluteSD(old_sd, + AbsoluteSD, + &dwAbsoluteSDSize, + old_Dacl, + &dwDaclSize, + Sacl, + &dwSaclSize, + Owner, + &dwOwnerSize, + PrimaryGroup, + &dwPrimaryGroupSize); + if (!ok) { + status = GetLastError(); + printf("LINE:%u: Error: %d (0x%X)\n", __LINE__, status, status); + return status; + } + + AbsoluteSD->Control |= SE_DACL_AUTO_INHERITED | SE_DACL_AUTO_INHERIT_REQ | SE_DACL_PROTECTED; + dwRelativeSDSize = 0; + ok = MakeSelfRelativeSD(AbsoluteSD, + NULL, + &dwRelativeSDSize); + if (!ok) { + status = GetLastError(); + } + if (status != ERROR_INSUFFICIENT_BUFFER) { + printf("LINE:%u: Error: %d (0x%X)\n", __LINE__, status, status); + return ERROR_NOT_ENOUGH_MEMORY; + } + + old_parent_sd = (SECURITY_DESCRIPTOR *)malloc(dwRelativeSDSize); + if (old_parent_sd == NULL) { + printf("LINE:%u: Error: no memory\n", __LINE__); + return ERROR_NOT_ENOUGH_MEMORY; + } + + ok = MakeSelfRelativeSD(AbsoluteSD, + old_parent_sd, + &dwRelativeSDSize); + if (!ok) { + status = GetLastError(); + printf("LINE:%u: Error: %d (0x%X)\n", __LINE__, status, status); + return status; + } + + ok = GetAclInformation(old_Dacl, + &dacl_info, + sizeof(dacl_info), + AclSizeInformation); + if (!ok) { + status = GetLastError(); + printf("LINE:%u: Error: %d (0x%X)\n", __LINE__, status, status); + return status; + } + + new_Dacl = (ACL *)calloc(dacl_info.AclBytesInUse + 1024, 1); + if (new_Dacl == NULL) { + printf("LINE:%u: Error: no memory\n", __LINE__); + return ERROR_NOT_ENOUGH_MEMORY; + } + + InitializeAcl(new_Dacl, dacl_info.AclBytesInUse + 1024, ACL_REVISION); + + ok = AddAccessAllowedAce(new_Dacl, ACL_REVISION, + KEY_ALL_ACCESS, current_user_sid); + if (!ok) { + status = GetLastError(); + printf("LINE:%u: Error: %d (0x%X)\n", __LINE__, status, status); + return status; + } + + ok = GetAce(new_Dacl, 0, (LPVOID *)&ace); + if (!ok) { + status = GetLastError(); + printf("LINE:%u: Error: %d (0x%X)\n", __LINE__, status, status); + return status; + } + + ace->Header.AceFlags |= CONTAINER_INHERIT_ACE | OBJECT_INHERIT_ACE; + + for (i=0; i < dacl_info.AceCount; i++) { + ok = GetAce(old_Dacl, i, (LPVOID *)&ace); + if (!ok) { + status = GetLastError(); + printf("LINE:%u: Error: %d (0x%X)\n", __LINE__, status, status); + return status; + } + + ok = AddAce(new_Dacl, ACL_REVISION, MAXDWORD, + ace, ace->Header.AceSize); + if (!ok) { + status = GetLastError(); + printf("LINE:%u: Error: %d (0x%X)\n", __LINE__, status, status); + return status; + } + } + + AbsoluteSD->Dacl = new_Dacl; + dwRelativeSDSize = 0; + ok = MakeSelfRelativeSD(AbsoluteSD, + NULL, + &dwRelativeSDSize); + if (!ok) { + status = GetLastError(); + } + if (status != ERROR_INSUFFICIENT_BUFFER) { + printf("LINE:%u: Error: %d (0x%X)\n", __LINE__, status, status); + return ERROR_NOT_ENOUGH_MEMORY; + } + + new_parent_sd = (SECURITY_DESCRIPTOR *)malloc(dwRelativeSDSize); + if (new_parent_sd == NULL) { + printf("LINE:%u: Error: no memory\n", __LINE__); + return ERROR_NOT_ENOUGH_MEMORY; + } + + ok = MakeSelfRelativeSD(AbsoluteSD, + new_parent_sd, + &dwRelativeSDSize); + if (!ok) { + status = GetLastError(); + printf("LINE:%u: Error: %d (0x%X)\n", __LINE__, status, status); + return status; + } + + for (i=0; i < dacl_info.AceCount; i++) { + ok = GetAce(old_Dacl, i, (LPVOID *)&ace); + if (!ok) { + status = GetLastError(); + printf("LINE:%u: Error: %d (0x%X)\n", __LINE__, status, status); + return status; + } + + ace->Header.AceFlags |= INHERITED_ACE; + } + + AbsoluteSD->Control &= ~SE_DACL_PROTECTED; + AbsoluteSD->Dacl = old_Dacl; + dwRelativeSDSize = 0; + ok = MakeSelfRelativeSD(AbsoluteSD, + NULL, + &dwRelativeSDSize); + if (!ok) { + status = GetLastError(); + } + if (status != ERROR_INSUFFICIENT_BUFFER) { + printf("LINE:%u: Error: %d (0x%X)\n", __LINE__, status, status); + return ERROR_NOT_ENOUGH_MEMORY; + } + + old_child_sd = (SECURITY_DESCRIPTOR *)malloc(dwRelativeSDSize); + if (old_child_sd == NULL) { + printf("LINE:%u: Error: no memory\n", __LINE__); + return ERROR_NOT_ENOUGH_MEMORY; + } + + ok = MakeSelfRelativeSD(AbsoluteSD, + old_child_sd, + &dwRelativeSDSize); + if (!ok) { + status = GetLastError(); + printf("LINE:%u: Error: %d (0x%X)\n", __LINE__, status, status); + return status; + } + + for (i=0; i < dacl_info.AceCount + 1; i++) { + ok = GetAce(new_Dacl, i, (LPVOID *)&ace); + if (!ok) { + status = GetLastError(); + printf("LINE:%u: Error: %d (0x%X)\n", __LINE__, status, status); + return status; + } + + ace->Header.AceFlags |= INHERITED_ACE; + } + + AbsoluteSD->Dacl = new_Dacl; + dwRelativeSDSize = 0; + ok = MakeSelfRelativeSD(AbsoluteSD, + NULL, + &dwRelativeSDSize); + if (!ok) { + status = GetLastError(); + } + if (status != ERROR_INSUFFICIENT_BUFFER) { + printf("LINE:%u: Error: %d (0x%X)\n", __LINE__, status, status); + return ERROR_NOT_ENOUGH_MEMORY; -- Samba Shared Repository