1*2912Sartem /*************************************************************************** 2*2912Sartem * 3*2912Sartem * osspec.c : Solaris HAL backend entry points 4*2912Sartem * 5*2912Sartem * Copyright 2006 Sun Microsystems, Inc. All rights reserved. 6*2912Sartem * Use is subject to license terms. 7*2912Sartem * 8*2912Sartem * Licensed under the Academic Free License version 2.1 9*2912Sartem * 10*2912Sartem **************************************************************************/ 11*2912Sartem 12*2912Sartem #pragma ident "%Z%%M% %I% %E% SMI" 13*2912Sartem 14*2912Sartem #ifdef HAVE_CONFIG_H 15*2912Sartem # include <config.h> 16*2912Sartem #endif 17*2912Sartem 18*2912Sartem #include <stdio.h> 19*2912Sartem #include <unistd.h> 20*2912Sartem #include <strings.h> 21*2912Sartem #include <port.h> 22*2912Sartem #include <sys/stat.h> 23*2912Sartem #include <fcntl.h> 24*2912Sartem #include <sys/types.h> 25*2912Sartem #include <sys/mntent.h> 26*2912Sartem #include <sys/mnttab.h> 27*2912Sartem 28*2912Sartem #include "../osspec.h" 29*2912Sartem #include "../logger.h" 30*2912Sartem #include "../hald.h" 31*2912Sartem #include "../hald_dbus.h" 32*2912Sartem #include "../device_info.h" 33*2912Sartem #include "../util.h" 34*2912Sartem #include "../ids.h" 35*2912Sartem #include "osspec_solaris.h" 36*2912Sartem #include "hotplug.h" 37*2912Sartem #include "sysevent.h" 38*2912Sartem #include "devinfo.h" 39*2912Sartem #include "devinfo_storage.h" 40*2912Sartem 41*2912Sartem static void mnttab_event_init (); 42*2912Sartem static gboolean mnttab_event (GIOChannel *channel, GIOCondition cond, gpointer user_data); 43*2912Sartem 44*2912Sartem void 45*2912Sartem osspec_init (void) 46*2912Sartem { 47*2912Sartem ids_init (); 48*2912Sartem sysevent_init (); 49*2912Sartem mnttab_event_init (); 50*2912Sartem } 51*2912Sartem 52*2912Sartem void 53*2912Sartem hotplug_queue_now_empty (void) 54*2912Sartem { 55*2912Sartem if (hald_is_initialising) { 56*2912Sartem osspec_probe_done (); 57*2912Sartem } 58*2912Sartem } 59*2912Sartem 60*2912Sartem void 61*2912Sartem osspec_probe (void) 62*2912Sartem { 63*2912Sartem /* add entire device tree */ 64*2912Sartem devinfo_add (NULL, "/"); 65*2912Sartem 66*2912Sartem /* start processing events */ 67*2912Sartem hotplug_event_process_queue (); 68*2912Sartem } 69*2912Sartem 70*2912Sartem gboolean 71*2912Sartem osspec_device_rescan (HalDevice *d) 72*2912Sartem { 73*2912Sartem return (devinfo_device_rescan (d)); 74*2912Sartem } 75*2912Sartem 76*2912Sartem gboolean 77*2912Sartem osspec_device_reprobe (HalDevice *d) 78*2912Sartem { 79*2912Sartem return FALSE; 80*2912Sartem } 81*2912Sartem 82*2912Sartem DBusHandlerResult 83*2912Sartem osspec_filter_function (DBusConnection *connection, DBusMessage *message, void *user_data) 84*2912Sartem { 85*2912Sartem return DBUS_HANDLER_RESULT_NOT_YET_HANDLED; 86*2912Sartem } 87*2912Sartem 88*2912Sartem /** Find the closest ancestor by looking at devfs paths 89*2912Sartem * 90*2912Sartem * @param devfs_path Path into devfs, e.g. /pci@0,0/pci1025,57@10,2/storage@1 91*2912Sartem * @return Parent Hal Device Object or #NULL if there is none 92*2912Sartem */ 93*2912Sartem HalDevice * 94*2912Sartem hal_util_find_closest_ancestor (const gchar *devfs_path, gchar **ancestor_devfs_path, gchar **hotplug_devfs_path) 95*2912Sartem { 96*2912Sartem gchar buf[512]; 97*2912Sartem gchar c; 98*2912Sartem HalDevice *parent; 99*2912Sartem 100*2912Sartem parent = NULL; 101*2912Sartem 102*2912Sartem strncpy (buf, devfs_path, sizeof (buf)); 103*2912Sartem do { 104*2912Sartem char *p; 105*2912Sartem 106*2912Sartem p = strrchr (buf, '/'); 107*2912Sartem if (p == NULL) 108*2912Sartem break; 109*2912Sartem c = *p; 110*2912Sartem *p = '\0'; 111*2912Sartem 112*2912Sartem parent = hal_device_store_match_key_value_string (hald_get_gdl (), 113*2912Sartem "solaris.devfs_path", 114*2912Sartem buf); 115*2912Sartem if (parent != NULL) { 116*2912Sartem if (ancestor_devfs_path != NULL) { 117*2912Sartem *ancestor_devfs_path = g_strdup (buf); 118*2912Sartem } 119*2912Sartem if (hotplug_devfs_path != NULL) { 120*2912Sartem *p = c; 121*2912Sartem *hotplug_devfs_path = g_strdup (buf); 122*2912Sartem } 123*2912Sartem break; 124*2912Sartem } 125*2912Sartem 126*2912Sartem } while (TRUE); 127*2912Sartem 128*2912Sartem return parent; 129*2912Sartem } 130*2912Sartem 131*2912Sartem char * 132*2912Sartem dsk_to_rdsk(char *dsk) 133*2912Sartem { 134*2912Sartem int len, pos; 135*2912Sartem char *p; 136*2912Sartem char *rdsk; 137*2912Sartem 138*2912Sartem if ((len = strlen (dsk)) < sizeof ("/dev/dsk/cN") - 1) { 139*2912Sartem return (strdup("")); 140*2912Sartem } 141*2912Sartem if ((p = strstr (dsk, "/dsk/")) == NULL) { 142*2912Sartem if ((p = strstr (dsk, "/lofi/")) == NULL) { 143*2912Sartem p = strstr (dsk, "/diskette"); 144*2912Sartem } 145*2912Sartem } 146*2912Sartem if (p == NULL) { 147*2912Sartem return (strdup("")); 148*2912Sartem } 149*2912Sartem 150*2912Sartem pos = (uintptr_t)p - (uintptr_t)dsk; 151*2912Sartem if ((rdsk = (char *)calloc (len + 2, 1)) != NULL) { 152*2912Sartem strncpy (rdsk, dsk, pos + 1); 153*2912Sartem rdsk[pos + 1] = 'r'; 154*2912Sartem strcpy (rdsk + pos + 2, dsk + pos + 1); 155*2912Sartem } 156*2912Sartem 157*2912Sartem return (rdsk); 158*2912Sartem } 159*2912Sartem 160*2912Sartem /* 161*2912Sartem * Setup to watch mnttab changes 162*2912Sartem * 163*2912Sartem * When mnttab changes, POLLRDBAND is set. However, glib does not 164*2912Sartem * support POLLRDBAND, so we use Solaris ports (see port_create(3C)) 165*2912Sartem * to "map" POLLRDBAND to POLLIN: 166*2912Sartem * 167*2912Sartem * - create a port 168*2912Sartem * - associate the port with mnttab file descriptor and POLLRDBAND 169*2912Sartem * - now polling for POLLIN on the port descriptor will unblock when 170*2912Sartem * the associated file descriptor receives POLLRDBAND 171*2912Sartem */ 172*2912Sartem static int mnttab_fd; 173*2912Sartem static int mnttab_port; 174*2912Sartem static GIOChannel *mnttab_channel; 175*2912Sartem 176*2912Sartem static void 177*2912Sartem mnttab_event_init () 178*2912Sartem { 179*2912Sartem char buf[81]; 180*2912Sartem 181*2912Sartem if ((mnttab_fd = open (MNTTAB, O_RDONLY)) < 0) { 182*2912Sartem return; 183*2912Sartem } 184*2912Sartem if ((mnttab_port = port_create ()) < 0) { 185*2912Sartem (void) close (mnttab_fd); 186*2912Sartem return; 187*2912Sartem } 188*2912Sartem if (port_associate (mnttab_port, PORT_SOURCE_FD, mnttab_fd, POLLRDBAND, 189*2912Sartem NULL) != 0) { 190*2912Sartem (void) close (mnttab_port); 191*2912Sartem (void) close (mnttab_fd); 192*2912Sartem return; 193*2912Sartem } 194*2912Sartem 195*2912Sartem /* suppress initial event */ 196*2912Sartem (void) read(mnttab_fd, buf, (size_t)(sizeof (buf) - 1)); 197*2912Sartem (void) lseek(mnttab_fd, 0, SEEK_SET); 198*2912Sartem 199*2912Sartem mnttab_channel = g_io_channel_unix_new (mnttab_port); 200*2912Sartem g_io_add_watch (mnttab_channel, G_IO_IN, mnttab_event, NULL); 201*2912Sartem } 202*2912Sartem 203*2912Sartem static gboolean 204*2912Sartem mnttab_event (GIOChannel *channel, GIOCondition cond, gpointer user_data) 205*2912Sartem { 206*2912Sartem port_event_t pe; 207*2912Sartem timespec_t timeout; 208*2912Sartem char buf[81]; 209*2912Sartem 210*2912Sartem /* if (cond & ~G_IO_ERR) 211*2912Sartem return TRUE; 212*2912Sartem */ 213*2912Sartem HAL_INFO (("mnttab event")); 214*2912Sartem 215*2912Sartem /* we have to re-associate port with fd every time */ 216*2912Sartem timeout.tv_sec = timeout.tv_nsec = 0; 217*2912Sartem (void) port_get(mnttab_port, &pe, &timeout); 218*2912Sartem (void) port_associate(mnttab_port, PORT_SOURCE_FD, 219*2912Sartem mnttab_fd, POLLRDBAND, NULL); 220*2912Sartem 221*2912Sartem if (!hald_is_initialising) { 222*2912Sartem devinfo_storage_mnttab_event (NULL); 223*2912Sartem } 224*2912Sartem 225*2912Sartem (void) lseek(mnttab_fd, 0, SEEK_SET); 226*2912Sartem (void) read(mnttab_fd, buf, (size_t)(sizeof (buf) - 1)); 227*2912Sartem 228*2912Sartem return TRUE; 229*2912Sartem } 230*2912Sartem 231*2912Sartem void 232*2912Sartem osspec_refresh_mount_state_for_block_device (HalDevice *d) 233*2912Sartem { 234*2912Sartem devinfo_storage_mnttab_event (d); 235*2912Sartem } 236