1 /* -----------------------------------------------------------------------
2 *
3 * Copyright 1999-2008 H. Peter Anvin - All Rights Reserved
4 * Copyright 2009-2011 Intel Corporation; author: H. Peter Anvin
5 *
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation, Inc., 53 Temple Place Ste 330,
9 * Boston MA 02111-1307, USA; either version 2 of the License, or
10 * (at your option) any later version; incorporated herein by reference.
11 *
12 * ----------------------------------------------------------------------- */
13
14 /*
15 * pxe.h
16 *
17 * PXE opcodes
18 *
19 */
20 #ifndef PXE_H
21 #define PXE_H
22
23 #include <syslinux/pxe_api.h>
24 #include <syslinux/config.h>
25 #include <fcntl.h> /* For OK_FLAGS_MASK */
26 #include "fs.h" /* Mostly for FILENAME_MAX */
27
28 /*
29 * Some basic defines...
30 */
31 #define PKTBUF_SIZE 2048 /* Used mostly by the gPXE backend */
32
33 #define is_digit(c) (((c) >= '0') && ((c) <= '9'))
34
35 #define BOOTP_OPTION_MAGIC htonl(0x63825363)
36 #define MAC_MAX 32
37
38 /*
39 * structures
40 */
41 struct pxenv_t {
42 uint8_t signature[6]; /* PXENV+ */
43 uint16_t version;
44 uint8_t length;
45 uint8_t checksum;
46 segoff16_t rmentry;
47 uint32_t pmoffset;
48 uint16_t pmselector;
49 uint16_t stackseg;
50 uint16_t stacksize;
51 uint16_t bc_codeseg;
52 uint16_t bc_codesize;
53 uint16_t bc_dataseg;
54 uint16_t bc_datasize;
55 uint16_t undidataseg;
56 uint16_t undidatasize;
57 uint16_t undicodeseg;
58 uint16_t undicodesize;
59 segoff16_t pxeptr;
60 } __packed;
61
62 struct pxe_t {
63 uint8_t signature[4]; /* !PXE */
64 uint8_t structlength;
65 uint8_t structcksum;
66 uint8_t structrev;
67 uint8_t _pad1;
68 segoff16_t undiromid;
69 segoff16_t baseromid;
70 segoff16_t entrypointsp;
71 segoff16_t entrypointesp;
72 segoff16_t statuscallout;
73 uint8_t _pad2;
74 uint8_t segdesccnt;
75 uint16_t firstselector;
76 pxe_segdesc_t seg[7];
77 } __packed;
78
79 enum pxe_segments {
80 PXE_Seg_Stack = 0,
81 PXE_Seg_UNDIData = 1,
82 PXE_Seg_UNDICode = 2,
83 PXE_Seg_UNDICodeWrite = 3,
84 PXE_Seg_BC_Data = 4,
85 PXE_Seg_BC_Code = 5,
86 PXE_Seg_BC_CodeWrite = 6
87 };
88
89 struct bootp_t {
90 uint8_t opcode; /* BOOTP/DHCP "opcode" */
91 uint8_t hardware; /* ARP hreadware type */
92 uint8_t hardlen; /* Hardware address length */
93 uint8_t gatehops; /* Used by forwarders */
94 uint32_t ident; /* Transaction ID */
95 uint16_t seconds; /* Seconds elapsed */
96 uint16_t flags; /* Broadcast flags */
97 uint32_t cip; /* Cient IP */
98 uint32_t yip; /* "Your" IP */
99 uint32_t sip; /* Next Server IP */
100 uint32_t gip; /* Relay agent IP */
101 uint8_t macaddr[16]; /* Client MAC address */
102 uint8_t sname[64]; /* Server name (optional) */
103 char bootfile[128]; /* Boot file name */
104 uint32_t option_magic; /* Vendor option magic cookie */
105 uint8_t options[1260]; /* Vendor options */
106 } __attribute__ ((packed));
107
108 struct netconn;
109 struct netbuf;
110 struct efi_binding;
111
112 /*
113 * Our inode private information -- this includes the packet buffer!
114 */
115 struct pxe_conn_ops {
116 void (*fill_buffer)(struct inode *inode);
117 void (*close)(struct inode *inode);
118 int (*readdir)(struct inode *inode, struct dirent *dirent);
119 };
120
121 union net_private {
122 struct net_private_lwip {
123 struct netconn *conn; /* lwip network connection */
124 struct netbuf *buf; /* lwip cached buffer */
125 } lwip;
126 struct net_private_tftp {
127 uint32_t remoteip; /* Remote IP address (0 = disconnected) */
128 uint16_t localport; /* Local port number (0=not in use) */
129 } tftp;
130 struct net_private_efi {
131 struct efi_binding *binding; /* EFI binding for protocol */
132 uint16_t localport; /* Local port number (0=not in use) */
133 } efi;
134 };
135
136 struct pxe_pvt_inode {
137 union net_private net; /* Network stack private data */
138 uint16_t tftp_remoteport; /* Remote port number */
139 uint32_t tftp_filepos; /* bytes downloaded (including buffer) */
140 uint32_t tftp_blksize; /* Block size for this connection(*) */
141 uint16_t tftp_bytesleft; /* Unclaimed data bytes */
142 uint16_t tftp_lastpkt; /* Sequence number of last packet (HBO) */
143 char *tftp_dataptr; /* Pointer to available data */
144 uint8_t tftp_goteof; /* 1 if the EOF packet received */
145 uint8_t tftp_unused[3]; /* Currently unused */
146 char *tftp_pktbuf; /* Packet buffer */
147 struct inode *ctl; /* Control connection (for FTP) */
148 const struct pxe_conn_ops *ops;
149 };
150
151 #define PVT(i) ((struct pxe_pvt_inode *)((i)->pvt))
152
153 /*
154 * Variable externs
155 */
156 extern struct syslinux_ipinfo IPInfo;
157
158 extern t_PXENV_UNDI_GET_INFORMATION pxe_undi_info;
159 extern t_PXENV_UNDI_GET_IFACE_INFO pxe_undi_iface;
160
161 extern uint8_t MAC[];
162 extern char BOOTIFStr[];
163 extern uint8_t MAC_len;
164 extern uint8_t MAC_type;
165
166 extern uint8_t DHCPMagic;
167 extern uint32_t RebootTime;
168
169 extern char boot_file[];
170 extern char path_prefix[];
171 extern char LocalDomain[];
172
173 extern uint32_t dns_server[];
174
175 extern uint16_t APIVer;
176 extern far_ptr_t PXEEntry;
177 extern uint8_t KeepPXE;
178
179 extern far_ptr_t InitStack;
180
181 extern bool have_uuid;
182 extern uint8_t uuid_type;
183 extern uint8_t uuid[];
184
185 struct url_info;
186 struct url_scheme {
187 const char *name;
188 void (*open)(struct url_info *, int, struct inode *, const char **);
189 int ok_flags;
190 };
191 /* Flags which can be specified in url_scheme.ok_flags */
192 #define OK_FLAGS_MASK (O_DIRECTORY|O_WRONLY)
193
194 extern const struct url_scheme url_schemes[];
195
196 /*
197 * Compute the suitable gateway for a specific route -- too many
198 * vendor PXE stacks don't do this correctly...
199 */
gateway(uint32_t ip)200 static inline uint32_t gateway(uint32_t ip)
201 {
202 if ((ip ^ IPInfo.myip) & IPInfo.netmask)
203 return IPInfo.gateway;
204 else
205 return 0;
206 }
207
208 /*
209 * functions
210 */
211
212 /* pxeisr.inc */
213 extern uint8_t pxe_irq_vector;
214 extern void pxe_isr(void);
215 extern far_ptr_t pxe_irq_chain;
216 extern void pxe_poll(void);
217
218 /* isr.c */
219 void pxe_init_isr(void);
220 void pxe_start_isr(void);
221 int reset_pxe(void);
222
223 /* pxe.c */
224 struct url_info;
225 bool ip_ok(uint32_t);
226 int pxe_getc(struct inode *inode);
227 void free_socket(struct inode *inode);
228
229 /* undiif.c */
230 int undiif_start(uint32_t ip, uint32_t netmask, uint32_t gw);
231 void undiif_input(t_PXENV_UNDI_ISR *isr);
232
233 /* dhcp_options.c */
234 void parse_dhcp_options(const void *, int, uint8_t);
235 void parse_dhcp(const void *, size_t);
236
237 /* idle.c */
238 void pxe_idle_init(void);
239 void pxe_idle_cleanup(void);
240
241 /* tftp.c */
242 void tftp_open(struct url_info *url, int flags, struct inode *inode,
243 const char **redir);
244
245 /* gpxeurl.c */
246 void gpxe_open(struct inode *inode, const char *url);
247 #define GPXE 0
248
249 /* http.c */
250 void http_open(struct url_info *url, int flags, struct inode *inode,
251 const char **redir);
252
253 /* http_readdir.c */
254 int http_readdir(struct inode *inode, struct dirent *dirent);
255
256 /* ftp.c */
257 void ftp_open(struct url_info *url, int flags, struct inode *inode,
258 const char **redir);
259
260 /* ftp_readdir.c */
261 int ftp_readdir(struct inode *inode, struct dirent *dirent);
262
263 /* tcp.c */
264 const struct pxe_conn_ops tcp_conn_ops;
265
266 extern void gpxe_init(void);
267 extern int pxe_init(bool quiet);
268
269 #endif /* pxe.h */
270