⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 ntreg.c

📁 The Offline NT Password Editor (c) 1997-2004 Petter Nordahl-Hagen
💻 C
📖 第 1 页 / 共 5 页
字号:
  if (vkkey->len_data == 0) return NULL;  if (vkkey->len_data == 0x80000000) {  /* Special inline case (len = 0x80000000) */    return(&vkkey->val_type); /* Data (4 bytes?) in type field */  }      if (val_type && vkkey->val_type && (vkkey->val_type) != val_type) {    printf("Value <%s> is not of correct type!\n",path);    return NULL;  }  /* Negative len is inline, return ptr to offset-field which in   * this case contains the data itself   */  if (vkkey->len_data & 0x80000000) return(&vkkey->ofs_data);  /* Normal return, return data pointer */  return(hdesc->buffer + vkkey->ofs_data + 0x1004);}/* Get and copy key data (if any) to buffer * if kv==NULL will allocate needed return struct & buffer * else will use buffer allocated for it (if it fits) * return len+data or NULL if not found (or other error) * NOTE: caller must deallocate buffer! a simple free(keyval) will suffice. */struct keyval *get_val2buf(struct hive *hdesc, struct keyval *kv,			    int vofs, char *path, int type ){  int l;  struct keyval *kr;  void *keydataptr;  l = get_val_len(hdesc, vofs, path);  if (l == -1) return(NULL);  /* error */  if (kv && (kv->len < l)) return(NULL); /* Check for overflow of supplied buffer */  keydataptr = get_val_data(hdesc, vofs, path, type);  /*  if (!keydataptr) return(NULL); error */  /* Allocate space for data + header, or use supplied buffer */  if (kv) {    kr = kv;  } else {    ALLOC(kr,1,l+sizeof(int)+4);  }  kr->len = l;  memcpy(&(kr->data), keydataptr, l);  return(kr);}/* DWORDs are so common that I make a small function to get it easily */int get_dword(struct hive *hdesc, int vofs, char *path){  struct keyval *v;  int dword;  v = get_val2buf(hdesc, NULL, vofs, path, REG_DWORD);  if (!v) return(-1); /* well... -1 COULD BE THE STORED VALUE TOO */  dword = (int)v->data;  FREE(v);  return(dword);  }/* Sanity checker when transferring data into a block * ofs = offset to data block, point to start of actual datablock linkage * data = data to copy * size = size of data to copy */int fill_block(struct hive *hdesc, int ofs, void *data, int size){  int blksize;  blksize = get_int(hdesc->buffer + ofs);  blksize = -blksize;#if 0  printf("fill_block: ofs = %x - %x, size = %x, blksize = %x\n",ofs,ofs+size,size,blksize);#endif  /*  if (blksize < size || ( (ofs & 0xfffff000) != ((ofs+size) & 0xfffff000) )) { */  if (blksize < size) {    printf("fill_block: ERROR: block to small for data: ofs = %x, size = %x, blksize = %x\n",ofs,size,blksize);    debugit(hdesc->buffer,hdesc->size);    abort();  }  memcpy(hdesc->buffer + ofs + 4, data, size);  return(0);}/* Free actual data of a value, and update value descriptor * hdesc - hive * vofs  - current key * path  - path to value * we return offset of vk */int free_val_data(struct hive *hdesc, int vofs, char *path){  struct vk_key *vkkey;  int vkofs, inl;  vkofs = trav_path(hdesc,vofs,path,1);  if (!vkofs) {    return 0;  }  vkofs +=4;  vkkey = (struct vk_key *)(hdesc->buffer + vkofs);  inl = (vkkey->len_data & 0x80000000);  if (!inl) {    free_block(hdesc, vkkey->ofs_data + 0x1000);  }  vkkey->len_data = 0;  vkkey->ofs_data = 0;  return(vkofs);}/* Allocate data for value, realloc if it already contains stuff * hdesc - hive * vofs  - current key * path  - path to value * size  - size of data * Returns: 0 - error, >0 pointer to actual dataspace */int alloc_val_data(struct hive *hdesc, int vofs, char *path, int size){  struct vk_key *vkkey;  int vkofs, len;  int datablk;  vkofs = trav_path(hdesc,vofs,path,1);  if (!vkofs) {    return (0);  }  vkofs +=4;  vkkey = (struct vk_key *)(hdesc->buffer + vkofs);  /* Allocate space for new data */  datablk = alloc_block(hdesc, vkofs, size);  if (!datablk) return(0);  len = vkkey->len_data & 0x7fffffff;  /* Then we dealloc if something was there before */  if (len) free_val_data(hdesc,vofs,path);  /* Link in new datablock */  vkkey->ofs_data = datablk - 0x1000;  vkkey->len_data = size;  return(datablk + 4);}/* Add a value to a key. * Just add the metadata (empty value), to put data into it, use * put_buf2val afterwards * hdesc - hive * nkofs - current key * name  - name of value * type  - type of value * returns: 0 err, >0 offset to value metadata */struct vk_key *add_value(struct hive *hdesc, int nkofs, char *name, int type){  struct nk_key *nk;  int oldvlist = 0, newvlist, newvkofs;  struct vk_key *newvkkey;  char *blank="";  if (!name || !*name) return(NULL);  nk = (struct nk_key *)(hdesc->buffer + nkofs);  if (nk->id != 0x6b6e) {    printf("add_value: Key pointer not to 'nk' node!\n");    return(NULL);  }  if (trav_path(hdesc, nkofs, name, 1)) {    printf("add_value: value %s already exists\n",name);    return(NULL);  }  if (!strcmp(name,"@")) name = blank;   if (nk->no_values) oldvlist = nk->ofs_vallist;  newvlist = alloc_block(hdesc, nkofs, nk->no_values * 4 + 4);  if (!newvlist) {    printf("add_value: failed to allocate new value list!\n");    return(NULL);  }  if (oldvlist) {   /* Copy old data if any */    memcpy(hdesc->buffer + newvlist + 4, hdesc->buffer + oldvlist + 0x1004, nk->no_values * 4 + 4);  }  /* Allocate value descriptor including its name */  newvkofs = alloc_block(hdesc, newvlist, sizeof(struct vk_key) + strlen(name));  if (!newvkofs) {    printf("add_value: failed to allocate value descriptor\n");    free_block(hdesc, newvlist);    return(NULL);  }  /* Success, now fill in the metadata */  newvkkey = (struct vk_key *)(hdesc->buffer + newvkofs + 4);  /* Add pointer in value list */  *(int *)(hdesc->buffer + newvlist + 4 + (nk->no_values * 4)) = newvkofs - 0x1000;  /* Fill in vk struct */  newvkkey->id = 0x6b76;  newvkkey->len_name = strlen(name);  if (type == REG_DWORD || type == REG_DWORD_BIG_ENDIAN) {    newvkkey->len_data = 0x80000004;  /* Prime the DWORD inline stuff */  } else {    newvkkey->len_data = 0x00000000;  }  newvkkey->ofs_data = 0;  newvkkey->val_type = type;  newvkkey->flag     = 1;   /* Don't really know what this is */  newvkkey->dummy1   = 0;  strcpy((char *)&newvkkey->keyname, name);  /* And copy name */  /* Finally update the key and free the old valuelist */  nk->no_values++;  nk->ofs_vallist = newvlist - 0x1000;  if (oldvlist) free_block(hdesc,oldvlist + 0x1000);  return(newvkkey);}/* Remove a vk-struct incl dataspace if any * Mostly for use by higher level stuff * hdesc - hive * vkofs - offset to vk */void del_vk(struct hive *hdesc, int vkofs){  struct vk_key *vk;  vk = (struct vk_key *)(hdesc->buffer + vkofs);  if (vk->id != 0x6b76) {    printf("del_vk: Key pointer not to 'vk' node!\n");    return;  }    if ( !(vk->len_data & 0x80000000) && vk->ofs_data) {    free_block(hdesc, vk->ofs_data + 0x1000);  }  free_block(hdesc, vkofs - 4);}/* Delete all values from key (used in recursive delete) * hdesc - yer usual hive * nkofs - current keyoffset */void del_allvalues(struct hive *hdesc, int nkofs){  int vlistofs, o, vkofs;  long *vlistkey;  struct nk_key *nk;  nk = (struct nk_key *)(hdesc->buffer + nkofs);  if (nk->id != 0x6b6e) {    printf("del_allvalues: Key pointer not to 'nk' node!\n");    return;  }  if (!nk->no_values) {    /*    printf("del_avalues: Key has no values!\n"); */    return;  }  vlistofs = nk->ofs_vallist + 0x1004;  vlistkey = (long *)(hdesc->buffer + vlistofs);  /* Loop through index and delete all vk's */  for (o = 0; o < nk->no_values; o++) {    vkofs = vlistkey[o] + 0x1004;    del_vk(hdesc, vkofs);  }  /* Then zap the index, and update nk */  free_block(hdesc, vlistofs-4);  nk->ofs_vallist = -1;  nk->no_values = 0;}/* Delete single value from key * hdesc - yer usual hive * nkofs - current keyoffset * name  - name of value to delete * returns: 0 - ok, 1 - failed */int del_value(struct hive *hdesc, int nkofs, char *name){  int vlistofs, slot, o, n, vkofs, newlistofs;  long *vlistkey, *tmplist, *newlistkey;  struct nk_key *nk;  char *blank="";  if (!name || !*name) return(1);  if (!strcmp(name,"@")) name = blank;  nk = (struct nk_key *)(hdesc->buffer + nkofs);  if (nk->id != 0x6b6e) {    printf("del_value: Key pointer not to 'nk' node!\n");    return(1);  }  if (!nk->no_values) {    printf("del_value: Key has no values!\n");    return(1);  }  vlistofs = nk->ofs_vallist + 0x1004;  vlistkey = (long *)(hdesc->buffer + vlistofs);  slot = vlist_find(hdesc, vlistofs, nk->no_values, name);  if (slot == -1) {    printf("del_value: value %s not found!\n",name);    return(1);  }  /* Delete vk and data */  vkofs = vlistkey[slot] + 0x1004;  del_vk(hdesc, vkofs);  /* Copy out old index list */  CREATE(tmplist,long,nk->no_values);  memcpy(tmplist, vlistkey, nk->no_values * sizeof(long));  free_block(hdesc,vlistofs-4);  /* Get rid of old list */  nk->no_values--;  if (nk->no_values) {    newlistofs = alloc_block(hdesc, vlistofs, nk->no_values * sizeof(long));    if (!newlistofs) {      printf("del_value: FATAL: Was not able to alloc new index list\n");      abort();    }    /* Now copy over, omitting deleted entry */    newlistkey = (long *)(hdesc->buffer + newlistofs + 4);    for (n = 0, o = 0; o < nk->no_values+1; o++, n++) {      if (o == slot) o++;      newlistkey[n] = tmplist[o];    }    nk->ofs_vallist = newlistofs - 0x1000;  } else {    nk->ofs_vallist = -1;  }  return(0);}/* Add a subkey to a key * hdesc - usual.. * nkofs - offset of current nk * name  - name of key to add * return: ptr to new keystruct, or NULL */#undef AKDEBUGstruct nk_key *add_key(struct hive *hdesc, int nkofs, char *name){  int slot, newlfofs = 0, oldlfofs = 0, newliofs = 0;  int oldliofs = 0;  int o, n, i, onkofs, newnkofs, cmp;  int rimax, rislot, riofs, namlen;  struct ri_key *ri = NULL;  struct lf_key *newlf = NULL, *oldlf;  struct li_key *newli = NULL, *oldli;  struct nk_key *key, *newnk, *onk;  long hash;  key = (struct nk_key *)(hdesc->buffer + nkofs);  if (key->id != 0x6b6e) {    printf("add_key: current ptr not 'nk'\n");    return(NULL);  }  namlen = strlen(name);  slot = -1;  if (key->no_subkeys) {   /* It already has subkeys */        oldlfofs = key->ofs_lf;    oldliofs = key->ofs_lf;       oldlf = (struct lf_key *)(hdesc->buffer + oldlfofs + 0x1004);    if (oldlf->id != 0x666c && oldlf->id != 0x686c && oldlf->id != 0x696c && oldlf->id != 0x6972)  {      printf("add_key: index type not supported: 0x%04x\n",oldlf->id);      return(NULL);    }    rimax = 0; ri = NULL; riofs = 0; rislot = -1;    if (oldlf->id == 0x6972) {  /* Indirect index 'ri', init loop */      riofs = key->ofs_lf;      ri = (struct ri_key *)(hdesc->buffer + riofs + 0x1004);      rimax = ri->no_lis-1;#ifdef AKDEBUG      printf("add_key: entering 'ri' traverse, rimax = %d\n",rimax);#endif      oldliofs = ri->hash[rislot+1].ofs_li;      oldlfofs = ri->hash[rislot+1].ofs_li;    }    do {   /* 'ri' loop, at least run once if no 'ri' deep index */      if (ri) { /* Do next 'ri' slot */	rislot++;	oldliofs = ri->hash[rislot].ofs_li;	oldlfofs = ri->hash[rislot].ofs_li;	oldli = (struct li_key *)(hdesc->buffer + oldliofs + 0x1004);	oldlf = (struct lf_key *)(hdesc->buffer + oldlfofs + 0x1004);      }      oldli = (struct li_key *)(hdesc->buffer + oldliofs + 0x1004);      oldlf = (struct lf_key *)(hdesc->buffer + oldlfofs + 0x1004);#ifdef AKDEBUG      printf("add_key: top of ri-loop: rislot = %d\n",rislot);#endif      slot = -1;      if (oldli->id == 0x696c) {  /* li */	#ifdef AKDEBUG	printf("add_key: li slot allocate\n");#endif		FREE(newli);	ALLOC(newli, 8 + 4*oldli->no_keys + 4, 1);	newli->no_keys = oldli->no_keys;	newli->id = oldli->id;		/* Now copy old, checking where to insert (alphabetically) */	for (o = 0, n = 0; o < oldli->no_keys; o++,n++) {	  onkofs = oldli->hash[o].ofs_nk;	  onk = (struct nk_key *)(onkofs + hdesc->buffer + 0x1004);	  if (slot == -1) {#if 0	    printf("add_key: cmp <%s> with <%s>\n",name,onk->keyname);#endif	    cmp = strncasecmp(name, onk->keyname, (namlen > onk->len_name) ? namlen : onk->len_name);	    if (!cmp) {	      printf("add_key: key %s already exists!\n",name);	      FREE(newli);	      return(NULL);	    }	    if ( cmp < 0) {	      slot = o;	      rimax = rislot; /* Cause end of 'ri' search, too */	      n++;

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -