ia64/xen-unstable

changeset 14202:42aa0100574b

hvm: Clean up console-information passing via xenstore.

Each serial, parallel and monitor device in qemu that is connected to
a pty creates a xenstore node of the form:
<domain-path>/monitor/tty
<domain-path>/serial/<n>/tty
<domain-path>/parallel/<n>/tty

In addition, serial/0 (com1) also registers its information at:
<domain-path>/console/tty

Also fix a realloc() failure memory leak.

Signed-off-by: Ben Thomas <ben@virtualiron.com>
author kfraser@localhost.localdomain
date Thu Mar 01 13:57:25 2007 +0000 (2007-03-01)
parents 780ef7701772
children beabac411220
files tools/ioemu/vl.c
line diff
     1.1 --- a/tools/ioemu/vl.c	Thu Mar 01 13:48:31 2007 +0000
     1.2 +++ b/tools/ioemu/vl.c	Thu Mar 01 13:57:25 2007 +0000
     1.3 @@ -1565,12 +1565,51 @@ CharDriverState *qemu_chr_open_stdio(voi
     1.4      return chr;
     1.5  }
     1.6  
     1.7 -int store_console_dev(int domid, char *pts)
     1.8 +/*
     1.9 + * Create a store entry for a device (e.g., monitor, serial/parallel lines).
    1.10 + * The entry is <domain-path><storeString>/tty and the value is the name
    1.11 + * of the pty associated with the device.
    1.12 + */
    1.13 +static int store_dev_info(char *devName, int domid,
    1.14 +                          CharDriverState *cState, char *storeString)
    1.15  {
    1.16      int xc_handle;
    1.17      struct xs_handle *xs;
    1.18      char *path;
    1.19 -
    1.20 +    char *newpath;
    1.21 +    FDCharDriver *s;
    1.22 +    char *pts;
    1.23 +
    1.24 +    /* Check for valid arguments (at least, prevent segfaults). */
    1.25 +    if ((devName == NULL) || (cState == NULL) || (storeString == NULL)) {
    1.26 +        fprintf(logfile, "%s - invalid arguments\n", __FUNCTION__);
    1.27 +        return EINVAL;
    1.28 +    }
    1.29 +
    1.30 +    /*
    1.31 +     * Only continue if we're talking to a pty
    1.32 +     * Actually, the following code works for any CharDriverState using
    1.33 +     * FDCharDriver, but we really only care about pty's here
    1.34 +     */
    1.35 +    if (strcmp(devName, "pty"))
    1.36 +        return 0;
    1.37 +
    1.38 +    s = cState->opaque;
    1.39 +    if (s == NULL) {
    1.40 +        fprintf(logfile, "%s - unable to retrieve fd for '%s'/'%s'\n",
    1.41 +                __FUNCTION__, storeString, devName);
    1.42 +        return EBADF;
    1.43 +    }
    1.44 +
    1.45 +    pts = ptsname(s->fd_in);
    1.46 +    if (pts == NULL) {
    1.47 +        fprintf(logfile, "%s - unable to determine ptsname '%s'/'%s', "
    1.48 +                "error %d (%s)\n",
    1.49 +                __FUNCTION__, storeString, devName, errno, strerror(errno));
    1.50 +        return errno;
    1.51 +    }
    1.52 +
    1.53 +    /* We now have everything we need to set the xenstore entry. */
    1.54      xs = xs_daemon_open();
    1.55      if (xs == NULL) {
    1.56          fprintf(logfile, "Could not contact XenStore\n");
    1.57 @@ -1588,14 +1627,19 @@ int store_console_dev(int domid, char *p
    1.58          fprintf(logfile, "xs_get_domain_path() error\n");
    1.59          return -1;
    1.60      }
    1.61 -    path = realloc(path, strlen(path) + strlen("/console/tty") + 1);
    1.62 -    if (path == NULL) {
    1.63 +    newpath = realloc(path, (strlen(path) + strlen(storeString) +
    1.64 +                             strlen("/tty") + 1));
    1.65 +    if (newpath == NULL) {
    1.66 +        free(path); /* realloc errors leave old block */
    1.67          fprintf(logfile, "realloc error\n");
    1.68          return -1;
    1.69      }
    1.70 -    strcat(path, "/console/tty");
    1.71 +    path = newpath;
    1.72 +
    1.73 +    strcat(path, storeString);
    1.74 +    strcat(path, "/tty");
    1.75      if (!xs_write(xs, XBT_NULL, path, pts, strlen(pts))) {
    1.76 -        fprintf(logfile, "xs_write for console fail");
    1.77 +        fprintf(logfile, "xs_write for '%s' fail", storeString);
    1.78          return -1;
    1.79      }
    1.80  
    1.81 @@ -1622,7 +1666,6 @@ CharDriverState *qemu_chr_open_pty(void)
    1.82      tcsetattr(slave_fd, TCSAFLUSH, &tty);
    1.83      
    1.84      fprintf(stderr, "char device redirected to %s\n", ptsname(master_fd));
    1.85 -    store_console_dev(domid, ptsname(master_fd));
    1.86  
    1.87      return qemu_chr_open_fd(master_fd, master_fd);
    1.88  }
    1.89 @@ -6694,16 +6737,23 @@ int main(int argc, char **argv)
    1.90          fprintf(stderr, "qemu: could not open monitor device '%s'\n", monitor_device);
    1.91          exit(1);
    1.92      }
    1.93 +    store_dev_info(monitor_device, domid, monitor_hd, "/monitor");
    1.94      monitor_init(monitor_hd, !nographic);
    1.95  
    1.96      for(i = 0; i < MAX_SERIAL_PORTS; i++) {
    1.97          if (serial_devices[i][0] != '\0') {
    1.98 +            char buf[16];
    1.99              serial_hds[i] = qemu_chr_open(serial_devices[i]);
   1.100              if (!serial_hds[i]) {
   1.101                  fprintf(stderr, "qemu: could not open serial device '%s'\n", 
   1.102                          serial_devices[i]);
   1.103                  exit(1);
   1.104              }
   1.105 +            snprintf(buf, sizeof(buf), "/serial/%d", i);
   1.106 +            store_dev_info(serial_devices[i], domid, serial_hds[i], buf);
   1.107 +            if (i == 0) /* serial 0 is also called the console */
   1.108 +                store_dev_info(serial_devices[i], domid,
   1.109 +                               serial_hds[i], "/console");
   1.110              if (!strcmp(serial_devices[i], "vc"))
   1.111                  qemu_chr_printf(serial_hds[i], "serial%d console\r\n", i);
   1.112          }
   1.113 @@ -6711,12 +6761,15 @@ int main(int argc, char **argv)
   1.114  
   1.115      for(i = 0; i < MAX_PARALLEL_PORTS; i++) {
   1.116          if (parallel_devices[i][0] != '\0') {
   1.117 +            char buf[16];
   1.118              parallel_hds[i] = qemu_chr_open(parallel_devices[i]);
   1.119              if (!parallel_hds[i]) {
   1.120                  fprintf(stderr, "qemu: could not open parallel device '%s'\n", 
   1.121                          parallel_devices[i]);
   1.122                  exit(1);
   1.123              }
   1.124 +            snprintf(buf, sizeof(buf), "/parallel/%d", i);
   1.125 +            store_dev_info(parallel_devices[i], domid, parallel_hds[i], buf);
   1.126              if (!strcmp(parallel_devices[i], "vc"))
   1.127                  qemu_chr_printf(parallel_hds[i], "parallel%d console\r\n", i);
   1.128          }