1 /* $NetBSD: if_xennet_xenbus.c,v 1.51 2011/05/30 13:03:56 joerg Exp $ */ 2 3 /* 4 * Copyright (c) 2006 Manuel Bouyer. 5 * 6 * Redistribution and use in source and binary forms, with or without 7 * modification, are permitted provided that the following conditions 8 * are met: 9 * 1. Redistributions of source code must retain the above copyright 10 * notice, this list of conditions and the following disclaimer. 11 * 2. Redistributions in binary form must reproduce the above copyright 12 * notice, this list of conditions and the following disclaimer in the 13 * documentation and/or other materials provided with the distribution. 14 * 15 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR 16 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES 17 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. 18 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, 19 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT 20 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 21 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 22 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 23 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF 24 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 25 * 26 */ 27 28 /* 29 * Copyright (c) 2004 Christian Limpach. 30 * All rights reserved. 31 * 32 * Redistribution and use in source and binary forms, with or without 33 * modification, are permitted provided that the following conditions 34 * are met: 35 * 1. Redistributions of source code must retain the above copyright 36 * notice, this list of conditions and the following disclaimer. 37 * 2. Redistributions in binary form must reproduce the above copyright 38 * notice, this list of conditions and the following disclaimer in the 39 * documentation and/or other materials provided with the distribution. 40 * 41 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR 42 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES 43 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. 44 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, 45 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT 46 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 47 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 48 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 49 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF 50 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 51 */ 52 53 /* 54 * This file contains the xennet frontend code required for the network 55 * communication between two Xen domains. 56 * It ressembles xbd, but is a little more complex as it must deal with two 57 * rings: 58 * - the TX ring, to transmit packets to backend (inside => outside) 59 * - the RX ring, to receive packets from backend (outside => inside) 60 * 61 * Principles are following. 62 * 63 * For TX: 64 * Purpose is to transmit packets to the outside. The start of day is in 65 * xennet_start() (default output routine of xennet) that schedules a softint, 66 * xennet_softstart(). xennet_softstart() generates the requests associated 67 * to the TX mbufs queued (see altq(9)). 68 * The backend's responses are processed by xennet_tx_complete(), called either 69 * from: 70 * - xennet_start() 71 * - xennet_handler(), during an asynchronous event notification from backend 72 * (similar to an IRQ). 73 * 74 * for RX: 75 * Purpose is to process the packets received from the outside. RX buffers 76 * are pre-allocated through xennet_alloc_rx_buffer(), during xennet autoconf 77 * attach. During pre-allocation, frontend pushes requests in the I/O ring, in 78 * preparation for incoming packets from backend. 79 * When RX packets need to be processed, backend takes the requests previously 80 * offered by frontend and pushes the associated responses inside the I/O ring. 81 * When done, it notifies frontend through an event notification, which will 82 * asynchronously call xennet_handler() in frontend. 83 * xennet_handler() processes the responses, generates the associated mbuf, and 84 * passes it to the MI layer for further processing. 85 */ 86 87 #include <sys/cdefs.h> 88 __KERNEL_RCSID(0, "$NetBSD: if_xennet_xenbus.c,v 1.51 2011/05/30 13:03:56 joerg Exp $"); 89 90 #include "opt_xen.h" 91 #include "opt_nfs_boot.h" 92 #include "rnd.h" 93 94 #include <sys/param.h> 95 #include <sys/device.h> 96 #include <sys/conf.h> 97 #include <sys/kernel.h> 98 #include <sys/proc.h> 99 #include <sys/systm.h> 100 #include <sys/intr.h> 101 #if NRND > 0 102 #include <sys/rnd.h> 103 #endif 104 105 #include <net/if.h> 106 #include <net/if_dl.h> 107 #include <net/if_ether.h> 108 #include <net/bpf.h> 109 #include <net/bpfdesc.h> 110 111 #if defined(NFS_BOOT_BOOTSTATIC) 112 #include <sys/fstypes.h> 113 #include <sys/mount.h> 114 #include <sys/statvfs.h> 115 #include <netinet/in.h> 116 #include <nfs/rpcv2.h> 117 #include <nfs/nfsproto.h> 118 #include <nfs/nfs.h> 119 #include <nfs/nfsmount.h> 120 #include <nfs/nfsdiskless.h> 121 #include <xen/if_xennetvar.h> 122 #endif /* defined(NFS_BOOT_BOOTSTATIC) */ 123 124 #include <xen/xennet_checksum.h> 125 126 #include <uvm/uvm.h> 127 128 #include <xen/hypervisor.h> 129 #include <xen/evtchn.h> 130 #include <xen/granttables.h> 131 #include <xen/xen3-public/io/netif.h> 132 #include <xen/xenpmap.h> 133 134 #include <xen/xenbus.h> 135 #include "locators.h" 136 137 #undef XENNET_DEBUG_DUMP 138 #undef XENNET_DEBUG 139 #ifdef XENNET_DEBUG 140 #define XEDB_FOLLOW 0x01 141 #define XEDB_INIT 0x02 142 #define XEDB_EVENT 0x04 143 #define XEDB_MBUF 0x08 144 #define XEDB_MEM 0x10 145 int xennet_debug = 0xff; 146 #define DPRINTF(x) if (xennet_debug) printf x; 147 #define DPRINTFN(n,x) if (xennet_debug & (n)) printf x; 148 #else 149 #define DPRINTF(x) 150 #define DPRINTFN(n,x) 151 #endif 152 153 #define GRANT_INVALID_REF -1 /* entry is free */ 154 #define GRANT_STACK_REF -2 /* entry owned by the network stack */ 155 156 #define NET_TX_RING_SIZE __RING_SIZE((netif_tx_sring_t *)0, PAGE_SIZE) 157 #define NET_RX_RING_SIZE __RING_SIZE((netif_rx_sring_t *)0, PAGE_SIZE) 158 159 struct xennet_txreq { 160 SLIST_ENTRY(xennet_txreq) txreq_next; 161 uint16_t txreq_id; /* ID passed to backend */ 162 grant_ref_t txreq_gntref; /* grant ref of this request */ 163 struct mbuf *txreq_m; /* mbuf being transmitted */ 164 }; 165 166 struct xennet_rxreq { 167 SLIST_ENTRY(xennet_rxreq) rxreq_next; 168 uint16_t rxreq_id; /* ID passed to backend */ 169 grant_ref_t rxreq_gntref; /* grant ref of this request */ 170 /* va/pa for this receive buf. ma will be provided by backend */ 171 paddr_t rxreq_pa; 172 vaddr_t rxreq_va; 173 struct xennet_xenbus_softc *rxreq_sc; /* pointer to our interface */ 174 }; 175 176 struct xennet_xenbus_softc { 177 device_t sc_dev; 178 struct ethercom sc_ethercom; 179 uint8_t sc_enaddr[6]; 180 struct xenbus_device *sc_xbusd; 181 182 netif_tx_front_ring_t sc_tx_ring; 183 netif_rx_front_ring_t sc_rx_ring; 184 185 unsigned int sc_evtchn; 186 void *sc_softintr; 187 188 grant_ref_t sc_tx_ring_gntref; 189 grant_ref_t sc_rx_ring_gntref; 190 191 struct xennet_txreq sc_txreqs[NET_TX_RING_SIZE]; 192 struct xennet_rxreq sc_rxreqs[NET_RX_RING_SIZE]; 193 SLIST_HEAD(,xennet_txreq) sc_txreq_head; /* list of free TX requests */ 194 SLIST_HEAD(,xennet_rxreq) sc_rxreq_head; /* list of free RX requests */ 195 int sc_free_rxreql; /* number of free receive request struct */ 196 197 int sc_backend_status; /* our status with backend */ 198 #define BEST_CLOSED 0 199 #define BEST_DISCONNECTED 1 200 #define BEST_CONNECTED 2 201 #define BEST_SUSPENDED 3 202 unsigned long sc_rx_feature; 203 #define FEATURE_RX_FLIP 0 204 #define FEATURE_RX_COPY 1 205 #if NRND > 0 206 rndsource_element_t sc_rnd_source; 207 #endif 208 }; 209 #define SC_NLIVEREQ(sc) ((sc)->sc_rx_ring.req_prod_pvt - \ 210 (sc)->sc_rx_ring.sring->rsp_prod) 211 212 /* too big to be on stack */ 213 static multicall_entry_t rx_mcl[NET_RX_RING_SIZE+1]; 214 static u_long xennet_pages[NET_RX_RING_SIZE]; 215 216 static int xennet_xenbus_match(device_t, cfdata_t, void *); 217 static void xennet_xenbus_attach(device_t, device_t, void *); 218 static int xennet_xenbus_detach(device_t, int); 219 static void xennet_backend_changed(void *, XenbusState); 220 221 static int xennet_xenbus_resume(void *); 222 static void xennet_alloc_rx_buffer(struct xennet_xenbus_softc *); 223 static void xennet_free_rx_buffer(struct xennet_xenbus_softc *); 224 static void xennet_tx_complete(struct xennet_xenbus_softc *); 225 static void xennet_rx_mbuf_free(struct mbuf *, void *, size_t, void *); 226 static int xennet_handler(void *); 227 static int xennet_talk_to_backend(struct xennet_xenbus_softc *); 228 #ifdef XENNET_DEBUG_DUMP 229 static void xennet_hex_dump(const unsigned char *, size_t, const char *, int); 230 #endif 231 232 static int xennet_init(struct ifnet *); 233 static void xennet_stop(struct ifnet *, int); 234 static void xennet_reset(struct xennet_xenbus_softc *); 235 static void xennet_softstart(void *); 236 static void xennet_start(struct ifnet *); 237 static int xennet_ioctl(struct ifnet *, u_long, void *); 238 static void xennet_watchdog(struct ifnet *); 239 240 CFATTACH_DECL_NEW(xennet, sizeof(struct xennet_xenbus_softc), 241 xennet_xenbus_match, xennet_xenbus_attach, xennet_xenbus_detach, NULL); 242 243 static int 244 xennet_xenbus_match(device_t parent, cfdata_t match, void *aux) 245 { 246 struct xenbusdev_attach_args *xa = aux; 247 248 if (strcmp(xa->xa_type, "vif") != 0) 249 return 0; 250 251 if (match->cf_loc[XENBUSCF_ID] != XENBUSCF_ID_DEFAULT && 252 match->cf_loc[XENBUSCF_ID] != xa->xa_id) 253 return 0; 254 255 return 1; 256 } 257 258 static void 259 xennet_xenbus_attach(device_t parent, device_t self, void *aux) 260 { 261 struct xennet_xenbus_softc *sc = device_private(self); 262 struct xenbusdev_attach_args *xa = aux; 263 struct ifnet *ifp = &sc->sc_ethercom.ec_if; 264 int err; 265 RING_IDX i; 266 char *val, *e, *p; 267 int s; 268 extern int ifqmaxlen; /* XXX */ 269 #ifdef XENNET_DEBUG 270 char **dir; 271 int dir_n = 0; 272 char id_str[20]; 273 #endif 274 275 aprint_normal(": Xen Virtual Network Interface\n"); 276 sc->sc_dev = self; 277 278 #ifdef XENNET_DEBUG 279 printf("path: %s\n", xa->xa_xbusd->xbusd_path); 280 snprintf(id_str, sizeof(id_str), "%d", xa->xa_id); 281 err = xenbus_directory(NULL, "device/vif", id_str, &dir_n, &dir); 282 if (err) { 283 aprint_error_dev(self, "xenbus_directory err %d\n", err); 284 } else { 285 printf("%s/\n", xa->xa_xbusd->xbusd_path); 286 for (i = 0; i < dir_n; i++) { 287 printf("\t/%s", dir[i]); 288 err = xenbus_read(NULL, xa->xa_xbusd->xbusd_path, 289 dir[i], NULL, &val); 290 if (err) { 291 aprint_error_dev(self, "xenbus_read err %d\n", 292 err); 293 } else { 294 printf(" = %s\n", val); 295 free(val, M_DEVBUF); 296 } 297 } 298 } 299 #endif /* XENNET_DEBUG */ 300 sc->sc_xbusd = xa->xa_xbusd; 301 sc->sc_xbusd->xbusd_otherend_changed = xennet_backend_changed; 302 303 /* initialize free RX and RX request lists */ 304 SLIST_INIT(&sc->sc_txreq_head); 305 for (i = 0; i < NET_TX_RING_SIZE; i++) { 306 sc->sc_txreqs[i].txreq_id = i; 307 SLIST_INSERT_HEAD(&sc->sc_txreq_head, &sc->sc_txreqs[i], 308 txreq_next); 309 } 310 SLIST_INIT(&sc->sc_rxreq_head); 311 s = splvm(); 312 for (i = 0; i < NET_RX_RING_SIZE; i++) { 313 struct xennet_rxreq *rxreq = &sc->sc_rxreqs[i]; 314 rxreq->rxreq_id = i; 315 rxreq->rxreq_sc = sc; 316 rxreq->rxreq_va = uvm_km_alloc(kernel_map, 317 PAGE_SIZE, PAGE_SIZE, UVM_KMF_WIRED | UVM_KMF_ZERO); 318 if (rxreq->rxreq_va == 0) 319 break; 320 if (!pmap_extract(pmap_kernel(), rxreq->rxreq_va, 321 &rxreq->rxreq_pa)) 322 panic("%s: no pa for mapped va ?", device_xname(self)); 323 rxreq->rxreq_gntref = GRANT_INVALID_REF; 324 SLIST_INSERT_HEAD(&sc->sc_rxreq_head, rxreq, rxreq_next); 325 } 326 splx(s); 327 sc->sc_free_rxreql = i; 328 if (sc->sc_free_rxreql == 0) { 329 aprint_error_dev(self, "failed to allocate rx memory\n"); 330 return; 331 } 332 333 /* read mac address */ 334 err = xenbus_read(NULL, xa->xa_xbusd->xbusd_path, "mac", NULL, &val); 335 if (err) { 336 aprint_error_dev(self, "can't read mac address, err %d\n", err); 337 return; 338 } 339 for (i = 0, p = val; i < 6; i++) { 340 sc->sc_enaddr[i] = strtoul(p, &e, 16); 341 if ((e[0] == '\0' && i != 5) && e[0] != ':') { 342 aprint_error_dev(self, 343 "%s is not a valid mac address\n", val); 344 free(val, M_DEVBUF); 345 return; 346 } 347 p = &e[1]; 348 } 349 free(val, M_DEVBUF); 350 aprint_normal_dev(self, "MAC address %s\n", 351 ether_sprintf(sc->sc_enaddr)); 352 /* Initialize ifnet structure and attach interface */ 353 strlcpy(ifp->if_xname, device_xname(self), IFNAMSIZ); 354 ifp->if_softc = sc; 355 ifp->if_start = xennet_start; 356 ifp->if_ioctl = xennet_ioctl; 357 ifp->if_watchdog = xennet_watchdog; 358 ifp->if_init = xennet_init; 359 ifp->if_stop = xennet_stop; 360 ifp->if_flags = IFF_BROADCAST|IFF_SIMPLEX|IFF_NOTRAILERS|IFF_MULTICAST; 361 ifp->if_timer = 0; 362 ifp->if_snd.ifq_maxlen = max(ifqmaxlen, NET_TX_RING_SIZE * 2); 363 ifp->if_capabilities = IFCAP_CSUM_TCPv4_Tx | IFCAP_CSUM_UDPv4_Tx; 364 IFQ_SET_READY(&ifp->if_snd); 365 if_attach(ifp); 366 ether_ifattach(ifp, sc->sc_enaddr); 367 sc->sc_softintr = softint_establish(SOFTINT_NET, xennet_softstart, sc); 368 if (sc->sc_softintr == NULL) 369 panic("%s: can't establish soft interrupt", 370 device_xname(self)); 371 372 #if NRND > 0 373 rnd_attach_source(&sc->sc_rnd_source, device_xname(sc->sc_dev), 374 RND_TYPE_NET, 0); 375 #endif 376 377 /* resume shared structures and tell backend that we are ready */ 378 xennet_xenbus_resume(sc); 379 } 380 381 static int 382 xennet_xenbus_detach(device_t self, int flags) 383 { 384 struct xennet_xenbus_softc *sc = device_private(self); 385 struct ifnet *ifp = &sc->sc_ethercom.ec_if; 386 int s0, s1; 387 RING_IDX i; 388 389 DPRINTF(("%s: xennet_xenbus_detach\n", device_xname(self))); 390 s0 = splnet(); 391 xennet_stop(ifp, 1); 392 /* wait for pending TX to complete, and collect pending RX packets */ 393 xennet_handler(sc); 394 while (sc->sc_tx_ring.sring->rsp_prod != sc->sc_tx_ring.rsp_cons) { 395 tsleep(xennet_xenbus_detach, PRIBIO, "xnet_detach", hz/2); 396 xennet_handler(sc); 397 } 398 xennet_free_rx_buffer(sc); 399 400 s1 = splvm(); 401 for (i = 0; i < NET_RX_RING_SIZE; i++) { 402 struct xennet_rxreq *rxreq = &sc->sc_rxreqs[i]; 403 uvm_km_free(kernel_map, rxreq->rxreq_va, PAGE_SIZE, 404 UVM_KMF_WIRED); 405 } 406 splx(s1); 407 408 ether_ifdetach(ifp); 409 if_detach(ifp); 410 411 #if NRND > 0 412 /* Unhook the entropy source. */ 413 rnd_detach_source(&sc->sc_rnd_source); 414 #endif 415 416 while (xengnt_status(sc->sc_tx_ring_gntref)) { 417 tsleep(xennet_xenbus_detach, PRIBIO, "xnet_txref", hz/2); 418 } 419 xengnt_revoke_access(sc->sc_tx_ring_gntref); 420 uvm_km_free(kernel_map, (vaddr_t)sc->sc_tx_ring.sring, PAGE_SIZE, 421 UVM_KMF_WIRED); 422 while (xengnt_status(sc->sc_rx_ring_gntref)) { 423 tsleep(xennet_xenbus_detach, PRIBIO, "xnet_rxref", hz/2); 424 } 425 xengnt_revoke_access(sc->sc_rx_ring_gntref); 426 uvm_km_free(kernel_map, (vaddr_t)sc->sc_rx_ring.sring, PAGE_SIZE, 427 UVM_KMF_WIRED); 428 softint_disestablish(sc->sc_softintr); 429 event_remove_handler(sc->sc_evtchn, &xennet_handler, sc); 430 splx(s0); 431 DPRINTF(("%s: xennet_xenbus_detach done\n", device_xname(self))); 432 return 0; 433 } 434 435 static int 436 xennet_xenbus_resume(void *p) 437 { 438 struct xennet_xenbus_softc *sc = p; 439 int error; 440 netif_tx_sring_t *tx_ring; 441 netif_rx_sring_t *rx_ring; 442 paddr_t ma; 443 444 sc->sc_tx_ring_gntref = GRANT_INVALID_REF; 445 sc->sc_rx_ring_gntref = GRANT_INVALID_REF; 446 447 /* setup device: alloc event channel and shared rings */ 448 tx_ring = (void *)uvm_km_alloc(kernel_map, PAGE_SIZE, 0, 449 UVM_KMF_WIRED | UVM_KMF_ZERO); 450 rx_ring = (void *)uvm_km_alloc(kernel_map, PAGE_SIZE, 0, 451 UVM_KMF_WIRED | UVM_KMF_ZERO); 452 if (tx_ring == NULL || rx_ring == NULL) 453 panic("xennet_xenbus_resume: can't alloc rings"); 454 455 SHARED_RING_INIT(tx_ring); 456 FRONT_RING_INIT(&sc->sc_tx_ring, tx_ring, PAGE_SIZE); 457 SHARED_RING_INIT(rx_ring); 458 FRONT_RING_INIT(&sc->sc_rx_ring, rx_ring, PAGE_SIZE); 459 460 (void)pmap_extract_ma(pmap_kernel(), (vaddr_t)tx_ring, &ma); 461 error = xenbus_grant_ring(sc->sc_xbusd, ma, &sc->sc_tx_ring_gntref); 462 if (error) 463 return error; 464 (void)pmap_extract_ma(pmap_kernel(), (vaddr_t)rx_ring, &ma); 465 error = xenbus_grant_ring(sc->sc_xbusd, ma, &sc->sc_rx_ring_gntref); 466 if (error) 467 return error; 468 error = xenbus_alloc_evtchn(sc->sc_xbusd, &sc->sc_evtchn); 469 if (error) 470 return error; 471 aprint_verbose_dev(sc->sc_dev, "using event channel %d\n", 472 sc->sc_evtchn); 473 event_set_handler(sc->sc_evtchn, &xennet_handler, sc, 474 IPL_NET, device_xname(sc->sc_dev)); 475 476 return 0; 477 } 478 479 static int 480 xennet_talk_to_backend(struct xennet_xenbus_softc *sc) 481 { 482 int error; 483 unsigned long rx_copy; 484 struct xenbus_transaction *xbt; 485 const char *errmsg; 486 487 error = xenbus_read_ul(NULL, sc->sc_xbusd->xbusd_otherend, 488 "feature-rx-copy", &rx_copy, 10); 489 if (error) 490 rx_copy = 0; /* default value if key is absent */ 491 492 if (rx_copy == 1) { 493 aprint_normal_dev(sc->sc_dev, "using RX copy mode\n"); 494 sc->sc_rx_feature = FEATURE_RX_COPY; 495 } else { 496 aprint_normal_dev(sc->sc_dev, "using RX flip mode\n"); 497 sc->sc_rx_feature = FEATURE_RX_FLIP; 498 } 499 500 again: 501 xbt = xenbus_transaction_start(); 502 if (xbt == NULL) 503 return ENOMEM; 504 error = xenbus_printf(xbt, sc->sc_xbusd->xbusd_path, 505 "vifname", "%s", device_xname(sc->sc_dev)); 506 if (error) { 507 errmsg = "vifname"; 508 goto abort_transaction; 509 } 510 error = xenbus_printf(xbt, sc->sc_xbusd->xbusd_path, 511 "tx-ring-ref","%u", sc->sc_tx_ring_gntref); 512 if (error) { 513 errmsg = "writing tx ring-ref"; 514 goto abort_transaction; 515 } 516 error = xenbus_printf(xbt, sc->sc_xbusd->xbusd_path, 517 "rx-ring-ref","%u", sc->sc_rx_ring_gntref); 518 if (error) { 519 errmsg = "writing rx ring-ref"; 520 goto abort_transaction; 521 } 522 error = xenbus_printf(xbt, sc->sc_xbusd->xbusd_path, 523 "request-rx-copy", "%lu", rx_copy); 524 if (error) { 525 errmsg = "writing request-rx-copy"; 526 goto abort_transaction; 527 } 528 error = xenbus_printf(xbt, sc->sc_xbusd->xbusd_path, 529 "feature-rx-notify", "%u", 1); 530 if (error) { 531 errmsg = "writing feature-rx-notify"; 532 goto abort_transaction; 533 } 534 error = xenbus_printf(xbt, sc->sc_xbusd->xbusd_path, 535 "event-channel", "%u", sc->sc_evtchn); 536 if (error) { 537 errmsg = "writing event channel"; 538 goto abort_transaction; 539 } 540 error = xenbus_transaction_end(xbt, 0); 541 if (error == EAGAIN) 542 goto again; 543 if (error) { 544 xenbus_dev_fatal(sc->sc_xbusd, error, "completing transaction"); 545 return -1; 546 } 547 xennet_alloc_rx_buffer(sc); 548 sc->sc_backend_status = BEST_CONNECTED; 549 return 0; 550 551 abort_transaction: 552 xenbus_transaction_end(xbt, 1); 553 xenbus_dev_fatal(sc->sc_xbusd, error, "%s", errmsg); 554 return error; 555 } 556 557 static void xennet_backend_changed(void *arg, XenbusState new_state) 558 { 559 struct xennet_xenbus_softc *sc = device_private((device_t)arg); 560 DPRINTF(("%s: new backend state %d\n", 561 device_xname(sc->sc_dev), new_state)); 562 563 switch (new_state) { 564 case XenbusStateInitialising: 565 case XenbusStateInitialised: 566 case XenbusStateConnected: 567 break; 568 case XenbusStateClosing: 569 sc->sc_backend_status = BEST_CLOSED; 570 xenbus_switch_state(sc->sc_xbusd, NULL, XenbusStateClosed); 571 break; 572 case XenbusStateInitWait: 573 if (sc->sc_backend_status == BEST_CONNECTED) 574 break; 575 if (xennet_talk_to_backend(sc) == 0) 576 xenbus_switch_state(sc->sc_xbusd, NULL, 577 XenbusStateConnected); 578 break; 579 case XenbusStateUnknown: 580 default: 581 panic("bad backend state %d", new_state); 582 } 583 } 584 585 /* 586 * Allocate RX buffers and put the associated request structures 587 * in the ring. This allows the backend to use them to communicate with 588 * frontend when some data is destined to frontend 589 */ 590 591 static void 592 xennet_alloc_rx_buffer(struct xennet_xenbus_softc *sc) 593 { 594 RING_IDX req_prod = sc->sc_rx_ring.req_prod_pvt; 595 RING_IDX i; 596 struct xennet_rxreq *req; 597 struct xen_memory_reservation reservation; 598 int s1, s2, otherend_id; 599 paddr_t pfn; 600 601 otherend_id = sc->sc_xbusd->xbusd_otherend_id; 602 603 s1 = splnet(); 604 for (i = 0; sc->sc_free_rxreql != 0; i++) { 605 req = SLIST_FIRST(&sc->sc_rxreq_head); 606 KASSERT(req != NULL); 607 KASSERT(req == &sc->sc_rxreqs[req->rxreq_id]); 608 RING_GET_REQUEST(&sc->sc_rx_ring, req_prod + i)->id = 609 req->rxreq_id; 610 611 switch (sc->sc_rx_feature) { 612 case FEATURE_RX_COPY: 613 if (xengnt_grant_access(otherend_id, 614 xpmap_ptom_masked(req->rxreq_pa), 615 0, &req->rxreq_gntref) != 0) { 616 goto out_loop; 617 } 618 break; 619 case FEATURE_RX_FLIP: 620 if (xengnt_grant_transfer(otherend_id, 621 &req->rxreq_gntref) != 0) { 622 goto out_loop; 623 } 624 break; 625 default: 626 panic("%s: unsupported RX feature mode: %ld\n", 627 __func__, sc->sc_rx_feature); 628 } 629 630 RING_GET_REQUEST(&sc->sc_rx_ring, req_prod + i)->gref = 631 req->rxreq_gntref; 632 633 SLIST_REMOVE_HEAD(&sc->sc_rxreq_head, rxreq_next); 634 sc->sc_free_rxreql--; 635 636 if (sc->sc_rx_feature == FEATURE_RX_FLIP) { 637 /* unmap the page */ 638 MULTI_update_va_mapping(&rx_mcl[i], 639 req->rxreq_va, 0, 0); 640 /* 641 * Remove this page from pseudo phys map before 642 * passing back to Xen. 643 */ 644 pfn = (req->rxreq_pa - XPMAP_OFFSET) >> PAGE_SHIFT; 645 xennet_pages[i] = xpmap_phys_to_machine_mapping[pfn]; 646 xpmap_phys_to_machine_mapping[pfn] = INVALID_P2M_ENTRY; 647 } 648 } 649 650 out_loop: 651 if (i == 0) { 652 splx(s1); 653 return; 654 } 655 656 if (sc->sc_rx_feature == FEATURE_RX_FLIP) { 657 /* also make sure to flush all TLB entries */ 658 rx_mcl[i-1].args[MULTI_UVMFLAGS_INDEX] = 659 UVMF_TLB_FLUSH | UVMF_ALL; 660 /* 661 * We may have allocated buffers which have entries 662 * outstanding in the page update queue -- make sure we flush 663 * those first! 664 */ 665 s2 = splvm(); 666 xpq_flush_queue(); 667 splx(s2); 668 /* now decrease reservation */ 669 xenguest_handle(reservation.extent_start) = xennet_pages; 670 reservation.nr_extents = i; 671 reservation.extent_order = 0; 672 reservation.address_bits = 0; 673 reservation.domid = DOMID_SELF; 674 rx_mcl[i].op = __HYPERVISOR_memory_op; 675 rx_mcl[i].args[0] = XENMEM_decrease_reservation; 676 rx_mcl[i].args[1] = (unsigned long)&reservation; 677 HYPERVISOR_multicall(rx_mcl, i+1); 678 if (__predict_false(rx_mcl[i].result != i)) { 679 panic("xennet_alloc_rx_buffer: " 680 "XENMEM_decrease_reservation"); 681 } 682 } 683 684 sc->sc_rx_ring.req_prod_pvt = req_prod + i; 685 RING_PUSH_REQUESTS(&sc->sc_rx_ring); 686 687 splx(s1); 688 return; 689 } 690 691 /* 692 * Reclaim all RX buffers used by the I/O ring between frontend and backend 693 */ 694 static void 695 xennet_free_rx_buffer(struct xennet_xenbus_softc *sc) 696 { 697 paddr_t ma, pa; 698 vaddr_t va; 699 RING_IDX i; 700 mmu_update_t mmu[1]; 701 multicall_entry_t mcl[2]; 702 703 int s = splbio(); 704 705 DPRINTF(("%s: xennet_free_rx_buffer\n", device_xname(sc->sc_dev))); 706 /* get back memory from RX ring */ 707 for (i = 0; i < NET_RX_RING_SIZE; i++) { 708 struct xennet_rxreq *rxreq = &sc->sc_rxreqs[i]; 709 710 /* 711 * if the buffer is in transit in the network stack, wait for 712 * the network stack to free it. 713 */ 714 while ((volatile grant_ref_t)rxreq->rxreq_gntref == 715 GRANT_STACK_REF) 716 tsleep(xennet_xenbus_detach, PRIBIO, "xnet_free", hz/2); 717 718 if (rxreq->rxreq_gntref != GRANT_INVALID_REF) { 719 /* 720 * this req is still granted. Get back the page or 721 * allocate a new one, and remap it. 722 */ 723 SLIST_INSERT_HEAD(&sc->sc_rxreq_head, rxreq, 724 rxreq_next); 725 sc->sc_free_rxreql++; 726 727 switch (sc->sc_rx_feature) { 728 case FEATURE_RX_COPY: 729 xengnt_revoke_access(rxreq->rxreq_gntref); 730 rxreq->rxreq_gntref = GRANT_INVALID_REF; 731 break; 732 case FEATURE_RX_FLIP: 733 ma = xengnt_revoke_transfer( 734 rxreq->rxreq_gntref); 735 rxreq->rxreq_gntref = GRANT_INVALID_REF; 736 if (ma == 0) { 737 u_long pfn; 738 struct xen_memory_reservation xenres; 739 /* 740 * transfer not complete, we lost the page. 741 * Get one from hypervisor 742 */ 743 xenguest_handle(xenres.extent_start) = &pfn; 744 xenres.nr_extents = 1; 745 xenres.extent_order = 0; 746 xenres.address_bits = 31; 747 xenres.domid = DOMID_SELF; 748 if (HYPERVISOR_memory_op( 749 XENMEM_increase_reservation, &xenres) < 0) { 750 panic("xennet_free_rx_buffer: " 751 "can't get memory back"); 752 } 753 ma = pfn; 754 KASSERT(ma != 0); 755 } 756 pa = rxreq->rxreq_pa; 757 va = rxreq->rxreq_va; 758 /* remap the page */ 759 mmu[0].ptr = (ma << PAGE_SHIFT) | MMU_MACHPHYS_UPDATE; 760 mmu[0].val = ((pa - XPMAP_OFFSET) >> PAGE_SHIFT); 761 MULTI_update_va_mapping(&mcl[0], va, 762 (ma << PAGE_SHIFT) | PG_V | PG_KW, 763 UVMF_TLB_FLUSH|UVMF_ALL); 764 xpmap_phys_to_machine_mapping[ 765 (pa - XPMAP_OFFSET) >> PAGE_SHIFT] = ma; 766 mcl[1].op = __HYPERVISOR_mmu_update; 767 mcl[1].args[0] = (unsigned long)mmu; 768 mcl[1].args[1] = 1; 769 mcl[1].args[2] = 0; 770 mcl[1].args[3] = DOMID_SELF; 771 HYPERVISOR_multicall(mcl, 2); 772 break; 773 default: 774 panic("%s: unsupported RX feature mode: %ld\n", 775 __func__, sc->sc_rx_feature); 776 } 777 } 778 779 } 780 splx(s); 781 DPRINTF(("%s: xennet_free_rx_buffer done\n", device_xname(sc->sc_dev))); 782 } 783 784 /* 785 * Clears a used RX request when its associated mbuf has been processed 786 */ 787 static void 788 xennet_rx_mbuf_free(struct mbuf *m, void *buf, size_t size, void *arg) 789 { 790 struct xennet_rxreq *req = arg; 791 struct xennet_xenbus_softc *sc = req->rxreq_sc; 792 793 int s = splnet(); 794 795 /* puts back the RX request in the list of free RX requests */ 796 SLIST_INSERT_HEAD(&sc->sc_rxreq_head, req, rxreq_next); 797 sc->sc_free_rxreql++; 798 799 /* 800 * ring needs more requests to be pushed in, allocate some 801 * RX buffers to catch-up with backend's consumption 802 */ 803 req->rxreq_gntref = GRANT_INVALID_REF; 804 if (sc->sc_free_rxreql >= SC_NLIVEREQ(sc) && 805 __predict_true(sc->sc_backend_status == BEST_CONNECTED)) { 806 xennet_alloc_rx_buffer(sc); 807 } 808 809 if (m) 810 pool_cache_put(mb_cache, m); 811 splx(s); 812 } 813 814 /* 815 * Process responses associated to the TX mbufs sent previously through 816 * xennet_softstart() 817 * Called at splnet. 818 */ 819 static void 820 xennet_tx_complete(struct xennet_xenbus_softc *sc) 821 { 822 struct xennet_txreq *req; 823 struct ifnet *ifp = &sc->sc_ethercom.ec_if; 824 RING_IDX resp_prod, i; 825 826 DPRINTFN(XEDB_EVENT, ("xennet_tx_complete prod %d cons %d\n", 827 sc->sc_tx_ring.sring->rsp_prod, sc->sc_tx_ring.rsp_cons)); 828 829 again: 830 resp_prod = sc->sc_tx_ring.sring->rsp_prod; 831 xen_rmb(); 832 for (i = sc->sc_tx_ring.rsp_cons; i != resp_prod; i++) { 833 req = &sc->sc_txreqs[RING_GET_RESPONSE(&sc->sc_tx_ring, i)->id]; 834 KASSERT(req->txreq_id == 835 RING_GET_RESPONSE(&sc->sc_tx_ring, i)->id); 836 if (__predict_false(xengnt_status(req->txreq_gntref))) { 837 aprint_verbose_dev(sc->sc_dev, 838 "grant still used by backend\n"); 839 sc->sc_tx_ring.rsp_cons = i; 840 goto end; 841 } 842 if (__predict_false( 843 RING_GET_RESPONSE(&sc->sc_tx_ring, i)->status != 844 NETIF_RSP_OKAY)) 845 ifp->if_oerrors++; 846 else 847 ifp->if_opackets++; 848 xengnt_revoke_access(req->txreq_gntref); 849 m_freem(req->txreq_m); 850 SLIST_INSERT_HEAD(&sc->sc_txreq_head, req, txreq_next); 851 } 852 sc->sc_tx_ring.rsp_cons = resp_prod; 853 /* set new event and check for race with rsp_cons update */ 854 sc->sc_tx_ring.sring->rsp_event = 855 resp_prod + ((sc->sc_tx_ring.sring->req_prod - resp_prod) >> 1) + 1; 856 ifp->if_timer = 0; 857 xen_wmb(); 858 if (resp_prod != sc->sc_tx_ring.sring->rsp_prod) 859 goto again; 860 end: 861 if (ifp->if_flags & IFF_OACTIVE) { 862 ifp->if_flags &= ~IFF_OACTIVE; 863 xennet_softstart(sc); 864 } 865 } 866 867 /* 868 * Xennet event handler. 869 * Get outstanding responses of TX packets, then collect all responses of 870 * pending RX packets 871 * Called at splnet. 872 */ 873 static int 874 xennet_handler(void *arg) 875 { 876 struct xennet_xenbus_softc *sc = arg; 877 struct ifnet *ifp = &sc->sc_ethercom.ec_if; 878 RING_IDX resp_prod, i; 879 struct xennet_rxreq *req; 880 paddr_t ma, pa; 881 vaddr_t va; 882 mmu_update_t mmu[1]; 883 multicall_entry_t mcl[2]; 884 struct mbuf *m; 885 void *pktp; 886 int more_to_do; 887 888 if (sc->sc_backend_status != BEST_CONNECTED) 889 return 1; 890 891 xennet_tx_complete(sc); 892 893 #if NRND > 0 894 rnd_add_uint32(&sc->sc_rnd_source, sc->sc_tx_ring.req_prod_pvt); 895 #endif 896 again: 897 DPRINTFN(XEDB_EVENT, ("xennet_handler prod %d cons %d\n", 898 sc->sc_rx_ring.sring->rsp_prod, sc->sc_rx_ring.rsp_cons)); 899 900 resp_prod = sc->sc_rx_ring.sring->rsp_prod; 901 xen_rmb(); /* ensure we see replies up to resp_prod */ 902 for (i = sc->sc_rx_ring.rsp_cons; i != resp_prod; i++) { 903 netif_rx_response_t *rx = RING_GET_RESPONSE(&sc->sc_rx_ring, i); 904 req = &sc->sc_rxreqs[rx->id]; 905 KASSERT(req->rxreq_gntref != GRANT_INVALID_REF); 906 KASSERT(req->rxreq_id == rx->id); 907 908 ma = 0; 909 switch (sc->sc_rx_feature) { 910 case FEATURE_RX_COPY: 911 xengnt_revoke_access(req->rxreq_gntref); 912 break; 913 case FEATURE_RX_FLIP: 914 ma = xengnt_revoke_transfer(req->rxreq_gntref); 915 if (ma == 0) { 916 DPRINTFN(XEDB_EVENT, ("xennet_handler ma == 0\n")); 917 /* 918 * the remote could't send us a packet. 919 * we can't free this rxreq as no page will be mapped 920 * here. Instead give it back immediatly to backend. 921 */ 922 ifp->if_ierrors++; 923 RING_GET_REQUEST(&sc->sc_rx_ring, 924 sc->sc_rx_ring.req_prod_pvt)->id = req->rxreq_id; 925 RING_GET_REQUEST(&sc->sc_rx_ring, 926 sc->sc_rx_ring.req_prod_pvt)->gref = 927 req->rxreq_gntref; 928 sc->sc_rx_ring.req_prod_pvt++; 929 RING_PUSH_REQUESTS(&sc->sc_rx_ring); 930 continue; 931 } 932 break; 933 default: 934 panic("%s: unsupported RX feature mode: %ld\n", 935 __func__, sc->sc_rx_feature); 936 } 937 938 req->rxreq_gntref = GRANT_INVALID_REF; 939 940 pa = req->rxreq_pa; 941 va = req->rxreq_va; 942 943 if (sc->sc_rx_feature == FEATURE_RX_FLIP) { 944 /* remap the page */ 945 mmu[0].ptr = (ma << PAGE_SHIFT) | MMU_MACHPHYS_UPDATE; 946 mmu[0].val = ((pa - XPMAP_OFFSET) >> PAGE_SHIFT); 947 MULTI_update_va_mapping(&mcl[0], va, 948 (ma << PAGE_SHIFT) | PG_V | PG_KW, UVMF_TLB_FLUSH|UVMF_ALL); 949 xpmap_phys_to_machine_mapping[ 950 (pa - XPMAP_OFFSET) >> PAGE_SHIFT] = ma; 951 mcl[1].op = __HYPERVISOR_mmu_update; 952 mcl[1].args[0] = (unsigned long)mmu; 953 mcl[1].args[1] = 1; 954 mcl[1].args[2] = 0; 955 mcl[1].args[3] = DOMID_SELF; 956 HYPERVISOR_multicall(mcl, 2); 957 } 958 959 pktp = (void *)(va + rx->offset); 960 #ifdef XENNET_DEBUG_DUMP 961 xennet_hex_dump(pktp, rx->status, "r", rx->id); 962 #endif 963 if ((ifp->if_flags & IFF_PROMISC) == 0) { 964 struct ether_header *eh = pktp; 965 if (ETHER_IS_MULTICAST(eh->ether_dhost) == 0 && 966 memcmp(CLLADDR(ifp->if_sadl), eh->ether_dhost, 967 ETHER_ADDR_LEN) != 0) { 968 DPRINTFN(XEDB_EVENT, 969 ("xennet_handler bad dest\n")); 970 /* packet not for us */ 971 xennet_rx_mbuf_free(NULL, (void *)va, PAGE_SIZE, 972 req); 973 continue; 974 } 975 } 976 MGETHDR(m, M_DONTWAIT, MT_DATA); 977 if (__predict_false(m == NULL)) { 978 printf("%s: rx no mbuf\n", ifp->if_xname); 979 ifp->if_ierrors++; 980 xennet_rx_mbuf_free(NULL, (void *)va, PAGE_SIZE, req); 981 continue; 982 } 983 MCLAIM(m, &sc->sc_ethercom.ec_rx_mowner); 984 985 m->m_pkthdr.rcvif = ifp; 986 if (__predict_true(sc->sc_rx_ring.req_prod_pvt != 987 sc->sc_rx_ring.sring->rsp_prod)) { 988 m->m_len = m->m_pkthdr.len = rx->status; 989 MEXTADD(m, pktp, rx->status, 990 M_DEVBUF, xennet_rx_mbuf_free, req); 991 m->m_flags |= M_EXT_RW; /* we own the buffer */ 992 req->rxreq_gntref = GRANT_STACK_REF; 993 } else { 994 /* 995 * This was our last receive buffer, allocate 996 * memory, copy data and push the receive 997 * buffer back to the hypervisor. 998 */ 999 m->m_len = min(MHLEN, rx->status); 1000 m->m_pkthdr.len = 0; 1001 m_copyback(m, 0, rx->status, pktp); 1002 xennet_rx_mbuf_free(NULL, (void *)va, PAGE_SIZE, req); 1003 if (m->m_pkthdr.len < rx->status) { 1004 /* out of memory, just drop packets */ 1005 ifp->if_ierrors++; 1006 m_freem(m); 1007 continue; 1008 } 1009 } 1010 if ((rx->flags & NETRXF_csum_blank) != 0) { 1011 xennet_checksum_fill(&m); 1012 if (m == NULL) { 1013 ifp->if_ierrors++; 1014 continue; 1015 } 1016 } 1017 /* 1018 * Pass packet to bpf if there is a listener. 1019 */ 1020 bpf_mtap(ifp, m); 1021 1022 ifp->if_ipackets++; 1023 1024 /* Pass the packet up. */ 1025 (*ifp->if_input)(ifp, m); 1026 } 1027 xen_rmb(); 1028 sc->sc_rx_ring.rsp_cons = i; 1029 RING_FINAL_CHECK_FOR_RESPONSES(&sc->sc_rx_ring, more_to_do); 1030 if (more_to_do) 1031 goto again; 1032 return 1; 1033 } 1034 1035 /* 1036 * The output routine of a xennet interface 1037 * Called at splnet. 1038 */ 1039 void 1040 xennet_start(struct ifnet *ifp) 1041 { 1042 struct xennet_xenbus_softc *sc = ifp->if_softc; 1043 1044 DPRINTFN(XEDB_FOLLOW, ("%s: xennet_start()\n", device_xname(sc->sc_dev))); 1045 1046 #if NRND > 0 1047 rnd_add_uint32(&sc->sc_rnd_source, sc->sc_tx_ring.req_prod_pvt); 1048 #endif 1049 1050 xennet_tx_complete(sc); 1051 1052 if (__predict_false( 1053 (ifp->if_flags & (IFF_RUNNING | IFF_OACTIVE)) != IFF_RUNNING)) 1054 return; 1055 1056 /* 1057 * The Xen communication channel is much more efficient if we can 1058 * schedule batch of packets for domain0. To achieve this, we 1059 * schedule a soft interrupt, and just return. This way, the network 1060 * stack will enqueue all pending mbufs in the interface's send queue 1061 * before it is processed by xennet_softstart(). 1062 */ 1063 softint_schedule(sc->sc_softintr); 1064 return; 1065 } 1066 1067 /* 1068 * Prepares mbufs for TX, and notify backend when finished 1069 * Called at splsoftnet 1070 */ 1071 void 1072 xennet_softstart(void *arg) 1073 { 1074 struct xennet_xenbus_softc *sc = arg; 1075 struct ifnet *ifp = &sc->sc_ethercom.ec_if; 1076 struct mbuf *m, *new_m; 1077 netif_tx_request_t *txreq; 1078 RING_IDX req_prod; 1079 paddr_t pa, pa2; 1080 struct xennet_txreq *req; 1081 int notify; 1082 int do_notify = 0; 1083 int s; 1084 1085 s = splnet(); 1086 if (__predict_false( 1087 (ifp->if_flags & (IFF_RUNNING | IFF_OACTIVE)) != IFF_RUNNING)) { 1088 splx(s); 1089 return; 1090 } 1091 1092 req_prod = sc->sc_tx_ring.req_prod_pvt; 1093 while (/*CONSTCOND*/1) { 1094 uint16_t txflags; 1095 1096 req = SLIST_FIRST(&sc->sc_txreq_head); 1097 if (__predict_false(req == NULL)) { 1098 ifp->if_flags |= IFF_OACTIVE; 1099 break; 1100 } 1101 IFQ_POLL(&ifp->if_snd, m); 1102 if (m == NULL) 1103 break; 1104 1105 switch (m->m_flags & (M_EXT|M_EXT_CLUSTER)) { 1106 case M_EXT|M_EXT_CLUSTER: 1107 KASSERT(m->m_ext.ext_paddr != M_PADDR_INVALID); 1108 pa = m->m_ext.ext_paddr + 1109 (m->m_data - m->m_ext.ext_buf); 1110 break; 1111 case 0: 1112 KASSERT(m->m_paddr != M_PADDR_INVALID); 1113 pa = m->m_paddr + M_BUFOFFSET(m) + 1114 (m->m_data - M_BUFADDR(m)); 1115 break; 1116 default: 1117 if (__predict_false( 1118 !pmap_extract(pmap_kernel(), (vaddr_t)m->m_data, 1119 &pa))) { 1120 panic("xennet_start: no pa"); 1121 } 1122 break; 1123 } 1124 1125 if ((m->m_pkthdr.csum_flags & 1126 (M_CSUM_TCPv4 | M_CSUM_UDPv4)) != 0) { 1127 txflags = NETTXF_csum_blank; 1128 } else { 1129 txflags = 0; 1130 } 1131 1132 if (m->m_pkthdr.len != m->m_len || 1133 (pa ^ (pa + m->m_pkthdr.len - 1)) & PG_FRAME) { 1134 1135 MGETHDR(new_m, M_DONTWAIT, MT_DATA); 1136 if (__predict_false(new_m == NULL)) { 1137 printf("%s: cannot allocate new mbuf\n", 1138 device_xname(sc->sc_dev)); 1139 break; 1140 } 1141 if (m->m_pkthdr.len > MHLEN) { 1142 MCLGET(new_m, M_DONTWAIT); 1143 if (__predict_false( 1144 (new_m->m_flags & M_EXT) == 0)) { 1145 DPRINTF(("%s: no mbuf cluster\n", 1146 device_xname(sc->sc_dev))); 1147 m_freem(new_m); 1148 break; 1149 } 1150 } 1151 1152 m_copydata(m, 0, m->m_pkthdr.len, mtod(new_m, void *)); 1153 new_m->m_len = new_m->m_pkthdr.len = m->m_pkthdr.len; 1154 1155 if ((new_m->m_flags & M_EXT) != 0) { 1156 pa = new_m->m_ext.ext_paddr; 1157 KASSERT(new_m->m_data == new_m->m_ext.ext_buf); 1158 KASSERT(pa != M_PADDR_INVALID); 1159 } else { 1160 pa = new_m->m_paddr; 1161 KASSERT(pa != M_PADDR_INVALID); 1162 KASSERT(new_m->m_data == M_BUFADDR(new_m)); 1163 pa += M_BUFOFFSET(new_m); 1164 } 1165 if (__predict_false(xengnt_grant_access( 1166 sc->sc_xbusd->xbusd_otherend_id, 1167 xpmap_ptom_masked(pa), 1168 GNTMAP_readonly, &req->txreq_gntref) != 0)) { 1169 m_freem(new_m); 1170 ifp->if_flags |= IFF_OACTIVE; 1171 break; 1172 } 1173 /* we will be able to send new_m */ 1174 IFQ_DEQUEUE(&ifp->if_snd, m); 1175 m_freem(m); 1176 m = new_m; 1177 } else { 1178 if (__predict_false(xengnt_grant_access( 1179 sc->sc_xbusd->xbusd_otherend_id, 1180 xpmap_ptom_masked(pa), 1181 GNTMAP_readonly, &req->txreq_gntref) != 0)) { 1182 ifp->if_flags |= IFF_OACTIVE; 1183 break; 1184 } 1185 /* we will be able to send m */ 1186 IFQ_DEQUEUE(&ifp->if_snd, m); 1187 } 1188 MCLAIM(m, &sc->sc_ethercom.ec_tx_mowner); 1189 1190 KASSERT(((pa ^ (pa + m->m_pkthdr.len - 1)) & PG_FRAME) == 0); 1191 1192 SLIST_REMOVE_HEAD(&sc->sc_txreq_head, txreq_next); 1193 req->txreq_m = m; 1194 1195 DPRINTFN(XEDB_MBUF, ("xennet_start id %d, " 1196 "mbuf %p, buf %p/%p/%p, size %d\n", 1197 req->txreq_id, m, mtod(m, void *), (void *)pa, 1198 (void *)xpmap_ptom_masked(pa), m->m_pkthdr.len)); 1199 pmap_extract_ma(pmap_kernel(), mtod(m, vaddr_t), &pa2); 1200 DPRINTFN(XEDB_MBUF, ("xennet_start pa %p ma %p/%p\n", 1201 (void *)pa, (void *)xpmap_ptom_masked(pa), (void *)pa2)); 1202 #ifdef XENNET_DEBUG_DUMP 1203 xennet_hex_dump(mtod(m, u_char *), m->m_pkthdr.len, "s", 1204 req->txreq_id); 1205 #endif 1206 1207 txreq = RING_GET_REQUEST(&sc->sc_tx_ring, req_prod); 1208 txreq->id = req->txreq_id; 1209 txreq->gref = req->txreq_gntref; 1210 txreq->offset = pa & ~PG_FRAME; 1211 txreq->size = m->m_pkthdr.len; 1212 txreq->flags = txflags; 1213 1214 req_prod++; 1215 sc->sc_tx_ring.req_prod_pvt = req_prod; 1216 RING_PUSH_REQUESTS_AND_CHECK_NOTIFY(&sc->sc_tx_ring, notify); 1217 if (notify) 1218 do_notify = 1; 1219 1220 #ifdef XENNET_DEBUG 1221 DPRINTFN(XEDB_MEM, ("packet addr %p/%p, physical %p/%p, " 1222 "m_paddr %p, len %d/%d\n", M_BUFADDR(m), mtod(m, void *), 1223 (void *)*kvtopte(mtod(m, vaddr_t)), 1224 (void *)xpmap_mtop(*kvtopte(mtod(m, vaddr_t))), 1225 (void *)m->m_paddr, m->m_pkthdr.len, m->m_len)); 1226 DPRINTFN(XEDB_MEM, ("id %d gref %d offset %d size %d flags %d" 1227 " prod %d\n", 1228 txreq->id, txreq->gref, txreq->offset, txreq->size, 1229 txreq->flags, req_prod)); 1230 #endif 1231 1232 /* 1233 * Pass packet to bpf if there is a listener. 1234 */ 1235 bpf_mtap(ifp, m); 1236 } 1237 1238 if (do_notify) { 1239 hypervisor_notify_via_evtchn(sc->sc_evtchn); 1240 ifp->if_timer = 5; 1241 } 1242 splx(s); 1243 1244 DPRINTFN(XEDB_FOLLOW, ("%s: xennet_start() done\n", 1245 device_xname(sc->sc_dev))); 1246 } 1247 1248 int 1249 xennet_ioctl(struct ifnet *ifp, u_long cmd, void *data) 1250 { 1251 #ifdef XENNET_DEBUG 1252 struct xennet_xenbus_softc *sc = ifp->if_softc; 1253 #endif 1254 int s, error = 0; 1255 1256 s = splnet(); 1257 1258 DPRINTFN(XEDB_FOLLOW, ("%s: xennet_ioctl()\n", 1259 device_xname(sc->sc_dev))); 1260 error = ether_ioctl(ifp, cmd, data); 1261 if (error == ENETRESET) 1262 error = 0; 1263 splx(s); 1264 1265 DPRINTFN(XEDB_FOLLOW, ("%s: xennet_ioctl() returning %d\n", 1266 device_xname(sc->sc_dev), error)); 1267 1268 return error; 1269 } 1270 1271 void 1272 xennet_watchdog(struct ifnet *ifp) 1273 { 1274 aprint_verbose_ifnet(ifp, "xennet_watchdog\n"); 1275 } 1276 1277 int 1278 xennet_init(struct ifnet *ifp) 1279 { 1280 struct xennet_xenbus_softc *sc = ifp->if_softc; 1281 int s = splnet(); 1282 1283 DPRINTFN(XEDB_FOLLOW, ("%s: xennet_init()\n", 1284 device_xname(sc->sc_dev))); 1285 1286 if ((ifp->if_flags & IFF_RUNNING) == 0) { 1287 sc->sc_rx_ring.sring->rsp_event = 1288 sc->sc_rx_ring.rsp_cons + 1; 1289 hypervisor_enable_event(sc->sc_evtchn); 1290 hypervisor_notify_via_evtchn(sc->sc_evtchn); 1291 xennet_reset(sc); 1292 } 1293 ifp->if_flags |= IFF_RUNNING; 1294 ifp->if_flags &= ~IFF_OACTIVE; 1295 ifp->if_timer = 0; 1296 splx(s); 1297 return 0; 1298 } 1299 1300 void 1301 xennet_stop(struct ifnet *ifp, int disable) 1302 { 1303 struct xennet_xenbus_softc *sc = ifp->if_softc; 1304 int s = splnet(); 1305 1306 ifp->if_flags &= ~(IFF_RUNNING | IFF_OACTIVE); 1307 hypervisor_mask_event(sc->sc_evtchn); 1308 xennet_reset(sc); 1309 splx(s); 1310 } 1311 1312 void 1313 xennet_reset(struct xennet_xenbus_softc *sc) 1314 { 1315 1316 DPRINTFN(XEDB_FOLLOW, ("%s: xennet_reset()\n", 1317 device_xname(sc->sc_dev))); 1318 } 1319 1320 #if defined(NFS_BOOT_BOOTSTATIC) 1321 int 1322 xennet_bootstatic_callback(struct nfs_diskless *nd) 1323 { 1324 #if 0 1325 struct ifnet *ifp = nd->nd_ifp; 1326 struct xennet_xenbus_softc *sc = 1327 (struct xennet_xenbus_softc *)ifp->if_softc; 1328 #endif 1329 int flags = 0; 1330 union xen_cmdline_parseinfo xcp; 1331 struct sockaddr_in *sin; 1332 1333 memset(&xcp, 0, sizeof(xcp.xcp_netinfo)); 1334 xcp.xcp_netinfo.xi_ifno = /* XXX sc->sc_ifno */ 0; 1335 xcp.xcp_netinfo.xi_root = nd->nd_root.ndm_host; 1336 xen_parse_cmdline(XEN_PARSE_NETINFO, &xcp); 1337 1338 if (xcp.xcp_netinfo.xi_root[0] != '\0') { 1339 flags |= NFS_BOOT_HAS_SERVER; 1340 if (strchr(xcp.xcp_netinfo.xi_root, ':') != NULL) 1341 flags |= NFS_BOOT_HAS_ROOTPATH; 1342 } 1343 1344 nd->nd_myip.s_addr = ntohl(xcp.xcp_netinfo.xi_ip[0]); 1345 nd->nd_gwip.s_addr = ntohl(xcp.xcp_netinfo.xi_ip[2]); 1346 nd->nd_mask.s_addr = ntohl(xcp.xcp_netinfo.xi_ip[3]); 1347 1348 sin = (struct sockaddr_in *) &nd->nd_root.ndm_saddr; 1349 memset((void *)sin, 0, sizeof(*sin)); 1350 sin->sin_len = sizeof(*sin); 1351 sin->sin_family = AF_INET; 1352 sin->sin_addr.s_addr = ntohl(xcp.xcp_netinfo.xi_ip[1]); 1353 1354 if (nd->nd_myip.s_addr) 1355 flags |= NFS_BOOT_HAS_MYIP; 1356 if (nd->nd_gwip.s_addr) 1357 flags |= NFS_BOOT_HAS_GWIP; 1358 if (nd->nd_mask.s_addr) 1359 flags |= NFS_BOOT_HAS_MASK; 1360 if (sin->sin_addr.s_addr) 1361 flags |= NFS_BOOT_HAS_SERVADDR; 1362 1363 return flags; 1364 } 1365 #endif /* defined(NFS_BOOT_BOOTSTATIC) */ 1366 1367 #ifdef XENNET_DEBUG_DUMP 1368 #define XCHR(x) hexdigits[(x) & 0xf] 1369 static void 1370 xennet_hex_dump(const unsigned char *pkt, size_t len, const char *type, int id) 1371 { 1372 size_t i, j; 1373 1374 printf("pkt %p len %zd/%zx type %s id %d\n", pkt, len, len, type, id); 1375 printf("00000000 "); 1376 for(i=0; i<len; i++) { 1377 printf("%c%c ", XCHR(pkt[i]>>4), XCHR(pkt[i])); 1378 if ((i+1) % 16 == 8) 1379 printf(" "); 1380 if ((i+1) % 16 == 0) { 1381 printf(" %c", '|'); 1382 for(j=0; j<16; j++) 1383 printf("%c", pkt[i-15+j]>=32 && 1384 pkt[i-15+j]<127?pkt[i-15+j]:'.'); 1385 printf("%c\n%c%c%c%c%c%c%c%c ", '|', 1386 XCHR((i+1)>>28), XCHR((i+1)>>24), 1387 XCHR((i+1)>>20), XCHR((i+1)>>16), 1388 XCHR((i+1)>>12), XCHR((i+1)>>8), 1389 XCHR((i+1)>>4), XCHR(i+1)); 1390 } 1391 } 1392 printf("\n"); 1393 } 1394 #undef XCHR 1395 #endif 1396