読者です 読者をやめる 読者になる 読者になる

fpsを読めたら次はload_mph()でMP Configuration Table Headerを探す。

minix
int load_mph(void) {
/* Find and load a valid MP config header struct. Return noncero on success */

   unsigned addr;

   phys_copy ( fps.fp_mp_table , vir2phys(&mph) , sizeof(mph) );
   if (test_mptable_checksum()) return 1;
   ADDS_MP_STATUS("MP config table checksum FAILLED!\n");
   return 0;
}

ここの処理は割と単純。fpsにはMP Configuration Table Headerのアドレスが入っているので、そのアドレスを読み込めば良い。
MPの仕様書ではMP Floating Pointer Structureの説明にある「PHYSICAL ADDRESS POINTER」フィールドで、長さは32bit。

そして、データを読み込んだらfpsの時と同様にシグネチャチェックサムを確認する。

int test_mptable_checksum(void) {
/* Cheks a MP table header structure for a valid signature and checksum. 
   Return noncero on success */

   unsigned char data, checksum;
   int i;

   /* first match the signature */
   for (i=0; i<4; i++) 
      if (mph.mpch_signature[i] != SIGN_MP_C_HEADER[i] )
         return 0;

   /* then calculate checksum */
   checksum=0;
   for (i=0; i<mph.mpch_length; i++) {
      /* the complete table is in another segment, so we need copy 
         each byte into kernel address space (mph is only the header) */
      phys_copy(fps.fp_mp_table+i, vir2phys(&data), 1);
      checksum +=data;
   }
   return (!checksum);  /* checksum ok if sums 0 */
}

MP Configuration Table Structureのシグネチャは仕様で"PCMP"と定義されているので、SIGN_MP_C_HEADERの値は当然"PCMP"。
そして、チェックサムの計算なんだけど、これもfpsと同様のチェック方式になっているので、バイト毎に足し算していって結果が0になればチェックサムが正しかったことになる。
チェックサムが正しかったら、mp_start()では次に、process_mp_configuration()をコールして、MP Configurationに関する情報を読みに行く。

load_mph()はここまで。