Merge from vendor branch GDB:
[dragonfly.git] / contrib / ipfilter / kmem.c
1 /*
2  * Copyright (C) 1993-2002 by Darren Reed.
3  *
4  * See the IPFILTER.LICENCE file for details on licencing.
5  */
6 /*
7  * kmemcpy() - copies n bytes from kernel memory into user buffer.
8  * returns 0 on success, -1 on error.
9  */
10
11 #if defined(__sgi) && (IRIX > 602)
12 # include <sys/ptimers.h>
13 #endif
14 #include <stdio.h>
15 #include <sys/param.h>
16 #include <sys/types.h>
17 #include <unistd.h>
18 #include <string.h>
19 #include <fcntl.h>
20 #include <stdlib.h>
21 #include <sys/file.h>
22 #ifndef __sgi
23 #include <kvm.h>
24 #endif
25 #include <fcntl.h>
26 #include <sys/socket.h>
27 #include <sys/ioctl.h>
28 #include <netinet/in.h>
29 #include <arpa/inet.h>
30 #include <netinet/in_systm.h>
31 #include <netinet/ip.h>
32 #include <net/if.h>
33 #if __FreeBSD_version >= 300000 || defined(__DragonFly__)
34 # include <net/if_var.h>
35 #endif
36
37 #include "kmem.h"
38 #include "netinet/ip_compat.h"
39 #include "netinet/ip_fil.h"
40 #include "ipf.h"
41
42
43 #ifndef __STDC__
44 # define        const
45 #endif
46
47 #if !defined(lint)
48 static const char sccsid[] = "@(#)kmem.c        1.4 1/12/96 (C) 1992 Darren Reed";
49 static const char rcsid[] = "@(#)$Id: kmem.c,v 2.2.2.18 2003/11/09 17:22:22 darrenr Exp $";
50 #endif
51
52 #ifdef  __sgi
53 typedef int     kvm_t;
54
55 static  int     kvm_fd = -1;
56 static  char    *kvm_errstr = NULL;
57
58 kvm_t *kvm_open(kernel, core, swap, mode, errstr)
59 char *kernel, *core, *swap;
60 int mode;
61 char *errstr;
62 {
63         kvm_errstr = errstr;
64
65         if (core == NULL)
66                 core = "/dev/kmem";
67         kvm_fd = open(core, mode);
68         return (kvm_fd >= 0) ? (kvm_t *)&kvm_fd : NULL;
69 }
70
71 int kvm_read(kvm, pos, buffer, size)
72 kvm_t *kvm;
73 u_long pos;
74 char *buffer;
75 size_t size;
76 {
77         size_t left;
78         char *bufp;
79         int r;
80
81         if (lseek(*kvm, pos, 0) == -1) {
82                 if (kvm_errstr != NULL) {
83                         fprintf(stderr, "%s:", kvm_errstr);
84                         perror("lseek");
85                 }
86                 return -1;
87         }
88
89         for (bufp = buffer, left = size; left > 0; bufp += r, left -= r) {
90                 r = read(*kvm, bufp, 1);
91                 if (r <= 0)
92                         return -1;
93         }
94         return size;
95 }
96 #endif
97
98 static  kvm_t   *kvm_f = NULL;
99
100 int     openkmem(kern, core)
101 char    *kern, *core;
102 {
103         union {
104                 int ui;
105                 kvm_t *uk;
106         } k;
107
108         kvm_f = kvm_open(kern, core, NULL, O_RDONLY, NULL);
109         if (kvm_f == NULL)
110             {
111                 perror("openkmem:open");
112                 return -1;
113             }
114         k.uk = kvm_f;
115         return k.ui;
116 }
117
118 int     kmemcpy(buf, pos, n)
119 register char   *buf;
120 long    pos;
121 register int    n;
122 {
123         register int    r;
124
125         if (!n)
126                 return 0;
127
128         if (kvm_f == NULL)
129                 if (openkmem(NULL, NULL) == -1)
130                         return -1;
131
132         while ((r = kvm_read(kvm_f, pos, buf, (size_t)n)) < n)
133                 if (r <= 0)
134                     {
135                         fprintf(stderr, "pos=0x%x ", (u_int)pos);
136                         perror("kmemcpy:read");
137                         return -1;
138                     }
139                 else
140                     {
141                         buf += r;
142                         pos += r;
143                         n -= r;
144                     }
145         return 0;
146 }
147
148 int     kstrncpy(buf, pos, n)
149 register char   *buf;
150 long    pos;
151 register int    n;
152 {
153         register int    r;
154
155         if (!n)
156                 return 0;
157
158         if (kvm_f == NULL)
159                 if (openkmem(NULL, NULL) == -1)
160                         return -1;
161
162         while (n > 0)
163             {
164                 r = kvm_read(kvm_f, pos, buf, (size_t)1);
165                 if (r <= 0)
166                     {
167                         fprintf(stderr, "pos=0x%x ", (u_int)pos);
168                         perror("kstrncpy:read");
169                         return -1;
170                     }
171                 else
172                     {
173                         if (*buf == '\0')
174                                 break;
175                         buf++;
176                         pos++;
177                         n--;
178                     }
179             }
180         return 0;
181 }
182
183
184 /*
185  * Given a pointer to an interface in the kernel, return a pointer to a
186  * string which is the interface name.
187  */
188 char *getifname(ptr)
189 void *ptr;
190 {
191 #if SOLARIS
192         char *ifname;
193         ill_t ill;
194
195         if (ptr == (void *)-1)
196                 return "!";
197         if (ptr == NULL)
198                 return "-";
199
200         if (kmemcpy((char *)&ill, (u_long)ptr, sizeof(ill)) == -1)
201                 return "X";
202         ifname = malloc(ill.ill_name_length + 1);
203         if (kmemcpy(ifname, (u_long)ill.ill_name,
204                     ill.ill_name_length) == -1)
205                 return "X";
206         return ifname;
207 #else
208 # if defined(NetBSD) && (NetBSD >= 199905) && (NetBSD < 1991011) || \
209     defined(__OpenBSD__)
210 #else
211         char buf[32];
212         int len;
213 # endif
214         struct ifnet netif;
215
216         if (ptr == (void *)-1)
217                 return "!";
218         if (ptr == NULL)
219                 return "-";
220
221         if (kmemcpy((char *)&netif, (u_long)ptr, sizeof(netif)) == -1)
222                 return "X";
223 # if defined(NetBSD) && (NetBSD >= 199905) && (NetBSD < 1991011) || \
224     defined(__OpenBSD__) || defined(__DragonFly__)
225         return strdup(netif.if_xname);
226 # else
227         if (kstrncpy(buf, (u_long)netif.if_name, sizeof(buf)) == -1)
228                 return "X";
229         if (netif.if_unit < 10)
230                 len = 2;
231         else if (netif.if_unit < 1000)
232                 len = 3;
233         else if (netif.if_unit < 10000)
234                 len = 4;
235         else
236                 len = 5;
237         buf[sizeof(buf) - len] = '\0';
238         sprintf(buf + strlen(buf), "%d", netif.if_unit % 10000);
239         return strdup(buf);
240 # endif
241 #endif
242 }