[Patch] regtool: Add load/unload commands and --binary option

classic Classic list List threaded Threaded
32 messages Options
12
Reply | Threaded
Open this post in threaded view
|

[Patch] regtool: Add load/unload commands and --binary option

Christian Franke
Hi,

the attached patch adds commands "load" and "unload" and options "-b,
--binary" to regtool.

Load a registry hive from PATH into new SUBKEY:

 regtool load KEY\SUBKEY PATH

Unload and remove SUBKEY later:

 regtool unload KEY\SUBKEY

Print REG_BINARY value as hex:

 regtool -b get KEY\VALUE

Set REG_BINARY value from hex args:

 regtool -b set KEY\VALUE XX XX XX XX ...


Example:
Suppose S:\ is a partition on a second HD which contains a copy of all
files of XP system partition C:\.
The following script fixes the logical drive mappings of the backup
installation.
This allows booting backup drive S:\ as C:\ after original C:\ drive has
been removed.

#!/bin/sh
set -e

# Load backup SYSTEM hive as SYSTEM.TMP
regtool load /HKLM/SYSTEM.TMP /cygdrive/s/WINDOWS/system32/config/system
trap 'regtool unload /HKLM/SYSTEM.TMP' ERR

# Remove all logical drive mappings in backup
# (Somewhat tricky, because key value names contain backslashes)
for v in $(regtool list /HKLM/SYSTEM.TMP/MountedDevices |
          sed -n '/^\\DosDevices\\[C-Z]:$/s,\\,/,gp')
do
  regtool -K, unset "/HKLM/SYSTEM.TMP/MountedDevices,$v"
done

# Map current S:\ as C:\ in backup
m=$(regtool -K, -b get /HKLM/SYSTEM/MountedDevices/,/DosDevices/S:)
regtool -K, -b set /HKLM/SYSTEM.TMP/MountedDevices/,/DosDevices/C: $m

# Unload hive
trap '' ERR
regtool unload /HKLM/SYSTEM.TMP

# End of script
####################


Thanks for any comment

Christian


--- regtool.cc.orig 2005-09-12 01:48:05.001000000 +0200
+++ regtool.cc 2006-01-24 15:48:55.750000000 +0100
@@ -10,15 +10,17 @@
 
 #include <stdio.h>
 #include <stdlib.h>
+#include <errno.h>
 #include <ctype.h>
 #include <getopt.h>
 #include <windows.h>
+#include <sys/cygwin.h>
 
 #define DEFAULT_KEY_SEPARATOR '\\'
 
 enum
 {
-  KT_AUTO, KT_INT, KT_STRING, KT_EXPAND, KT_MULTI
+  KT_AUTO, KT_BINARY, KT_INT, KT_STRING, KT_EXPAND, KT_MULTI
 } key_type = KT_AUTO;
 
 char key_sep = DEFAULT_KEY_SEPARATOR;
@@ -32,6 +34,7 @@
 
 static struct option longopts[] =
 {
+  {"binary", no_argument, NULL, 'b' },
   {"expand-string", no_argument, NULL, 'e' },
   {"help", no_argument, NULL, 'h' },
   {"integer", no_argument, NULL, 'i' },
@@ -47,7 +50,7 @@
   {NULL, 0, NULL, 0}
 };
 
-static char opts[] = "ehiklmpqsvVK:";
+static char opts[] = "behiklmpqsvVK:";
 
 int listwhat = 0;
 int postfix = 0;
@@ -62,7 +65,7 @@
 usage (FILE *where = stderr)
 {
   fprintf (where, ""
-  "Usage: %s [OPTION] (add | check | get | list | remove | unset) KEY\n"
+  "Usage: %s [OPTION] (add|check|get|list|remove|unset|load|unload) KEY\n"
   "View or edit the Win32 registry\n"
   "\n"
   "", prog_name);
@@ -76,6 +79,8 @@
     " remove KEY                 remove KEY\n"
     " set KEY\\VALUE [data ...]   set VALUE\n"
     " unset KEY\\VALUE            removes VALUE from KEY\n"
+    " load KEY\\SUBKEY PATH       load hive from PATH into new SUBKEY\n"
+    " unload KEY\\SUBKEY          unload hive and remove SUBKEY\n"
     "\n");
   fprintf (where, ""
   "Options for 'list' Action:\n"
@@ -83,7 +88,11 @@
   " -l, --list           print only VALUEs\n"
   " -p, --postfix        like ls -p, appends '\\' postfix to KEY names\n"
   "\n"
+  "Options for 'get' Action:\n"
+  " -b, --binary         print REG_BINARY data as hex bytes\n"
+  "\n"
   "Options for 'set' Action:\n"
+  " -b, --binary         set type to REG_BINARY\n"
   " -e, --expand-string  set type to REG_EXPAND_SZ\n"
   " -i, --integer        set type to REG_DWORD\n"
   " -m, --multi-string   set type to REG_MULTI_SZ\n"
@@ -348,9 +357,30 @@
     key = base;
   else
     {
-      rv = RegOpenKeyEx (base, n, 0, access, &key);
-      if (rv != ERROR_SUCCESS)
- Fail (rv);
+      if (access)
+ {
+  rv = RegOpenKeyEx (base, n, 0, access, &key);
+  if (rv != ERROR_SUCCESS)
+    Fail (rv);
+ }
+      else if (argv[1])
+ {
+  char win32_path[MAX_PATH];
+  cygwin_conv_to_win32_path(argv[1], win32_path);
+  rv = RegLoadKey(base, n, win32_path);
+  if (rv != ERROR_SUCCESS)
+    Fail (rv);
+  if (verbose)
+    printf("key %s loaded from file %s\n", n, win32_path);
+ }
+      else
+ {
+  rv = RegUnLoadKey(base, n);
+  if (rv != ERROR_SUCCESS)
+    Fail (rv);
+  if (verbose)
+    printf("key %s unloaded\n", n);
+ }
     }
   //printf("key `%s' value `%s'\n", n, value);
 }
