~ubuntu-branches/ubuntu/karmic/x11-xserver-utils/karmic

« back to all changes in this revision

Viewing changes to debian/patches/01_sessreg_implement_hostname_hashing.diff

  • Committer: Bazaar Package Importer
  • Author(s): Brice Goglin, Julien Cristau, Brice Goglin
  • Date: 2007-08-17 09:58:34 UTC
  • Revision ID: james.westby@ubuntu.com-20070817095834-ywge2nyzj1s3rqnd
Tags: 7.3+1
[ Julien Cristau ]
* iceauth 1.0.2.
  + removes blank line in the manpage (closes: #25285).
* xmodmap 1.0.3.
  + manpage updated to state that -pm is the default (closes: #236198)
* xgamma 1.0.2.
  + the manpage now explains how to print the gamma value more clearly
    (closes: #296021).
* xsetroot 1.0.2.
* xrdb 1.0.4.
  + fixes manpage typo (closes: #276286).
* Add upstream URL to debian/copyright, and update it from xgamma's COPYING
  file.

[ Brice Goglin ]
* Add menu entries for xrefresh and xvidtune.
* sessreg 1.0.3.
* xset 1.0.3.
* Add myself to Uploaders, and remove Branden with his permission.

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
$Id: 085_sessreg_implement_hostname_hashing.diff 689 2005-10-19 22:11:30Z dnusinow $
 
2
 
 
3
The sessreg program assumes that hostnames in utmp entries are unique in
 
4
the last four characters.  When two entries are "test:0" and "fist:0", for
 
5
example, this assumption fails.
 
6
 
 
7
Rectify this problem by hashing the entire hostname field from the utmp
 
8
entry, so that we can tell unlike hostnames apart with much greater
 
9
reliability.  There is still a possiblility of one hash collision in 2^32.
 
10
 
 
11
This patch by Maximiliano Curia and Damián Viano, using a public-domain
 
12
hash algorithm by Bob Jenkins.
 
13
 
 
14
Not submitted to XFree86.
 
15
 
 
16
Index: sessreg/sessreg.c
 
17
===================================================================
 
18
--- sessreg/sessreg.c.orig      2005-10-18 19:45:25.000000000 -0400
 
19
+++ sessreg/sessreg.c   2005-10-18 21:36:02.000000000 -0400
 
20
@@ -182,6 +182,18 @@
 
21
                       const char *host, Time_t date, int addp);
 
22
 #endif
 
23
 
 
24
+#ifdef SYSV
 
25
+/* used for hashing ut_id */
 
26
+typedef  unsigned long  int  ub4;   /* unsigned 4-byte quantities */
 
27
+typedef  unsigned       char ub1;   /* unsigned 1-byte quantities */
 
28
+
 
29
+#define hashsize(n) ((ub4)1<<(n))
 
30
+#define hashmask(n) (hashsize(n)-1)
 
31
+
 
32
+ub4 hash(register ub1 *k, register ub4 length, register ub4 initval);
 
33
+
 
34
+#endif
 
35
+
 
36
 int    wflag, uflag, lflag;
 
37
 char   *wtmp_file, *utmp_file, *line;
 
38
 #ifdef USE_UTMPX
 
39
@@ -469,21 +481,23 @@
 
40
                bzero (u->ut_name, sizeof (u->ut_name));
 
41
 #ifdef SYSV
 
42
        if (line) {
 
43
-               int     i;
 
44
                /*
 
45
-                * this is a bit crufty, but
 
46
-                * follows the apparent conventions in
 
47
-                * the ttys file.  ut_id is only 4 bytes
 
48
-                * long, and the last 4 bytes of the line
 
49
-                * name are written into it, left justified.
 
50
+                * The ut_id is 4 bytes long.  We make a hash of the line
 
51
+                * received, preceding it by ":" to prevent clashing with
 
52
+                * other ut_ids.
 
53
                 */
 
54
-               i = strlen (line);
 
55
-               if (i >= sizeof (u->ut_id))
 
56
-                       i -= sizeof (u->ut_id);
 
57
-               else
 
58
-                       i = 0;
 
59
-               (void) strncpy (u->ut_id, line + i, sizeof (u->ut_id));
 
60
+               ub4 h;
 
61
+               u->ut_id[0]=':';
 
62
+               h = hash(line, strlen(line),0x9e3779b9);
 
63
+               h = (h & hashmask((sizeof(u->ut_id)-sizeof(char))*8));
 
64
+               (void) strncpy (u->ut_id + 1,(char *) &h,  sizeof (u->ut_id)-sizeof(char));
 
65
        } else
 
66
+               /*
 
67
+                * From utmp(5):
 
68
+                * Clearing ut_id may result in race conditions leading to corrupted
 
69
+                * utmp entries and and potential security holes.
 
70
+                */
 
71
+               /* TODO: CHECK this  */
 
72
                bzero (u->ut_id, sizeof (u->ut_id));
 
73
        if (addp) {
 
74
                u->ut_pid = getppid ();
 
75
@@ -722,3 +736,129 @@
 
76
                return freeslot;
 
77
 }
 
78
 #endif
 
79
+
 
80
+#ifdef SYSV
 
81
+/*
 
82
+--------------------------------------------------------------------
 
83
+mix -- mix 3 32-bit values reversibly.
 
84
+For every delta with one or two bits set, and the deltas of all three
 
85
+  high bits or all three low bits, whether the original value of a,b,c
 
86
+  is almost all zero or is uniformly distributed,
 
87
+* If mix() is run forward or backward, at least 32 bits in a,b,c
 
88
+  have at least 1/4 probability of changing.
 
89
+* If mix() is run forward, every bit of c will change between 1/3 and
 
90
+  2/3 of the time.  (Well, 22/100 and 78/100 for some 2-bit deltas.)
 
91
+mix() was built out of 36 single-cycle latency instructions in a
 
92
+  structure that could supported 2x parallelism, like so:
 
93
+      a -= b;
 
94
+      a -= c; x = (c>>13);
 
95
+      b -= c; a ^= x;
 
96
+      b -= a; x = (a<<8);
 
97
+      c -= a; b ^= x;
 
98
+      c -= b; x = (b>>13);
 
99
+      ...
 
100
+  Unfortunately, superscalar Pentiums and Sparcs can't take advantage
 
101
+  of that parallelism.  They've also turned some of those single-cycle
 
102
+  latency instructions into multi-cycle latency instructions.  Still,
 
103
+  this is the fastest good hash I could find.  There were about 2^^68
 
104
+  to choose from.  I only looked at a billion or so.
 
105
+--------------------------------------------------------------------
 
106
+*/
 
107
+#define mix(a,b,c) \
 
108
+{ \
 
109
+  a -= b; a -= c; a ^= (c>>13); \
 
110
+  b -= c; b -= a; b ^= (a<<8); \
 
111
+  c -= a; c -= b; c ^= (b>>13); \
 
112
+  a -= b; a -= c; a ^= (c>>12);  \
 
113
+  b -= c; b -= a; b ^= (a<<16); \
 
114
+  c -= a; c -= b; c ^= (b>>5); \
 
115
+  a -= b; a -= c; a ^= (c>>3);  \
 
116
+  b -= c; b -= a; b ^= (a<<10); \
 
117
+  c -= a; c -= b; c ^= (b>>15); \
 
118
+}
 
119
+
 
120
+/*
 
121
+--------------------------------------------------------------------
 
122
+hash() -- hash a variable-length key into a 32-bit value
 
123
+  k       : the key (the unaligned variable-length array of bytes)
 
124
+  len     : the length of the key, counting by bytes
 
125
+  initval : can be any 4-byte value
 
126
+Returns a 32-bit value.  Every bit of the key affects every bit of
 
127
+the return value.  Every 1-bit and 2-bit delta achieves avalanche.
 
128
+About 6*len+35 instructions.
 
129
+
 
130
+The best hash table sizes are powers of 2.  There is no need to do
 
131
+mod a prime (mod is sooo slow!).  If you need less than 32 bits,
 
132
+use a bitmask.  For example, if you need only 10 bits, do
 
133
+  h = (h & hashmask(10));
 
134
+In which case, the hash table should have hashsize(10) elements.
 
135
+
 
136
+If you are hashing n strings (ub1 **)k, do it like this:
 
137
+  for (i=0, h=0; i<n; ++i) h = hash( k[i], len[i], h);
 
138
+
 
139
+By Bob Jenkins, 1996.  bob_jenkins@burtleburtle.net.  You may use this
 
140
+code any way you wish, private, educational, or commercial.  It's free.
 
141
+
 
142
+[On 27 May 2004, Bob Jenkins further clarified the above statement.
 
143
+
 
144
+  From: Bob Jenkins <bob_jenkins@burtleburtle.net>
 
145
+  Date: Thu, 27 May 2004 22:33:06 -0700
 
146
+  To: Margarita Manterola <marga@marga.com.ar>
 
147
+  Subject: Re: Hash function
 
148
+
 
149
+  The algorithm is public domain.  I ask that I be referenced as the
 
150
+  source of the algorithm, but I can't enforce that, since being public
 
151
+  domain means I've reserved no rights at all.
 
152
+
 
153
+-- Branden Robinson, 2004-06-06]
 
154
+
 
155
+See http://burtleburtle.net/bob/hash/evahash.html
 
156
+Use for hash table lookup, or anything where one collision in 2^^32 is
 
157
+acceptable.  Do NOT use for cryptographic purposes.
 
158
+--------------------------------------------------------------------
 
159
+*/
 
160
+
 
161
+ub4
 
162
+hash(register ub1 *k, register ub4 length, register ub4 initval)
 
163
+{
 
164
+   register ub4 a,b,c,len;
 
165
+
 
166
+   /* Set up the internal state */
 
167
+   len = length;
 
168
+   a = b = 0x9e3779b9;  /* the golden ratio; an arbitrary value */
 
169
+   c = initval;         /* the previous hash value */
 
170
+
 
171
+   /*---------------------------------------- handle most of the key */
 
172
+   while (len >= 12)
 
173
+   {
 
174
+      a += (k[0] +((ub4)k[1]<<8) +((ub4)k[2]<<16) +((ub4)k[3]<<24));
 
175
+      b += (k[4] +((ub4)k[5]<<8) +((ub4)k[6]<<16) +((ub4)k[7]<<24));
 
176
+      c += (k[8] +((ub4)k[9]<<8) +((ub4)k[10]<<16)+((ub4)k[11]<<24));
 
177
+      mix(a,b,c);
 
178
+      k += 12; len -= 12;
 
179
+   }
 
180
+
 
181
+   /*------------------------------------- handle the last 11 bytes */
 
182
+   c += length;
 
183
+   switch(len)              /* all the case statements fall through */
 
184
+   {
 
185
+   case 11: c+=((ub4)k[10]<<24);
 
186
+   case 10: c+=((ub4)k[9]<<16);
 
187
+   case 9 : c+=((ub4)k[8]<<8);
 
188
+      /* the first byte of c is reserved for the length */
 
189
+   case 8 : b+=((ub4)k[7]<<24);
 
190
+   case 7 : b+=((ub4)k[6]<<16);
 
191
+   case 6 : b+=((ub4)k[5]<<8);
 
192
+   case 5 : b+=k[4];
 
193
+   case 4 : a+=((ub4)k[3]<<24);
 
194
+   case 3 : a+=((ub4)k[2]<<16);
 
195
+   case 2 : a+=((ub4)k[1]<<8);
 
196
+   case 1 : a+=k[0];
 
197
+     /* case 0: nothing left to add */
 
198
+   }
 
199
+   mix(a,b,c);
 
200
+   /*-------------------------------------------- report the result */
 
201
+   return c;
 
202
+}
 
203
+
 
204
+#endif