summaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
authorMichael Brown2007-01-08 04:45:00 +0100
committerMichael Brown2007-01-08 04:45:00 +0100
commit075d79f6d4ee0725dd118cf291959221e7e681d8 (patch)
treedb0049e34bcb688621ba3fd36ff31f9e07b1f36f /src
parentNeaten up debug messages (diff)
downloadipxe-075d79f6d4ee0725dd118cf291959221e7e681d8.tar.gz
ipxe-075d79f6d4ee0725dd118cf291959221e7e681d8.tar.xz
ipxe-075d79f6d4ee0725dd118cf291959221e7e681d8.zip
Checking in obsolete but working memory-scanning code just for the record
Diffstat (limited to 'src')
-rw-r--r--src/arch/i386/drivers/bus/pxebus.c263
1 files changed, 70 insertions, 193 deletions
diff --git a/src/arch/i386/drivers/bus/pxebus.c b/src/arch/i386/drivers/bus/pxebus.c
index 7ad3b6aad..4876fa2ab 100644
--- a/src/arch/i386/drivers/bus/pxebus.c
+++ b/src/arch/i386/drivers/bus/pxebus.c
@@ -1,3 +1,5 @@
+#if 0
+
/*
* Copyright (C) 2007 Michael Brown <mbrown@fensystems.co.uk>.
*
@@ -22,7 +24,10 @@
#include <assert.h>
#include <pxe.h>
#include <realmode.h>
+#include <bios.h>
+#include <pnpbios.h>
#include <gpxe/device.h>
+#include <gpxe/pci.h>
/** @file
*
@@ -31,84 +36,6 @@
*/
/**
- * UNDI parameter block
- *
- * Used as the paramter block for all UNDI API calls. Resides in base
- * memory.
- */
-static union u_PXENV_ANY __data16 ( pxe_params );
-#define pxe_params __use_data16 ( pxe_params )
-
-/** UNDI entry point */
-static SEGOFF16_t __data16 ( pxe_entry_point );
-#define pxe_entry_point __use_data16 ( pxe_entry_point )
-
-/**
- * Issue PXE API call
- *
- * @v pxe PXE device
- * @v function API call number
- * @v params PXE parameter block
- * @v params_len Length of PXE parameter block
- * @ret rc Return status code
- */
-int pxe_call ( struct pxe_device *pxe, unsigned int function,
- void *params, size_t params_len ) {
- union u_PXENV_ANY *pxenv_any = params;
- PXENV_EXIT_t exit;
- int discard_b, discard_D;
- int rc;
-
- /* Copy parameter block and entry point */
- assert ( params_len <= sizeof ( pxe_params ) );
- memcpy ( &pxe_params, params, params_len );
- pxe_entry_point = pxe->entry;
-
- /* Call real-mode entry point. This calling convention will
- * work with both the !PXE and the PXENV+ entry points.
- */
- __asm__ __volatile__ ( REAL_CODE ( "pushw %%es\n\t"
- "pushw %%di\n\t"
- "pushw %%bx\n\t"
- "lcall *%c3\n\t"
- "addw $6, %%sp\n\t" )
- : "=a" ( exit ), "=b" ( discard_b ),
- "=D" ( discard_D )
- : "p" ( & __from_data16 ( pxe_entry_point ) ),
- "b" ( function ),
- "D" ( & __from_data16 ( pxe_params ) ) );
-
- /* UNDI API calls may rudely change the status of A20 and not
- * bother to restore it afterwards. Intel is known to be
- * guilty of this.
- *
- * Note that we will return to this point even if A20 gets
- * screwed up by the UNDI driver, because Etherboot always
- * resides in an even megabyte of RAM.
- */
- gateA20_set();
-
- /* Copy parameter block back */
- memcpy ( params, &pxe_params, params_len );
-
- /* Determine return status code based on PXENV_EXIT and
- * PXENV_STATUS
- */
- if ( exit == PXENV_EXIT_SUCCESS ) {
- rc = 0;
- } else {
- rc = -pxenv_any->Status;
- /* Paranoia; don't return success for the combination
- * of PXENV_EXIT_FAILURE but PXENV_STATUS_SUCCESS
- */
- if ( rc == 0 )
- rc = -EIO;
- }
-
- return rc;
-}
-
-/**
* Byte checksum
*
* @v data Data to checksum
@@ -126,82 +53,6 @@ static uint8_t checksum ( void *data, size_t len ) {
}
/**
- * Get PXE device information for an instantiated device
- *
- * @v pxe PXE device
- * @ret rc Return status code
- */
-static int pxedev_get_instance_info ( struct pxe_device *pxe ) {
- struct s_PXENV pxenv;
- struct s_PXE ppxe;
- struct s_PXENV_UNDI_GET_INFORMATION undi_info;
- int rc;
-
- /* Determine entry point from PXENV+ structure */
- DBGC ( pxe, "PXE %p has PXENV+ structure at %04x:%04x\n", pxe,
- pxe->pxenv.segment, pxe->pxenv.offset );
- copy_from_real ( &pxenv, pxe->pxenv.segment, pxe->pxenv.offset,
- sizeof ( pxenv ) );
- if ( checksum ( &pxenv, sizeof ( pxenv ) ) != 0 ) {
- DBGC ( pxe, "PXE %p bad PXENV+ checksum\n", pxe );
- return -EINVAL;
- }
- pxe->entry = pxenv.RMEntry;
-
- /* If API version is 2.1 or greater, use the !PXE structure instead */
- if ( pxenv.Version >= 0x0201 ) {
- pxe->ppxe = pxenv.PXEPtr;
- DBGC ( pxe, "PXE %p has !PXE structure at %04x:%04x\n", pxe,
- pxe->ppxe.segment, pxe->ppxe.offset );
- copy_from_real ( &ppxe, pxe->ppxe.segment, pxe->ppxe.offset,
- sizeof ( ppxe ) );
- if ( checksum ( &pxenv, sizeof ( pxenv ) ) != 0 ) {
- DBGC ( pxe, "PXE %p bad !PXE checksum\n", pxe );
- return -EINVAL;
- }
- pxe->entry = ppxe.EntryPointSP;
- }
-
- DBGC ( pxe, "PXE %p using entry point at %04x:%04x\n", pxe,
- pxe->entry.segment, pxe->entry.offset );
-
- /* Get device information */
- memset ( &undi_info, 0, sizeof ( undi_info ) );
- if ( ( rc = pxe_call ( pxe, PXENV_UNDI_GET_INFORMATION, &undi_info,
- sizeof ( undi_info ) ) ) != 0 ) {
- DBGC ( pxe, "PXE %p could not retrieve UNDI information: %s\n",
- pxe, strerror ( rc ) );
- return rc;
- }
- memcpy ( pxe->hwaddr, undi_info.PermNodeAddress,
- sizeof ( pxe->hwaddr ) );
- pxe->irq = undi_info.IntNumber;
- pxe->rom_segment = undi_info.ROMAddress;
-
- return 0;
-}
-
-/**
- * Register PXE device
- *
- * @v pxe PXE device
- * @ret rc Return status code
- */
-static int register_pxedev ( struct pxe_device *pxe ) {
- int rc;
-
- DBGC ( pxe, "PXE %p registering\n", pxe );
-
- /* Register as an UNDI driver */
- if ( ( rc = undi_probe ( pxe ) ) != 0 )
- return rc;
-
- /* Add to device hierarchy and return */
- list_add ( &pxe->dev.siblings, &pxe->dev.parent->children );
- return 0;
-}
-
-/**
* Unregister a PXE device
*
* @v pxe PXE device
@@ -224,47 +75,74 @@ static void pxebus_remove ( struct root_device *rootdev );
* find.
*/
static int pxebus_probe ( struct root_device *rootdev ) {
- struct pxe_device *pxe;
- uint16_t signature;
- uint16_t pxenv_segment;
- uint16_t pxenv_offset;
+ struct pxe_device *pxe = NULL;
+ struct s_PXENV pxenv;
+ struct s_PXE ppxe;
+ uint16_t fbms;
+ unsigned int segment;
+ unsigned int undi_cs;
int rc;
- /* PXE installation check */
- __asm__ __volatile__ ( REAL_CODE ( "stc\n\t"
- "int $0x1a\n\t"
- "jnc 1f\n\t"
- "xorw %%ax, %%ax\n\t"
- "\n1:\n\t"
- "movw %%es, %%dx\n\t" )
- : "=a" ( signature ), "=b" ( pxenv_offset ),
- "=d" ( pxenv_segment )
- : "a" ( 0x5650 ) );
- if ( signature != 0x564e ) {
- DBG ( "No pixies found\n" );
- return 0;
- }
-
- /* Allocate PXE device structure */
- pxe = malloc ( sizeof ( *pxe ) );
- if ( ! pxe ) {
- rc = -ENOMEM;
- goto err;
- }
- memset ( pxe, 0, sizeof ( *pxe ) );
+ /* Scan through allocated base memory for PXENV+ structure */
+ get_real ( fbms, BDA_SEG, BDA_FBMS );
+ for ( segment = ( fbms << 6 ) ; segment < 0xa000 ; segment++ ) {
- /* Populate PXE device structure */
- pxe->pxenv.segment = pxenv_segment;
- pxe->pxenv.offset = pxenv_offset;
- INIT_LIST_HEAD ( &pxe->dev.children );
- pxe->dev.parent = &rootdev->dev;
- if ( ( rc = pxedev_get_instance_info ( pxe ) ) != 0 )
- goto err;
+ /* Verify PXENV+ signature and checksum */
+ copy_from_real ( &pxenv, segment, 0, sizeof ( pxenv ) );
+ if ( memcmp ( pxenv.Signature, "PXENV+", 6 ) != 0 )
+ continue;
+ DBG ( "Found PXENV+ signature at %04x0\n", segment );
+ if ( checksum ( &pxenv, sizeof ( pxenv ) ) != 0 ) {
+ DBG ( "...bad checksum\n" );
+ continue;
+ }
- /* Register PXE device */
- if ( ( rc = register_pxedev ( pxe ) ) != 0 )
- goto err;
+ /* Allocate PXE device structure */
+ pxe = malloc ( sizeof ( *pxe ) );
+ if ( ! pxe ) {
+ rc = -ENOMEM;
+ goto err;
+ }
+ memset ( pxe, 0, sizeof ( *pxe ) );
+
+ /* Add to device hierarchy */
+ pxe->dev.parent = &rootdev->dev;
+ INIT_LIST_HEAD ( &pxe->dev.children );
+ list_add ( &pxe->dev.siblings, &rootdev->dev.children );
+
+ /* Populate PXE device structure */
+ undi_cs = pxenv.UNDICodeSeg;
+ pxe->pxenv.segment = undi_cs;
+ pxe->pxenv.offset = ( ( segment - undi_cs ) << 4 );
+ DBGC ( pxe, "PXE %p has PXENV+ structure at %04x:%04x\n",
+ pxe, pxe->pxenv.segment, pxe->pxenv.offset );
+ pxe->entry = pxenv.RMEntry;
+ if ( pxenv.Version >= 0x0201 ) {
+ pxe->ppxe = pxenv.PXEPtr;
+ copy_from_real ( &ppxe, pxe->ppxe.segment,
+ pxe->ppxe.offset, sizeof ( ppxe ) );
+ if ( ( memcmp ( ppxe.Signature, "!PXE", 4 ) == 0 ) &&
+ ( checksum ( &ppxe, sizeof ( ppxe ) ) == 0 ) ) {
+ DBGC ( pxe, "PXE %p has !PXE structure at "
+ "%04x:%04x\n", pxe,
+ pxe->ppxe.segment, pxe->ppxe.offset );
+ pxe->entry = ppxe.EntryPointSP;
+ }
+ }
+ DBGC ( pxe, "PXE %p using entry point at %04x:%04x\n", pxe,
+ pxe->entry.segment, pxe->entry.offset );
+
+ /* Register PXE device */
+ if ( undi_probe ( pxe ) == 0 ) {
+ /* Device registered; drop reference */
+ pxe = NULL;
+ } else {
+ /* Not registered; re-use struct pxe_device */
+ list_del ( &pxe->dev.siblings );
+ }
+ }
+ free ( pxe );
return 0;
err:
@@ -299,7 +177,6 @@ static struct root_driver pxe_root_driver = {
struct root_device pxe_root_device __root_device = {
.name = "PXE",
.driver = &pxe_root_driver,
- .dev = {
- .children = LIST_HEAD_INIT ( pxe_root_device.dev.children ),
- },
};
+
+#endif