@@ -491,7 +521,7 @@
 {
   int i, n;
   DWORD v, rv;
-  char *a = argv[1], *data;
+  char *a = argv[1], *data = 0;
   find_key (2, KEY_ALL_ACCESS);
 
   if (key_type == KT_AUTO)
@@ -510,6 +540,27 @@
 
   switch (key_type)
     {
+    case KT_BINARY:
+      for (n = 0; argv[n+1]; n++)
+        ;
+      if (n > 0)
+ {
+  data = (char *) malloc (n);
+  for (i = 0; i < n; i++)
+    {
+      char *e;
+      errno = 0;
+      v = strtoul (argv[i+1], &e, 16);
+      if (errno || v > 0xff || *e)
+ {
+  fprintf (stderr, "Invalid hex constant `%s'\n", argv[i+1]);
+  exit (1);
+ }
+      data[i] = (char) v;
+    }
+ }
+      rv = RegSetValueEx (key, value, 0, REG_BINARY, (const BYTE *) data, n);
+      break;
     case KT_INT:
       v = strtoul (a, 0, 0);
       rv = RegSetValueEx (key, value, 0, REG_DWORD, (const BYTE *) &v,
@@ -542,6 +593,9 @@
       rv = ERROR_INVALID_CATEGORY;
       break;
     }
+
+  if (data)
+    free(data);
 
   if (rv != ERROR_SUCCESS)
     Fail (rv);
@@ -577,7 +631,14 @@
   switch (vtype)
     {
     case REG_BINARY:
-      fwrite (data, dsize, 1, stdout);
+      if (key_type == KT_BINARY) // hack
+ {
+  for (unsigned i = 0; i < dsize; i++)
+    printf ("%02x%c", (unsigned char)data[i],
+      (i < dsize-1 ? ' ' : '\n'));
+ }
+      else
+ fwrite (data, dsize, 1, stdout);
       break;
     case REG_DWORD:
       printf ("%lu\n", *(DWORD *) data);
@@ -610,6 +671,31 @@
   return 0;
 }
 
+int
+cmd_load ()
+{
+  if (!argv[1])
+    {
+      usage();
+      return 1;
+    }
+  find_key(1, 0);
+  return 0;
+}
+
+int
+cmd_unload ()
+{
+  if (argv[1])
+    {
+      usage();
+      return 1;
+    }
+  find_key(1, 0);
+  return 0;
+}
+
+
 struct
 {
   const char *name;
@@ -623,6 +709,8 @@
   {"set", cmd_set},
   {"unset", cmd_unset},
   {"get", cmd_get},
+  {"load", cmd_load},
+  {"unload", cmd_unload},
   {0, 0}
 };
 
@@ -642,6 +730,9 @@
   while ((g = getopt_long (argc, _argv, opts, longopts, NULL)) != EOF)
     switch (g)
  {
+ case 'b':
+  key_type = KT_BINARY;
+  break;
  case 'e':
   key_type = KT_EXPAND;
   break;
Reply | Threaded
Open this post in threaded view
|

Re: [Patch] regtool: Add load/unload commands and --binary option

Corinna Vinschen-2
On Jan 24 21:00, Christian Franke wrote:

> Hi,
>
> the attached patch adds commands "load" and "unload" and options "-b,
> --binary" to regtool.
>
> Load a registry hive from PATH into new SUBKEY:
>
> regtool load KEY\SUBKEY PATH
>
> Unload and remove SUBKEY later:
>
> regtool unload KEY\SUBKEY
>
> Print REG_BINARY value as hex:
>
> regtool -b get KEY\VALUE
>
> Set REG_BINARY value from hex args:
>
> regtool -b set KEY\VALUE XX XX XX XX ...
>
>
> Example:
> Suppose S:\ is a partition on a second HD which contains a copy of all
> files of XP system partition C:\.
> The following script fixes the logical drive mappings of the backup
> installation.
> This allows booting backup drive S:\ as C:\ after original C:\ drive has
> been removed.
>
> #!/bin/sh
> set -e
>
> # Load backup SYSTEM hive as SYSTEM.TMP
> regtool load /HKLM/SYSTEM.TMP /cygdrive/s/WINDOWS/system32/config/system
> trap 'regtool unload /HKLM/SYSTEM.TMP' ERR
>
> # Remove all logical drive mappings in backup
> # (Somewhat tricky, because key value names contain backslashes)
> for v in $(regtool list /HKLM/SYSTEM.TMP/MountedDevices |
>          sed -n '/^\\DosDevices\\[C-Z]:$/s,\\,/,gp')
> do
>  regtool -K, unset "/HKLM/SYSTEM.TMP/MountedDevices,$v"
> done
>
> # Map current S:\ as C:\ in backup
> m=$(regtool -K, -b get /HKLM/SYSTEM/MountedDevices/,/DosDevices/S:)
> regtool -K, -b set /HKLM/SYSTEM.TMP/MountedDevices/,/DosDevices/C: $m
>
> # Unload hive
> trap '' ERR
> regtool unload /HKLM/SYSTEM.TMP
>
> # End of script
> ####################
>
>
> Thanks for any comment

Thanks for this patch, it looks pretty useful.  There are just two
things missing.  First, could you please create a matching ChangeLog
entry?  Second, worse, I don't see your name on the list of people
having a copyright assignment in place, which is definitely necessary
for a patch of this size.  We need a written copyright assignment from
you once, after that, you can create as many patches as you like.
Please see http://cygwin.com/contrib.html for the gory details about
the copyright assignment form and how to send it to Red Hat.


Thanks,
Corinna

--
Corinna Vinschen                  Please, send mails regarding Cygwin to
Cygwin Project Co-Leader          cygwin AT cygwin DOT com
Red Hat
Reply | Threaded
Open this post in threaded view
|

Re: [Patch] regtool: Add load/unload commands and --binary option

Igor Peshansky
On Wed, 25 Jan 2006, Corinna Vinschen wrote:

> On Jan 24 21:00, Christian Franke wrote:
> > Hi,
> >
> > the attached patch adds commands "load" and "unload" and options "-b,
> > --binary" to regtool.
> >
> > Load a registry hive from PATH into new SUBKEY:
> >
> > regtool load KEY\SUBKEY PATH
> >
> > Unload and remove SUBKEY later:
> >
> > regtool unload KEY\SUBKEY
> >
> > Print REG_BINARY value as hex:
> >
> > regtool -b get KEY\VALUE
> >
> > Set REG_BINARY value from hex args:
> >
> > regtool -b set KEY\VALUE XX XX XX XX ...
> >
> > [snip]
> > Thanks for any comment
>
> Thanks for this patch, it looks pretty useful.
> [snip]

I wonder if it would be better to use stdin/stdout for binary data (or
even add a -f option for set).  IMHO,

regtool -b get KEY1\\VALUE | regtool -b set KEY2\\VALUE

or

regtool -b get KEY1\\VALUE | regtool -b set -f - KEY2\\VALUE

looks cleaner than storing the hex encoding into a string...  If you want
a hex dump,

regtool -b get KEY1\\VALUE | od -t x1

will do it.  I'm not aware of any program that does the reverse
(hex dump->binary), but writing a perl script for that is trivial.

That said, I also think this functionality would be very useful.
        Igor
--
                                http://cs.nyu.edu/~pechtcha/
      |\      _,,,---,,_    [hidden email] | [hidden email]
ZZZzz /,`.-'`'    -.  ;-;;,_ Igor Peshansky, Ph.D. (name changed!)
     |,4-  ) )-,_. ,\ (  `'-' old name: Igor Pechtchanski
    '---''(_/--'  `-'\_) fL a.k.a JaguaR-R-R-r-r-r-.-.-.  Meow!

"Las! je suis sot... -Mais non, tu ne l'es pas, puisque tu t'en rends compte."
"But no -- you are no fool; you call yourself a fool, there's proof enough in
that!" -- Rostand, "Cyrano de Bergerac"
Reply | Threaded
Open this post in threaded view
|

Re: [Patch] regtool: Add load/unload commands and --binary option

Brian Ford
On Wed, 25 Jan 2006, Igor Peshansky wrote:

> I'm not aware of any program that does the reverse (hex dump->binary),
> but writing a perl script for that is trivial.

xxd -r ;-).

--
Brian Ford
Lead Realtime Software Engineer
VITAL - Visual Simulation Systems
FlightSafety International
the best safety device in any aircraft is a well-trained pilot...
Reply | Threaded
Open this post in threaded view
|

Re: [Patch] regtool: Add load/unload commands and --binary option

Christian Franke
In reply to this post by Corinna Vinschen-2
Corinna Vinschen wrote:

> [...]
>
>Thanks for this patch, it looks pretty useful.  There are just two
>things missing.  First, could you please create a matching ChangeLog
>entry?
>

OK.

>Second, worse, I don't see your name on the list of people
>having a copyright assignment in place, which is definitely necessary
>for a patch of this size. We need a written copyright assignment from
>you once, after that, you can create as many patches as you like.
>Please see http://cygwin.com/contrib.html for the gory details about
>the copyright assignment form and how to send it to Red Hat.
>  
>

Sorry, I wasn't aware that this is necessary for such a trivial patch.
Will send the snail mail with the legal stuff soon ;-)

Christian

Reply | Threaded
Open this post in threaded view
|

Re: [Patch] regtool: Add load/unload commands and --binary option

Christian Franke
In reply to this post by Igor Peshansky
Igor Peshansky wrote:

