osPfsInitPak osPfsInitPak (function)

Initializes the Controller Pak's file handle

Syntax

#include <ultra64.h>        /* os.h */
s32 osPfsInitPak(OSMesgQueue *mq,  OSPfs *pfs,  int controller_no);

Description

It initializes the OSPfs structure pfs, which is the file handle used to operate the Controller Pak. This function should be called first when a Controller Pak is used for the first time, a new Controller Pak is inserted, or to access different Controller Paks inserted in multiple controllers. However, because configuration must be performed to use SI, osContInit should be called once at the start, before osPfsInitPak is called.

When controlling a file system, a Controller Pak function uses the OSPfs structure pointed to by the pfs argument as a file handle to gain access. This function osPfsInitPak initializes that OSPfs structure.

The controller_no argument specifies the Controller number (0-3) into which the Controller Pak is inserted. A controller pak inserted in the controller port which is specified by the controller_no would be the target controller pak.

The mq argument is the initialized message queue linked to OS_EVENT_SI. Please refer to osSetEventMesg for creation of this link. Because mq is used by the function as an internal message queue, it is not necessary for the application to use mq for purposes such as queuing function-termination messages.

The osPfsInitPak performs the following kinds of processing internally. First it checks the disk ID area. If it recognizes the ID, it calls the function osPfsChecker. This enables recovery to be performed automatically if the file managment area (FAT area) is destroyed.

Although the previous Pfs initialization function, osPfsInit, performed automatic recovery if the ID area was completely destroyed, osPfsInitPak does not perform automatic restoration. (osPfsInitPak confirms ID integrity internally by checksum comparison. If the checksums do not agree, the ID is evaluated as corrupted.) ID recover requires a separate call to function osPfsRepairId. Normally when initializing the Controller Pak, the function osPfsInitPak should be used rather than osPfsInit. In addition, be sure to integrate osPfsRepairId into the program so that it can be called.

This is necessary because certain addresses could become indeterminate due to a poor connection at the connector or for other reasons. If you use osPfsInit to check the ID area, the function could reach the wrong address somehow because of the inappropriate address, although it was supposed to check the ID. And the function could determine that it is not a valid ID, looking at the data at the wrong address. In this case, the old osPfsInit function assigns a new ID automatically and it could write the new ID to the wrong address. As a result, the content of the Controller Pak may be destroyed.

Therefore, always use the following procedure when initializing a Controller Pak.

To initialize a Controller Pak, always call osPfsInitPak. If 0 is returned, the call is successful.

If PFS_ERR_ID_FATAL is returned as the error code, one of the following problems may exist: The Controller Pak's ID area is destroyed, the Controller Pak is not connected properly, the Controller Pak ID cannot be read due to a dirty connector, or the Controller's joy bus or Controller Pak is damaged. In this case, you must display the message, "The Controller or Controller Pak may not be inserted properly, the content may have been destroyed, or it may be damaged." Then prompt the user to choose between "connect again" or "repair it - the content of the Controller Pak may be destroyed.". If the user chooses "connect again," call the osPfsInitPak function again. If the user chooses "repair," call the osPfsRepairId function, and then call osPfsInitPak again.

If an error occurs, one of the following error codes is returned:

PFS_ERR_NOPACK
Either the Controller Pak is not inserted into the specified Controller or the Controller is not properly connected. To determine which is the case, use osContStartQuery or osContGetQuery.

PFS_ERR_NEW_PACK
A different Controller Pak has been inserted; internally specified controller pak is recognized by comparing ID each Controller pak has. To use the inserted Controller Pak, initialize it by calling osPfsInitPak.

PFS_ERR_CONTRFAIL
Data transfer to or from the Controller has failed. If a transfer error occurs, up to three tries will be done internally. Therefore, it is rather rare to see this error. If this error has returned, it is possible that either the Controller is not connected properly, or the Controller Pak or Controller Socket is damaged.

PFS_ERR_ID_FATAL
An attempt was made to initialize the file system, but the ID area was corrupted. Either the Controller Pak data were corrupted or the controller itself is malfunctioning or not properly connected. When this error is returned, the user should first be asked whether the Controller Pak should be initialized (assign a new ID) or to check the Controller Pak connection. If the user responds that the Controller Pak should be initialized, the function osPfsRepairId should be called.

PFS_ERR_DEVICE
A peripheral device other than a Controller Pak (eg, Rumble Pak, 64GB Pak) has been inserted in the controller. Whether a Controller Pak has been inserted is determined by whether the device has RAM. This error is issued if there is no RAM present.

The programming example with this function is shown below.

Example

void
mainproc(void) {
  int            i;
  OSMesgQueue    intMesgQueue;
  OSMesg         intMesgBuf[1];
  OSContStatus   contstat[MAXCONTROLLERS];
  OSPfs          pfs[MAXCONTROLLERS];
  u8             contpat;
  
  osCreateMesgQueue(&intMesgQueue, intMesgBuf, 1);
  osSetEventMesg(OS_EVENT_SI, &intMesgQueue, NULL);
  osContInit(&intMessageQ, &contpat, contstat);
  
  for (i = 0  ; i < MAXCONTROLLERS ; i ++) {
    if ((contpat >> i) & 1) {
      if ((contstat[i].type & CONT_TYPE_MASK) == CONT_TYPE_NORMAL) {
         do {
           ret = osPfsInitPak(&intMessageQ, &pfs[i], i);

           switch(ret) {
           case 0:
             osSyncPrintf("Controller Pak is inserted into PORT %d\n", i);
             break;
           case PFS_ERR_NOPACK:
             osSyncPrintf("Controller Pak is not inserted into PORT %d\n", i);
             osSyncPrintf("Insert Controller Pak\n");
             break;
           case PFS_ERR_NEW_PACK:
             osSyncPrintf("Controller Pak for PORT %d was replaced\n", i);
             osSyncPrintf("This Controller Pak will be used\n");
             break;
           case PFS_ERR_CONTRFAIL:
             osSyncPrintf("Abnormality is found in connection of Controller Pak for PORT %d\n", i);
             osSyncPrintf("Check if Controller is inserted properly\n");
             break;
           case PFS_ERR_DEVICE:
             osSyncPrintf("It cannot be saved in Controller Pak for PORT %d\n", i);
             osSyncPrintf("Check if Controller Pak is inserted properly\n");
             break;
           case PFS_ERR_ID_FATAL:
             osSyncPrintf("Abnormality is found in Controller Pak for PORT %d\n", i);
             osSyncPrintf("   A button..try to recover\n");
             osSyncPrintf("   Other buttons, re-insert\n");
            if (AskQuestion(i) == A_BUTTON) {
               osPfsRepairId(&pfs[i]);
             }
             break;
           }
           WaitForPushingAnyButton(i);
         } while (ret != 0) ;
      } else {
          osSyncPrintf("PORT %d is not a normal Controller\n", i);
      }
    } else {
      osSyncPrintf("Controller is not inserted into PORT %d\n", i);
    }
  }
}

See Also

osPfsRepairId, osPfsAllocateFile, osPfsChecker, osPfsFileState, osPfsFreeBlocks, osPfsIsPlug, osPfsReadWriteFile, osPfsSetLabel, and osSetEventMesg

Revision History

1999/02/01 Completely revised
1999/04/30 Changed format