1 #include <stdint.h> 2 #include <string.h> 3 #include <stdlib.h> 4 #include <stdio.h> 5 #include <errno.h> 6 #include <gpxe/iscsi.h> 7 #include <gpxe/netdevice.h> 8 #include <gpxe/ibft.h> 9 #include <gpxe/sanboot.h> 10 #include <int13.h> 11 12 FILE_LICENCE ( GPL2_OR_LATER ); 13 14 static int iscsiboot ( const char *root_path ) { 15 struct scsi_device *scsi; 16 struct int13_drive *drive; 17 int rc; 18 19 scsi = zalloc ( sizeof ( *scsi ) ); 20 if ( ! scsi ) { 21 rc = -ENOMEM; 22 goto err_alloc_scsi; 23 } 24 drive = zalloc ( sizeof ( *drive ) ); 25 if ( ! drive ) { 26 rc = -ENOMEM; 27 goto err_alloc_drive; 28 } 29 30 if ( ( rc = iscsi_attach ( scsi, root_path ) ) != 0 ) { 31 printf ( "Could not attach iSCSI device: %s\n", 32 strerror ( rc ) ); 33 goto err_attach; 34 } 35 if ( ( rc = init_scsidev ( scsi ) ) != 0 ) { 36 printf ( "Could not initialise iSCSI device: %s\n", 37 strerror ( rc ) ); 38 goto err_init; 39 } 40 41 drive->blockdev = &scsi->blockdev; 42 43 /* FIXME: ugly, ugly hack */ 44 struct net_device *netdev = last_opened_netdev(); 45 struct iscsi_session *iscsi = 46 container_of ( scsi->backend, struct iscsi_session, refcnt ); 47 ibft_fill_data ( netdev, iscsi ); 48 49 register_int13_drive ( drive ); 50 printf ( "Registered as BIOS drive %#02x\n", drive->drive ); 51 printf ( "Booting from BIOS drive %#02x\n", drive->drive ); 52 rc = int13_boot ( drive->drive ); 53 printf ( "Boot failed\n" ); 54 55 /* Leave drive registered, if instructed to do so */ 56 if ( keep_san() ) 57 return rc; 58 59 printf ( "Unregistering BIOS drive %#02x\n", drive->drive ); 60 unregister_int13_drive ( drive ); 61 62 err_init: 63 iscsi_detach ( scsi ); 64 err_attach: 65 free ( drive ); 66 err_alloc_drive: 67 free ( scsi ); 68 err_alloc_scsi: 69 return rc; 70 } 71 72 struct sanboot_protocol iscsi_sanboot_protocol __sanboot_protocol = { 73 .prefix = "iscsi:", 74 .boot = iscsiboot, 75 }; 76