>>[snip]
>>    
>>
>
>I wonder if it would be better to use stdin/stdout for binary data (or
>even add a -f option for set).  IMHO,
>
>regtool -b get KEY1\\VALUE | regtool -b set KEY2\\VALUE
>
>or
>
>regtool -b get KEY1\\VALUE | regtool -b set -f - KEY2\\VALUE
>
>looks cleaner than storing the hex encoding into a string...  
>

At least when regtool is used interactively, it is IMO not very useful
to have
modem-line-noise-like output for REG_BINARY, but human readable output for
the other value types.
But this is the current behavior of "regtool get ...".


Suggest to combine the best of both worlds:

regtool get KEY\\VALUE

should always produce human readable output, in particular a hex dump
for REG_BINARY.
(But this would change existing behavior on REG_BINARY)


regtool -b get KEY\\VALUE

writes REG_BINARY as binary data to stdout.


regtool -b set KEY\\VALUE 01 02 03

sets REG_BINARY value from hex bytes in args.


regtool -b set KEY\\VALUE -

set value from binary data read from stdin


>[...]
>
>
>That said, I also think this functionality would be very useful.
>  
>

Thx,

Christian

Reply | Threaded
Open this post in threaded view
|

Re: [Patch] regtool: Add load/unload commands and --binary option

Brian Dessent
Christian Franke wrote:

> At least when regtool is used interactively, it is IMO not very useful
> to have
> modem-line-noise-like output for REG_BINARY, but human readable output for
> the other value types.
> But this is the current behavior of "regtool get ...".

Instead of an explicit -b flag, perhaps it should just call isatty() and
if being run interactively, output human readable hex dump, otherwise
output raw binary.

Brian
Reply | Threaded
Open this post in threaded view
|

Re: [Patch] regtool: Add load/unload commands and --binary option

Igor Peshansky
On Wed, 25 Jan 2006, Brian Dessent wrote:

> Christian Franke wrote:
>
> > At least when regtool is used interactively, it is IMO not very useful
> > to have modem-line-noise-like output for REG_BINARY, but human
> > readable output for the other value types. But this is the current
> > behavior of "regtool get ...".
>
> Instead of an explicit -b flag, perhaps it should just call isatty() and
> if being run interactively, output human readable hex dump, otherwise
> output raw binary.

What if you want to redirect the hex dump to a file?  IMO, isatty() checks
are only useful if the output won't change qualitatively on redirection
(e.g., for coloring).  Otherwise, it's always better to use an explicit
flag.

That said, attempting to "regtool get" a binary value is no different from
attempting to cat a binary file -- and we're not changing "cat" to output
hex dumps.  What would be useful instead is a way to query the type of a
value via regtool.  We could also add a "-h" (for --human-readable) flag
to always output the value in human-readable form (see below).

FWIW, 'A=`regtool get KEY1\\VAL`; regtool set KEY2\\VAL "$A"' will already
break for REG_MULTI_SZ type values.  It would be good to make regtool's
behavior consistent: "regtool set -f FILE" reads the value from FILE,
which would work for all value types.
        Igor
--
                                http://cs.nyu.edu/~pechtcha/
      |\      _,,,---,,_    [hidden email] | [hidden email]
ZZZzz /,`.-'`'    -.  ;-;;,_ Igor Peshansky, Ph.D. (name changed!)
     |,4-  ) )-,_. ,\ (  `'-' old name: Igor Pechtchanski
    '---''(_/--'  `-'\_) fL a.k.a JaguaR-R-R-r-r-r-.-.-.  Meow!

"Las! je suis sot... -Mais non, tu ne l'es pas, puisque tu t'en rends compte."
"But no -- you are no fool; you call yourself a fool, there's proof enough in
that!" -- Rostand, "Cyrano de Bergerac"
Reply | Threaded
Open this post in threaded view
|

Re: [Patch] regtool: Add load/unload commands and --binary option

Brian Dessent
Igor Peshansky wrote:

> What if you want to redirect the hex dump to a file?  IMO, isatty() checks
> are only useful if the output won't change qualitatively on redirection
> (e.g., for coloring).  Otherwise, it's always better to use an explicit
> flag.

Good point.  Why don't we just emulate the behavior of 'cat' here?  If
isatty() is true and non-ascii characters are in the output, then prompt
first before possibly fubaring the user's terminal, otherwise just
output the raw data.

And just as 'cat' does not have any internal code for formatting binary
data as a hex dump, neither should regtool, since 'od' works perfectly
for that and already has the veritable kitchen sink of formatting
options.

Brian
Reply | Threaded
Open this post in threaded view
|

Re: [Patch] regtool: Add load/unload commands and --binary option

Corinna Vinschen-2
In reply to this post by Christian Franke
On Jan 25 21:58, Christian Franke wrote:
> Will send the snail mail with the legal stuff soon ;-)

Thanks, I'm looking forward.  Sorry for the hassle, but we still didn't
get legal permit for a simpler method.

Please be patient, this might take some time.


Corinna

--
Corinna Vinschen                  Please, send mails regarding Cygwin to
Cygwin Project Co-Leader          cygwin AT cygwin DOT com
Red Hat
Reply | Threaded
Open this post in threaded view
|

Re: [Patch] regtool: Add load/unload commands and --binary option

Corinna Vinschen-2
Hi Christian,

On Jan 26 10:19, Corinna Vinschen wrote:
> On Jan 25 21:58, Christian Franke wrote:
> > Will send the snail mail with the legal stuff soon ;-)
>
> Thanks, I'm looking forward.  Sorry for the hassle, but we still didn't
> get legal permit for a simpler method.
>
> Please be patient, this might take some time.

your assignment has finally arrived and is signed.  Do you have a
new version of your regtool patch available, after this discussion
took place?


Corinna

--
Corinna Vinschen                  Please, send mails regarding Cygwin to
Cygwin Project Co-Leader          cygwin AT cygwin DOT com
Red Hat
Reply | Threaded
Open this post in threaded view
|

Re: [Patch] regtool: Add load/unload commands and --binary option

Christian Franke
Hi Corrinna,

you wrote:

> Hi Christian,
>
> On Jan 26 10:19, Corinna Vinschen wrote:
>  
>> On Jan 25 21:58, Christian Franke wrote:
>>    
>>> Will send the snail mail with the legal stuff soon ;-)
>>>      
>> Thanks, I'm looking forward.  Sorry for the hassle, but we still didn't
>> get legal permit for a simpler method.
>>
>> Please be patient, this might take some time.
>>    
>
> your assignment has finally arrived and is signed.  Do you have a
> new version of your regtool patch available, after this discussion
> took place?
>  

No, sorry. Hope to find some time in about a week.

I'm still not sure how to handle binary registry values in a way most
useful inside of scripts.

Christian

Reply | Threaded
Open this post in threaded view
|

Re: [Patch] regtool: Add load/unload commands and --binary option

Corinna Vinschen-2
On Feb 13 20:43, Christian Franke wrote:
> you wrote:
> >your assignment has finally arrived and is signed.  Do you have a
> >new version of your regtool patch available, after this discussion
> >took place?
>
> No, sorry. Hope to find some time in about a week.
>
> I'm still not sure how to handle binary registry values in a way most
> useful inside of scripts.

By default, binary data should go as binary data over the pipe.  And
this is all what's needed, in theory, since tools like xxd exist.


Corinna

--
Corinna Vinschen                  Please, send mails regarding Cygwin to
Cygwin Project Co-Leader          cygwin AT cygwin DOT com
Red Hat
Reply | Threaded
Open this post in threaded view
|

Re: [Patch] regtool: Add load/unload commands and --binary option

Christian Franke
Attached is version 2 of the patch, including an update of utils.sgml

REG_BINARY can now be ether read as binary from stdin:

$ echo 0: 01 02 FE FF | xxd -r | regtool -b set KEY/BINVALUE -

$ regtool get KEY/BINVALUE | regtool -b set KEY/BINVALUE -

or specified as hex arguments:

$ regtool -b set KEY/BINVALUE 01 02 FE FF

$ x=$(regtool -b get KEY/BINVALUE)
$ regtool -b set KEY/BINVALUE $x


The load/unload actions are unchanged.

Christian

=====================

2006-03-01  Christian Franke <[hidden email]>

        * regtool.cc: Add actions load/unload and option -b, --binary.
        * utils.sgml (regtool): Document it.



Index: regtool.cc
===================================================================
RCS file: /cvs/src/src/winsup/utils/regtool.cc,v
retrieving revision 1.19
diff -u -r1.19 regtool.cc
--- regtool.cc 15 Feb 2006 10:57:17 -0000 1.19
+++ regtool.cc 1 Mar 2006 18:35:01 -0000
@@ -10,15 +10,17 @@
 
 #include <stdio.h>
 #include <stdlib.h>
+#include <errno.h>
 #include <ctype.h>
 #include <getopt.h>
 #include <windows.h>
+#include <sys/cygwin.h>
 
 #define DEFAULT_KEY_SEPARATOR '\\'
 
 enum
 {
-  KT_AUTO, KT_INT, KT_STRING, KT_EXPAND, KT_MULTI
+  KT_AUTO, KT_BINARY, KT_INT, KT_STRING, KT_EXPAND, KT_MULTI
 } key_type = KT_AUTO;
 
 char key_sep = DEFAULT_KEY_SEPARATOR;
@@ -32,6 +34,7 @@
 
 static struct option longopts[] =
 {
+  {"binary", no_argument, NULL, 'b' },
   {"expand-string", no_argument, NULL, 'e' },
   {"help", no_argument, NULL, 'h' },
   {"integer", no_argument, NULL, 'i' },
@@ -47,7 +50,7 @@
   {NULL, 0, NULL, 0}
 };
 
-static char opts[] = "ehiklmpqsvVK:";
+static char opts[] = "behiklmpqsvVK:";
 
 int listwhat = 0;
 int postfix = 0;
@@ -62,7 +65,7 @@
 usage (FILE *where = stderr)
 {
   fprintf (where, ""
-  "Usage: %s [OPTION] (add | check | get | list | remove | unset) KEY\n"
+  "Usage: %s [OPTION] (add|check|get|list|remove|unset|load|unload) KEY\n"
   "View or edit the Win32 registry\n"
   "\n"
   "", prog_name);
@@ -76,6 +79,8 @@
     " remove KEY                 remove KEY\n"
     " set KEY\\VALUE [data ...]   set VALUE\n"
     " unset KEY\\VALUE            removes VALUE from KEY\n"
+    " load KEY\\SUBKEY PATH       load hive from PATH into new SUBKEY\n"
+    " unload KEY\\SUBKEY          unload hive and remove SUBKEY\n"
     "\n");
   fprintf (where, ""
   "Options for 'list' Action:\n"
@@ -83,7 +88,11 @@
   " -l, --list           print only VALUEs\n"
   " -p, --postfix        like ls -p, appends '\\' postfix to KEY names\n"
   "\n"
+  "Options for 'get' Action:\n"
+  " -b, --binary         print REG_BINARY data as hex bytes\n"
+  "\n"
   "Options for 'set' Action:\n"
+  " -b, --binary         set type to REG_BINARY (hex args or '-')\n"
   " -e, --expand-string  set type to REG_EXPAND_SZ\n"
   " -i, --integer        set type to REG_DWORD\n"
   " -m, --multi-string   set type to REG_MULTI_SZ\n"
@@ -348,9 +357,30 @@
     key = base;
   else
     {
-      rv = RegOpenKeyEx (base, n, 0, access, &key);
-      if (rv != ERROR_SUCCESS)
- Fail (rv);
+      if (access)
+ {
+  rv = RegOpenKeyEx (base, n, 0, access, &key);
+  if (rv != ERROR_SUCCESS)
+    Fail (rv);
+ }
+      else if (argv[1])
+ {
+  char win32_path[MAX_PATH];
+  cygwin_conv_to_win32_path(argv[1], win32_path);
+  rv = RegLoadKey(base, n, win32_path);
+  if (rv != ERROR_SUCCESS)
+    Fail (rv);
+  if (verbose)
+    printf("key %s loaded from file %s\n", n, win32_path);
+ }
+      else
+ {
+  rv = RegUnLoadKey(base, n);
+  if (rv != ERROR_SUCCESS)
+    Fail (rv);
+  if (verbose)
+    printf("key %s unloaded\n", n);
+ }
     }
   //printf("key `%s' value `%s'\n", n, value);
 }
@@ -491,7 +521,7 @@
 {
   int i, n;
   DWORD v, rv;
-  char *a = argv[1], *data;
+  char *a = argv[1], *data = 0;
   find_key (2, KEY_ALL_ACCESS);
 
   if (key_type == KT_AUTO)
@@ -510,6 +540,43 @@
 
   switch (key_type)
     {
+    case KT_BINARY:
+      for (n = 0; argv[n+1]; n++)
+        ;
+      if (n == 1 && strcmp (argv[1], "-") == 0)
+ { /* read from stdin */
+  i = n = 0;
+  for (;;)
+    {
+      if (i <= n)
+ {
+  i = n + BUFSIZ;
+  data = (char *) realloc (data, i);
+ }
+      int r = fread (data+n, 1, i-n, stdin);
+      if (r <= 0)
+ break;
+      n += r;
+    }
+ }
+      else if (n > 0)
+ { /* parse hex from argv */
+  data = (char *) malloc (n);
+  for (i = 0; i < n; i++)
+    {
+      char *e;
+      errno = 0;
+      v = strtoul (argv[i+1], &e, 16);
+      if (errno || v > 0xff || *e)
+ {
+  fprintf (stderr, "Invalid hex constant `%s'\n", argv[i+1]);
+  exit (1);
+ }
+      data[i] = (char) v;
+    }
+ }
+      rv = RegSetValueEx (key, value, 0, REG_BINARY, (const BYTE *) data, n);
+      break;
     case KT_INT:
       v = strtoul (a, 0, 0);
       rv = RegSetValueEx (key, value, 0, REG_DWORD, (const BYTE *) &v,
@@ -542,6 +609,9 @@
       rv = ERROR_INVALID_CATEGORY;
       break;
     }
+
+  if (data)
+    free(data);
 
   if (rv != ERROR_SUCCESS)
     Fail (rv);
@@ -577,7 +647,14 @@
   switch (vtype)
     {
     case REG_BINARY:
-      fwrite (data, dsize, 1, stdout);
+      if (key_type == KT_BINARY) // hack
+ {
+  for (unsigned i = 0; i < dsize; i++)
+    printf ("%02x%c", (unsigned char)data[i],
+      (i < dsize-1 ? ' ' : '\n'));
+ }
+      else
+ fwrite (data, dsize, 1, stdout);
       break;
     case REG_DWORD:
       printf ("%lu\n", *(DWORD *) data);
@@ -610,6 +687,31 @@
   return 0;
 }
 
+int
+cmd_load ()
+{
+  if (!argv[1])
+    {
+      usage();
+      return 1;
+    }
+  find_key(1, 0);
+  return 0;
+}
+
+int
+cmd_unload ()
+{
+  if (argv[1])
+    {
+      usage();
+      return 1;
+    }
+  find_key(1, 0);
+  return 0;
+}
+
+
 struct
 {
   const char *name;
@@ -623,6 +725,8 @@
   {"set", cmd_set},
   {"unset", cmd_unset},
   {"get", cmd_get},
+  {"load", cmd_load},
+  {"unload", cmd_unload},
   {0, 0}
 };
 
@@ -642,6 +746,9 @@
   while ((g = getopt_long (argc, _argv, opts, longopts, NULL)) != EOF)
     switch (g)
  {
+ case 'b':
+  key_type = KT_BINARY;
+  break;
  case 'e':
   key_type = KT_EXPAND;
   break;
Index: utils.sgml
===================================================================
RCS file: /cvs/src/src/winsup/utils/utils.sgml,v
retrieving revision 1.58
diff -u -r1.58 utils.sgml
--- utils.sgml 16 Feb 2006 11:17:19 -0000 1.58
+++ utils.sgml 1 Mar 2006 18:35:09 -0000
@@ -1023,7 +1023,7 @@
 <sect2 id="regtool"><title>regtool</title>
 
 <screen>
-Usage: regtool.exe [OPTION] (add | check | get | list | remove | unset) KEY
+Usage: regtool [OPTION] (add|check|get|list|remove|unset|load|unload) KEY
 View or edit the Win32 registry
 
 Actions:
@@ -1034,13 +1034,19 @@
  remove KEY                 remove KEY
  set KEY\VALUE [data ...]   set VALUE
  unset KEY\VALUE            removes VALUE from KEY
+ load KEY\SUBKEY PATH       load hive from PATH into new SUBKEY
+ unload KEY\SUBKEY          unload hive and remove SUBKEY
 
 Options for 'list' Action:
  -k, --keys           print only KEYs
  -l, --list           print only VALUEs
  -p, --postfix        like ls -p, appends '\' postfix to KEY names
 
+Options for 'get' Action:
+ -b, --binary         print REG_BINARY data as hex bytes
+
 Options for 'set' Action:
+ -b, --binary         set type to REG_BINARY (hex args or '-')
  -e, --expand-string  set type to REG_EXPAND_SZ
  -i, --integer        set type to REG_DWORD
  -m, --multi-string   set type to REG_MULTI_SZ
@@ -1109,6 +1115,10 @@
 </para>
 
 <para>The <literal>set</literal> action sets a value within a key.
+<literal>-b</literal> means it's binary data (REG_BINARY).
+The binary values are specified as hex bytes in the argument list.
+If the argument is <literal>'-'</literal>, binary data is read
+from stdin instead.
 <literal>-e</literal> means it's an expanding string (REG_EXPAND_SZ)
 that contains embedded environment variables.  
 <literal>-i</literal> means the value is an integer (REG_DWORD).
@@ -1122,6 +1132,13 @@
 The <literal>unset</literal> action removes a value from a key.
 </para>
 
+<para>The <literal>load</literal> action adds a new subkey and loads
+the contents of a registry hive into it.
+The parent key must be HKEY_LOCAL_MACHINE or HKEY_USERS.
+The <literal>unload</literal> action unloads the file and removes
+the subkey.
+</para>
+
 <para>
 By default, the last "\" or "/" is assumed to be the separator between the
 key and the value.  You can use the <literal>-K</literal> option to provide

Reply | Threaded
Open this post in threaded view
|

Re: [Patch] regtool: Add load/unload commands and --binary option

Corinna Vinschen-2
On Mar  1 20:13, Christian Franke wrote:

> Attached is version 2 of the patch, including an update of utils.sgml
>
> REG_BINARY can now be ether read as binary from stdin:
>
> $ echo 0: 01 02 FE FF | xxd -r | regtool -b set KEY/BINVALUE -
>
> $ regtool get KEY/BINVALUE | regtool -b set KEY/BINVALUE -
>
> or specified as hex arguments:
>
> $ regtool -b set KEY/BINVALUE 01 02 FE FF
>
> $ x=$(regtool -b get KEY/BINVALUE)
> $ regtool -b set KEY/BINVALUE $x
>
>
> The load/unload actions are unchanged.
>
> Christian
>
> =====================
>
> 2006-03-01  Christian Franke <[hidden email]>
>
>        * regtool.cc: Add actions load/unload and option -b, --binary.
>        * utils.sgml (regtool): Document it.

Your patch looks pretty good to me, but I have a few minor nits.

First, be a bit more verbose in your ChangeLog entry.  Add explicit
entries for each changed function or global datastructure.

> retrieving revision 1.19
> diff -u -r1.19 regtool.cc

Could you please use diff -up?  It helps (at least me) navigating through
a patch.

> +  cygwin_conv_to_win32_path(argv[1], win32_path);

This happens a couple of times.  When you're calling functions, could
you please always add a space between the function name and the opening
parenthesis?

> +  rv = RegLoadKey(base, n, win32_path);

Ditto, etc.

>    //printf("key `%s' value `%s'\n", n, value);

Why is this printf commented out?  If it's not needed, please remove.

> @@ -577,7 +647,14 @@
>    switch (vtype)
>      {
>      case REG_BINARY:
> -      fwrite (data, dsize, 1, stdout);
> +      if (key_type == KT_BINARY) // hack

Hack?  Why hack?  Otherwise, please remove this comment.


Corinna

--
Corinna Vinschen                  Please, send mails regarding Cygwin to
Cygwin Project Co-Leader          cygwin AT cygwin DOT com
Red Hat
Reply | Threaded
Open this post in threaded view
|

Re: [Patch] regtool: Add load/unload commands and --binary option

Christian Franke
Corinna Vinschen wrote:
> ...
>  
>>    //printf("key `%s' value `%s'\n", n, value);
>>    
>
> Why is this printf commented out?  If it's not needed, please remove.
>  

cvs annotate regtool.cc
...
1.1 (cgf      17-Feb-00):     }
1.1 (cgf      17-Feb-00):   //printf("key `%s' value `%s'\n", n, value);
1.1 (cgf      17-Feb-00): }

Doing code-janitor work on historic code was not the intent of my patch ;-)
Uncommenting this line during testing was helpful, so I left it untouched.


>> @@ -577,7 +647,14 @@
>>    switch (vtype)
>>      {
>>      case REG_BINARY:
>> -      fwrite (data, dsize, 1, stdout);
>> +      if (key_type == KT_BINARY) // hack
>>    
>
> Hack?  Why hack?  Otherwise, please remove this comment.
>  
Because {re|mis}using "set" key_type for as a "get" option has been
called a hack many years ago:

1.1 (cgf      17-Feb-00):     case REG_EXPAND_SZ:
1.3 (cgf      10-Jan-01):       if (key_type == KT_EXPAND)    // hack
1.1 (cgf      17-Feb-00):     {


Attached is a new version of the patch.
Thanks to your help regarding SE_BACKUP_NAME, the "save" action is now
included.

Example: Backup system registry hives
(aka these ugly-forever-locked files in /windows/system32/config ;-)

#!/bin/sh
set -e
d="${1:-.}"

for k in SAM SECURITY SOFTWARE SYSTEM; do
  regtool save /HKLM/$k "$d/$k"
done
regtool save /HKU/.DEFAULT "$d/DEFAULT"
# End of script
####################

Hope the new features are helpful.

Christian


=====================

2006-03-02  Christian Franke <[hidden email]>

       * regtool.cc (options): Add 'binary'.
         (usage): Document 'load|unload|save' and '-b'.
         (find_key): Add 'options' parameter, add load/unload.
         (cmd_set): Add KT_BINARY case.
         (cmd_get): Add hex output in KT_BINARY case.
         (cmd_load): New function.
         (cmd_unload): New function.
         (set_privilege): New function.
         (cmd_save): New function.
         (commands): Add load, unload and save.
         (main): Add '-b'
       * utils.sgml (regtool): Document it.



Index: regtool.cc
===================================================================
RCS file: /cvs/src/src/winsup/utils/regtool.cc,v
retrieving revision 1.19
diff -u -p -r1.19 regtool.cc
--- regtool.cc 15 Feb 2006 10:57:17 -0000 1.19
+++ regtool.cc 2 Mar 2006 20:46:24 -0000
@@ -10,15 +10,17 @@ details. */
 
 #include <stdio.h>
 #include <stdlib.h>
+#include <errno.h>
 #include <ctype.h>
 #include <getopt.h>
 #include <windows.h>
+#include <sys/cygwin.h>
 
 #define DEFAULT_KEY_SEPARATOR '\\'
 
 enum
 {
-  KT_AUTO, KT_INT, KT_STRING, KT_EXPAND, KT_MULTI
+  KT_AUTO, KT_BINARY, KT_INT, KT_STRING, KT_EXPAND, KT_MULTI
 } key_type = KT_AUTO;
 
 char key_sep = DEFAULT_KEY_SEPARATOR;
@@ -32,6 +34,7 @@ static char *prog_name;
 
 static struct option longopts[] =
 {
+  {"binary", no_argument, NULL, 'b' },
   {"expand-string", no_argument, NULL, 'e' },
   {"help", no_argument, NULL, 'h' },
   {"integer", no_argument, NULL, 'i' },
@@ -47,7 +50,7 @@ static struct option longopts[] =
   {NULL, 0, NULL, 0}
 };
 
-static char opts[] = "ehiklmpqsvVK:";
+static char opts[] = "behiklmpqsvVK:";
 
 int listwhat = 0;
 int postfix = 0;
@@ -62,7 +65,7 @@ static void
 usage (FILE *where = stderr)
 {
   fprintf (where, ""
-  "Usage: %s [OPTION] (add | check | get | list | remove | unset) KEY\n"
+  "Usage: %s [OPTION] (add|check|get|list|remove|unset|load|unload|save) KEY\n"
   "View or edit the Win32 registry\n"
   "\n"
   "", prog_name);
@@ -76,6 +79,9 @@ usage (FILE *where = stderr)
     " remove KEY                 remove KEY\n"
     " set KEY\\VALUE [data ...]   set VALUE\n"
     " unset KEY\\VALUE            removes VALUE from KEY\n"
+    " load KEY\\SUBKEY PATH       load hive from PATH into new SUBKEY\n"
+    " unload KEY\\SUBKEY          unload hive and remove SUBKEY\n"
+    " save KEY\\SUBKEY PATH       save SUBKEY into new hive PATH\n"
     "\n");
   fprintf (where, ""
   "Options for 'list' Action:\n"
@@ -83,7 +89,11 @@ usage (FILE *where = stderr)
   " -l, --list           print only VALUEs\n"
   " -p, --postfix        like ls -p, appends '\\' postfix to KEY names\n"
   "\n"
+  "Options for 'get' Action:\n"
+  " -b, --binary         print REG_BINARY data as hex bytes\n"
+  "\n"
   "Options for 'set' Action:\n"
+  " -b, --binary         set type to REG_BINARY (hex args or '-')\n"
   " -e, --expand-string  set type to REG_EXPAND_SZ\n"
   " -i, --integer        set type to REG_DWORD\n"
   " -m, --multi-string   set type to REG_MULTI_SZ\n"
@@ -265,7 +275,7 @@ translate (char *key)
 }
 
 void
-find_key (int howmanyparts, REGSAM access)
+find_key (int howmanyparts, REGSAM access, int option = 0)
 {
   HKEY base;
   int rv;
@@ -348,9 +358,44 @@ find_key (int howmanyparts, REGSAM acces
     key = base;
   else
     {
-      rv = RegOpenKeyEx (base, n, 0, access, &key);
-      if (rv != ERROR_SUCCESS)
- Fail (rv);
+      if (access)
+ {
+  rv = RegOpenKeyEx (base, n, 0, access, &key);
+  if (option && (rv == ERROR_SUCCESS || rv == ERROR_ACCESS_DENIED))
+    {
+      /* reopen with desired option due to missing option support in RegOpenKeyE */
+      /* FIXME: may create the key in rare cases (e.g. access denied in parent) */
+      HKEY key2;
+      if (RegCreateKeyEx (base, n, 0, NULL, option, access, NULL, &key2, NULL)
+  == ERROR_SUCCESS)
+        {
+  if (rv == ERROR_SUCCESS)
+    RegCloseKey (key);
+  key = key2;
+  rv = ERROR_SUCCESS;
+        }
+    }
+  if (rv != ERROR_SUCCESS)
+    Fail (rv);
+ }
+      else if (argv[1])
+ {
+  char win32_path[MAX_PATH];
+  cygwin_conv_to_win32_path (argv[1], win32_path);
+  rv = RegLoadKey (base, n, win32_path);
+  if (rv != ERROR_SUCCESS)
+    Fail (rv);
+  if (verbose)
+    printf ("key %s loaded from file %s\n", n, win32_path);
+ }
+      else
+ {
+  rv = RegUnLoadKey (base, n);
+  if (rv != ERROR_SUCCESS)
+    Fail (rv);
+  if (verbose)
+    printf ("key %s unloaded\n", n);
+ }
     }
   //printf("key `%s' value `%s'\n", n, value);
 }
@@ -491,7 +536,7 @@ cmd_set ()
 {
   int i, n;
   DWORD v, rv;
-  char *a = argv[1], *data;
+  char *a = argv[1], *data = 0;
   find_key (2, KEY_ALL_ACCESS);
 
   if (key_type == KT_AUTO)
@@ -510,6 +555,43 @@ cmd_set ()
 
   switch (key_type)
     {
+    case KT_BINARY:
+      for (n = 0; argv[n+1]; n++)
+        ;
+      if (n == 1 && strcmp (argv[1], "-") == 0)
+ { /* read from stdin */
+  i = n = 0;
+  for (;;)
+    {
+      if (i <= n)
+ {
+  i = n + BUFSIZ;
+  data = (char *) realloc (data, i);
+ }
+      int r = fread (data+n, 1, i-n, stdin);
+      if (r <= 0)
+ break;
+      n += r;
+    }
+ }
+      else if (n > 0)
+ { /* parse hex from argv */
+  data = (char *) malloc (n);
+  for (i = 0; i < n; i++)
+    {
+      char *e;
+      errno = 0;
+      v = strtoul (argv[i+1], &e, 16);
+      if (errno || v > 0xff || *e)
+ {
+  fprintf (stderr, "Invalid hex constant `%s'\n", argv[i+1]);
+  exit (1);
+ }
+      data[i] = (char) v;
+    }
+ }
+      rv = RegSetValueEx (key, value, 0, REG_BINARY, (const BYTE *) data, n);
+      break;
     case KT_INT:
       v = strtoul (a, 0, 0);
       rv = RegSetValueEx (key, value, 0, REG_DWORD, (const BYTE *) &v,
@@ -542,6 +624,9 @@ cmd_set ()
       rv = ERROR_INVALID_CATEGORY;
       break;
     }
+
+  if (data)
+    free(data);
 
   if (rv != ERROR_SUCCESS)
     Fail (rv);
@@ -577,7 +662,14 @@ cmd_get ()
   switch (vtype)
     {
     case REG_BINARY:
-      fwrite (data, dsize, 1, stdout);
+      if (key_type == KT_BINARY) // hack
+ {
+  for (unsigned i = 0; i < dsize; i++)
+    printf ("%02x%c", (unsigned char)data[i],
+      (i < dsize-1 ? ' ' : '\n'));
+ }
+      else
+ fwrite (data, dsize, 1, stdout);
       break;
     case REG_DWORD:
       printf ("%lu\n", *(DWORD *) data);
@@ -610,6 +702,72 @@ cmd_get ()
   return 0;
 }
 
+int
+cmd_load ()
+{
+  if (!argv[1])
+    {
+      usage ();
+      return 1;
+    }
+  find_key (1, 0);
+  return 0;
+}
+
+int
+cmd_unload ()
+{
+  if (argv[1])
+    {
+      usage ();
+      return 1;
+    }
+  find_key (1, 0);
+  return 0;
+}
+
+DWORD
+set_privilege (const char * name)
+{
+  TOKEN_PRIVILEGES tp;
+  if (!LookupPrivilegeValue (NULL, name, &tp.Privileges[0].Luid))
+    return GetLastError ();
+  tp.PrivilegeCount = 1;
+  tp.Privileges[0].Attributes = SE_PRIVILEGE_ENABLED;
+  HANDLE t;
+  /* OpenProcessToken does not work here, because main thread has its own
+     impersonation token */
+  if (!OpenThreadToken (GetCurrentThread (), TOKEN_ADJUST_PRIVILEGES, FALSE, &t))
+    return GetLastError ();
+  AdjustTokenPrivileges (t, FALSE, &tp, 0, NULL, NULL);
+  DWORD rv = GetLastError ();
+  CloseHandle (t);
+  return rv;
+}
+
+int
+cmd_save ()
+{
+  if (!argv[1])
+    {
+      usage ();
+      return 1;
+    }
+  /* try to set SeBackupPrivilege, let RegSaveKey report the error */
+  set_privilege (SE_BACKUP_NAME);
+  /* REG_OPTION_BACKUP_RESTORE is necessary to save /HKLM/SECURITY */
+  find_key (1, KEY_QUERY_VALUE, REG_OPTION_BACKUP_RESTORE);
+  char win32_path[MAX_PATH];
+  cygwin_conv_to_win32_path (argv[1], win32_path);
+  DWORD rv = RegSaveKey (key, win32_path, NULL);
+  if (rv != ERROR_SUCCESS)
+    Fail (rv);
+  if (verbose)
+    printf ("key saved to %s\n", win32_path);
+  return 0;
+}
+
+
 struct
 {
   const char *name;
@@ -623,6 +781,9 @@ struct
   {"set", cmd_set},
   {"unset", cmd_unset},
   {"get", cmd_get},
+  {"load", cmd_load},
+  {"unload", cmd_unload},
+  {"save", cmd_save},
   {0, 0}
 };
 
@@ -642,6 +803,9 @@ main (int argc, char **_argv)
   while ((g = getopt_long (argc, _argv, opts, longopts, NULL)) != EOF)
     switch (g)
  {
+ case 'b':
+  key_type = KT_BINARY;
+  break;
  case 'e':
   key_type = KT_EXPAND;
   break;
Index: utils.sgml
===================================================================
RCS file: /cvs/src/src/winsup/utils/utils.sgml,v
retrieving revision 1.58
diff -u -p -r1.58 utils.sgml
--- utils.sgml 16 Feb 2006 11:17:19 -0000 1.58
+++ utils.sgml 2 Mar 2006 20:46:30 -0000
@@ -1023,7 +1023,7 @@ option.
 <sect2 id="regtool"><title>regtool</title>
 
 <screen>
-Usage: regtool.exe [OPTION] (add | check | get | list | remove | unset) KEY
+Usage: regtool [OPTION] (add|check|get|list|remove|unset|load|unload|save) KEY
 View or edit the Win32 registry
 
 Actions:
@@ -1034,13 +1034,20 @@ Actions:
  remove KEY                 remove KEY
  set KEY\VALUE [data ...]   set VALUE
  unset KEY\VALUE            removes VALUE from KEY
+ load KEY\SUBKEY PATH       load hive from PATH into new SUBKEY
+ unload KEY\SUBKEY          unload hive and remove SUBKEY
+ save KEY\SUBKEY PATH       save SUBKEY into new hive PATH
 
 Options for 'list' Action:
  -k, --keys           print only KEYs
  -l, --list           print only VALUEs
  -p, --postfix        like ls -p, appends '\' postfix to KEY names
 
+Options for 'get' Action:
+ -b, --binary         print REG_BINARY data as hex bytes
+
 Options for 'set' Action:
+ -b, --binary         set type to REG_BINARY (hex args or '-')
  -e, --expand-string  set type to REG_EXPAND_SZ
  -i, --integer        set type to REG_DWORD
  -m, --multi-string   set type to REG_MULTI_SZ
@@ -1109,6 +1116,10 @@ accidentally removing too much.  
 </para>
 
 <para>The <literal>set</literal> action sets a value within a key.
+<literal>-b</literal> means it's binary data (REG_BINARY).
+The binary values are specified as hex bytes in the argument list.
+If the argument is <literal>'-'</literal>, binary data is read
+from stdin instead.
 <literal>-e</literal> means it's an expanding string (REG_EXPAND_SZ)
 that contains embedded environment variables.  
 <literal>-i</literal> means the value is an integer (REG_DWORD).
@@ -1122,6 +1133,17 @@ a regular string.
 The <literal>unset</literal> action removes a value from a key.
 </para>
 
+<para>The <literal>load</literal> action adds a new subkey and loads
+the contents of a registry hive into it.
+The parent key must be HKEY_LOCAL_MACHINE or HKEY_USERS.
+The <literal>unload</literal> action unloads the file and removes
+the subkey.
+</para>
+
+<para>The <literal>save</literal> action saves a subkey into a
+registry hive.
+</para>
+
 <para>
 By default, the last "\" or "/" is assumed to be the separator between the
 key and the value.  You can use the <literal>-K</literal> option to provide

Reply | Threaded
Open this post in threaded view
|

Re: [Patch] regtool: Add load/unload commands and --binary option

Corinna Vinschen-2
On Mar  2 21:59, Christian Franke wrote:

> Corinna Vinschen wrote:
> >...
> >  
> >>   //printf("key `%s' value `%s'\n", n, value);
> >>    
> >
> >Why is this printf commented out?  If it's not needed, please remove.
> >  
>
> cvs annotate regtool.cc
> ...
> 1.1 (cgf      17-Feb-00):     }
> 1.1 (cgf      17-Feb-00):   //printf("key `%s' value `%s'\n", n, value);
> 1.1 (cgf      17-Feb-00): }
>
> Doing code-janitor work on historic code was not the intent of my patch ;-)

Urgh, sorry about that.  While scanning your patch I missed that this
printf isn't new but already in the code.

> >>@@ -577,7 +647,14 @@
> >>   switch (vtype)
> >>     {
> >>     case REG_BINARY:
> >>-      fwrite (data, dsize, 1, stdout);
> >>+      if (key_type == KT_BINARY) // hack
> >>    
> >
> >Hack?  Why hack?  Otherwise, please remove this comment.
> >  
>
> Because {re|mis}using "set" key_type for as a "get" option has been
> called a hack many years ago:
>
> 1.1 (cgf      17-Feb-00):     case REG_EXPAND_SZ:
> 1.3 (cgf      10-Jan-01):       if (key_type == KT_EXPAND)    // hack
> 1.1 (cgf      17-Feb-00):     {

Well, I can't see a hack in what you're using KT_BINARY here.  I removed
the comment from your patch.

> Attached is a new version of the patch.
> Thanks to your help regarding SE_BACKUP_NAME, the "save" action is now
> included.

Cool.

> 2006-03-02  Christian Franke <[hidden email]>
>
>       * regtool.cc (options): Add 'binary'.
>         (usage): Document 'load|unload|save' and '-b'.
>         (find_key): Add 'options' parameter, add load/unload.
>         (cmd_set): Add KT_BINARY case.
>         (cmd_get): Add hex output in KT_BINARY case.
>         (cmd_load): New function.
>         (cmd_unload): New function.
>         (set_privilege): New function.
>         (cmd_save): New function.
>         (commands): Add load, unload and save.
>         (main): Add '-b'
>       * utils.sgml (regtool): Document it.

I applied the patch.  I just had to reformat your ChangeLog slightly
(a TAB before all lines, no extra indentation for lines which don't
start with a '*').

Btw., since you seem to be interested in hacking the registry...  would
you also be interested to introduce registry write access below
/proc/registry inside of the Cygwin DLL?  That would be extra cool.
I'm not quite sure how to handle the mapping from file types to
registry key types, but there might be some simple way which I'm just
too blind to see.


Thanks,
Corinna

--
Corinna Vinschen                  Please, send mails regarding Cygwin to
Cygwin Project Co-Leader          cygwin AT cygwin DOT com
Red Hat
Reply | Threaded
Open this post in threaded view
|

RE: [Patch] regtool: Add load/unload commands and --binary option

Dave Korn
On 03 March 2006 09:46, Corinna Vinschen wrote:

>
> Btw., since you seem to be interested in hacking the registry...  would
> you also be interested to introduce registry write access below
> /proc/registry inside of the Cygwin DLL?  That would be extra cool.
> I'm not quite sure how to handle the mapping from file types to
> registry key types, but there might be some simple way which I'm just
> too blind to see.


  Hey, how about using pseudo filename-extensions on the pseudo-files that
represent registry keys?

  i.e

$  echo "Foo" >/proc/registry/HKEY_CURRENT_USER/Software/App/Key/ValueName.sz
creates /proc/registry/HKEY_CURRENT_USER/Software/App/Key/ValueName, type
REG_SZ, content "Foo<NUL>"

$  echo "%WINDIR%"
>/proc/registry/HKEY_CURRENT_USER/Software/App/Key/ValueName.xsz
creates /proc/registry/HKEY_CURRENT_USER/Software/App/Key/ValueName as
REG_EXPAND_SZ

$  echo "23"
>/proc/registry/HKEY_CURRENT_USER/Software/App/Key/ValueName.dword
$  echo "0x17"
>/proc/registry/HKEY_CURRENT_USER/Software/App/Key/ValueName.dword

$  dd bs=1024 count=3 if=/dev/random
of=/proc/registry/HKEY_CURRENT_USER/Software/App/Key/ValueName.bin

$  touch /proc/registry/HKEY_CURRENT_USER/Software/App/Key/ValueName.none

etc etc ?  (We might even want a $CYGWIN option to make the extension show up
in dir listings, but it wouldn't be backwardly-compatible to do so in
general).

  Hmm, and how about for MULTI_SZ taking account of the open mode?

$ echo "String1"
>/proc/registry/HKEY_CURRENT_USER/Software/App/Key/ValueName.msz
$ echo "String2"
>>/proc/registry/HKEY_CURRENT_USER/Software/App/Key/ValueName.msz
$ echo "String3"
>>/proc/registry/HKEY_CURRENT_USER/Software/App/Key/ValueName.msz
$ echo "String4"
>>/proc/registry/HKEY_CURRENT_USER/Software/App/Key/ValueName.msz
$ od -c < /proc/registry/HKEY_CURRENT_USER/Software/App/Key/ValueName.msz
  String1\0String2\0String3\0String4\0\0


    cheers,
      DaveK
--
Can't think of a witty .sigline today....

Reply | Threaded
Open this post in threaded view
|

Re: [Patch] regtool: Add load/unload commands and --binary option

Corinna Vinschen-2
On Mar  3 13:12, Dave Korn wrote:

> On 03 March 2006 09:46, Corinna Vinschen wrote:
>
> >
> > Btw., since you seem to be interested in hacking the registry...  would
> > you also be interested to introduce registry write access below
> > /proc/registry inside of the Cygwin DLL?  That would be extra cool.
> > I'm not quite sure how to handle the mapping from file types to
> > registry key types, but there might be some simple way which I'm just
> > too blind to see.
>
>
>   Hey, how about using pseudo filename-extensions on the pseudo-files that
> represent registry keys?
>
>   i.e
>
> $  echo "Foo" >/proc/registry/HKEY_CURRENT_USER/Software/App/Key/ValueName.sz
> creates /proc/registry/HKEY_CURRENT_USER/Software/App/Key/ValueName, type
> REG_SZ, content "Foo<NUL>"
>
> $  echo "%WINDIR%"
> >/proc/registry/HKEY_CURRENT_USER/Software/App/Key/ValueName.xsz
> creates /proc/registry/HKEY_CURRENT_USER/Software/App/Key/ValueName as
> REG_EXPAND_SZ
>
> $  echo "23"
> >/proc/registry/HKEY_CURRENT_USER/Software/App/Key/ValueName.dword
> $  echo "0x17"
> >/proc/registry/HKEY_CURRENT_USER/Software/App/Key/ValueName.dword
>
> $  dd bs=1024 count=3 if=/dev/random
> of=/proc/registry/HKEY_CURRENT_USER/Software/App/Key/ValueName.bin
>
> $  touch /proc/registry/HKEY_CURRENT_USER/Software/App/Key/ValueName.none
>
> etc etc ?  (We might even want a $CYGWIN option to make the extension show up
> in dir listings, but it wouldn't be backwardly-compatible to do so in
> general).
>
>   Hmm, and how about for MULTI_SZ taking account of the open mode?
>
> $ echo "String1"
> >/proc/registry/HKEY_CURRENT_USER/Software/App/Key/ValueName.msz
> $ echo "String2"
> >>/proc/registry/HKEY_CURRENT_USER/Software/App/Key/ValueName.msz
> $ echo "String3"
> >>/proc/registry/HKEY_CURRENT_USER/Software/App/Key/ValueName.msz
> $ echo "String4"
> >>/proc/registry/HKEY_CURRENT_USER/Software/App/Key/ValueName.msz
> $ od -c < /proc/registry/HKEY_CURRENT_USER/Software/App/Key/ValueName.msz
>   String1\0String2\0String3\0String4\0\0

That's actually an interesting idea.  I was always thinking along
the lines of using POSIX file types (plain,socket,pipe,...).

However, file suffixes is something we're already suffering from
a lot (it's not by chance that SUFFix and SUFFer are so similar, IMHO).

What if a key "foo.sz" really exists and somebody wants to create
a registry key "foo"?  When reading "foo", which file is meant?
What's the order of checking suffixes?

When somebody writes to a key "foo", what's the default suffix,
er..., key type?  Or does that fail with an error message?


Corinna

--
Corinna Vinschen                  Please, send mails regarding Cygwin to
Cygwin Project Co-Leader          cygwin AT cygwin DOT com
Red Hat
Reply | Threaded
Open this post in threaded view
|

RE: [Patch] regtool: Add load/unload commands and --binary option

Dave Korn

> That's actually an interesting idea.  I was always thinking along
> the lines of using POSIX file types (plain,socket,pipe,...).
>
> However, file suffixes is something we're already suffering from
> a lot (it's not by chance that SUFFix and SUFFer are so similar, IMHO).

  Heh, yeh, who could ever forget the .exe/.lnk/.exe.lnk/.lnk.exe troubles?
However, we're in a special situation here, it's not really a dir tree and the
things in it aren't really files, and we may be able to get away with it.  I
posted the idea so that others could see if it works or if they can see
problems with the approach.

> What if a key "foo.sz" really exists and somebody wants to create
> a registry key "foo"?

  No problem.  If you want to create foo, you write to "foo.sz".  If you want
to create foo.sz, you have to write to "foo.sz.sz".  Unless of course foo.sz
is a dword, in which case you'd write to "foo.sz.dw", etc etc.

> When reading "foo", which file is meant?

  There can only be one at a time, because in the registry there can only be
one value with the name foo, regardless of what type it has.

> What's the order of checking suffixes?

  I'm proposing that the suffix is only used when creating or writing to the
file, to determine the type, but the suffix is stripped off for generating the
actual name, and is not shown in dir listings, and is not required to open the
file for read.
 
> When somebody writes to a key "foo", what's the default suffix,
> er..., key type?  Or does that fail with an error message?

  Either; I haven't a strong opinion on the matter.


    cheers,
      DaveK
--
Can't think of a witty .sigline today....

12