PSP xvi

PSPプログラミングを教えるブログ(本気で頑張る人アクセス大歓迎サイト)

PSP-X.gif

記事の間違いを報告  新アップローダー
記事修正情報 PSPプログラミング資料 自作ゲーム PSP用エミュレータ リンク

公認リンク
公式PSP専科 公式PSVita専科 はじめるPSPSDK PSP EXEC GAME M@STER PSP 猫山のYouTubeチャンネル

TAG
全記事にタグをつけています  http://nekoyama2gillien.blog36.fc2.com/?tag=タグ
PSP PSPプログラミング DXライブラリPortable OSLib ショートプログラム ハローワールド
PSP自作ゲーム PSP自作ソフト エミュレータ ゲームアーカイブス PSP動画
動画 初音ミク ミクミクダンス MMDドラマ ゲーム 魔法少女まどか☆マギカ 侵略!イカ娘
アイドルマスター

このブログについて

このブログでは、非公式のPSPソフト、いわゆる自作ソフト( PSP Homebrew )を作る事を目的とします。

著作権などの こまかい利用規約については、こちらを開いてお読み下さい

このブログについて知りたい方、初めて来訪された方はこちらを開いてお読みください
お問い合わせは 猫山猫宗(nekomune@gmail.com)までどうぞ


当ブログはリンクフリーです。ブログ名は、アルファベットで「PSP xvi」と書いて『ピーエスピー・エクシビ』とお読みください。
相互リンクを希望されるブログ運営者様は、ココで申請して下さい。


このブログで全記事から探し物の方は、ここをクリックして下さい。
http://nekoyama2gillien.blog36.fc2.com/?all

スポンサーサイト 

--/--/--
--. --:--

上記の広告は1ヶ月以上更新のないブログに表示されています。
新しい記事を書く事で広告が消せます。

[edit]

CM: --
TB: --

page top

PSPプログラミング EBOOT.PBPの構造を知ろう! 

2009/02/01
Sun. 06:55

PSPの実行ファイル EBOOT.PBP の構造について

まずは、下記URLを参照して下さい。

>[ EBOOT.PBPのファイル構造 ]
> http://nagaokastation.com/psp_ebootpbp.html

「見てみても、良く解かりません。」と思われるかも知れません。

UMDビデオやUMDゲームやHomebrewアプリ等、XMBより ゲームのメモリースティック Pro Duo
や UMD を選択した時に、アプリにアイコン(画像)やアプリ名(文字列)や背景画像などが表示されるのをご存知ですね。
中にはBGMが流れる物もあります。

EBOOT.PBPファイルは、実行プログラム以外に、映像効果音声効果の付いた構成になっています。やるな SONY!(w

では、解説します。


ICON0.PNG アイコン画像 / PNG画像 形式
  寸法 横144ピクセル × 縦80ピクセル

ICON1.PMF アイコン動画 / PMF動画 形式
  寸法 横144ピクセル × 縦80ピクセル / FILESIZE 500KBytes以内

ICON1.PNG 詳細説明画像 / PNG画像 形式
  寸法 横310ピクセル × 縦180ピクセル

PIC1.PNG 背景画像 / PNG画像 形式
  寸法 横480ピクセル × 縦272ピクセル

SND0.AT3 サウンドファイル
  ATRCA3plus形式圧縮オーディオ / FILESIZE 500KBytes以内

BGM については、PMF動画ファイルに付属させるか AT3ファイルに付属させるか、という選択肢があります。

上記の物を、オプションで EBOOT.PBP に埋め込みする事が可能です。
無くても、デフォルトのアイコン&無音声&背景無しという構成の EBOOT.PBP が作成可能です。

この、ICON0.PNG を例に挙げると、これは標準でのファイル名です。別のファイル名でも良いです。
指定する際、144x80サイズの PNG画像ファイル名 を設定します。

PNG画像は、グラフィックソフト等で作成できますが、PMF動画AT3オーディオは、専用のソフトウェアを使用して作成します。
以下に方法を解説しているサイトを紹介。

PMFデータ 作成方法
> http://schneemondblume.blog109.fc2.com/blog-entry-39.html

AT3データ [ATRAC3plus](SONYが開発したオーディオ圧縮技術) 作成方法
SONYが開発した SonicStage という市販ソフトで作成が可能です。買わなければならないのだ。


これらは、後から EBOOT.PBP ファイルに埋め込みする事が可能なので、オマケ機能として参考して下さい。
>> EBOOT.PBPを弄れるアプリ PSP brew の使い方が書いてあるサイト
EBOOT.PBPを編集しよう - $$な趣味生活
> http://maisokikan.blog105.fc2.com/blog-entry-56.html


これらを設定する際に注意する点は、背景画像を設定した際は、アプリ名が表示されないという事
(但し、アプリのアイコンを△→情報→○を実行する事でアプリタイトルを見る事は可能)

また、リカバリーモードでの設定で、

"Configuration ->" 選択後 ×ボタン押し
"Hide PIC0.PNG and PIC1.PNG in game menu" を、Enabled に設定

をする事により、PIC0.PNG(詳細説明画像)とPIC1.PNG(背景画像)を非表示にでき、アプリ名がアイコンの右側に表示されるようになります。


まずは実行プログラムを作成しなければなりません。
では、どうするか?

PSP Homebrew 開発キット』を導入して、付属で付いてくるサンプルプログラムソースを実行ファイルにしてみる事から始める事にします。

次回は、
PSP Homebrew 開発キット』の導入
『プログラム・ソース作成エディタ』の導入
『プログラム・ソース印刷ソフト』の導入( プリンタを所有の方のみ )

について解説します。

スポンサーサイト

[edit]

CM: 0
TB: 0

page top

「PSPプログラムは、どうやって作るのか?」

1. 構想を練る。
    どういうソフトウェアを作るか、思案/討論する。
    著作権問題も考慮する。
    この段階で、ボツになる事もある。

2. 企画する。
    PSPにて実現可能か検証する。
    PSPの性能を熟知した人々に、意見を伺う。

3. プロジェクト。
    総指揮官(監督)を調達する。
    脚本家を調達する。
    プログラムの製作者を調達する。
    絵(グラフィック/視覚効果)の製作者を調達する。
    音(効果音/BGM等のサウンド)の製作者を調達する。
    テストプレイヤー(プログラムの不具合 発見担当者)を調達する。

4. 製作開始。
    ・絵(グラフィック/視覚効果)開発
       専用のソフトウェア等で開発する。
       実際に、PSPで表示してみて、どう見えるか確認する。

    ・音(効果音/BGM等のサウンド)開発
       楽団に演奏させたり、声の専門家に喋ってもらったりして、
       それを録音して使用する場合もあるが、ファイルサイズが
       とても大きくなるので、専用のソフトウェア等で
       ファイルサイズが小さい演奏データ等を作成する。
       会話は演奏データに出来ないので、そのまま使用する場合が多い。
       実際に、PSPで視聴してみて、どう聴こえるか確認する。

    ・プログラム開発
       専用のソフトウェア等で開発する。
       一般的には、コンピュータを使用する。
       プログラマーの腕の見せ所。

    ・デバッグ
       テストプレイヤー(プログラムの不具合 発見担当者)に、動作確認を
       させて、ソフトウェアの不具合を発見/指摘/報告して貰う。
       プログラム開発者は、それを聞いて、プログラムを改善する。
       鬼のように厳しい仕事。高度なゲーマー技術が必要。

5. サンプル配布。
    試作版が完成すると、特定の関係者等に配布され、試し動作確認をして貰う。
    使用感、感動、苦情、著作権問題、等が飛び交う。

6. 発売へ。
    開発側の発売許可が下りれば、いよいよ発売です。
    発売記念の打ち上げ会 等も行われるらしい。


[ 豆知識 ]
某ゲームソフトメーカーでは、プログラムが完成するまで、スタッフ一同をマンションの一室に監禁するとか。

「バグ」「デバッグ」とは?
プログラムの不具合を、「バグ(=BUG/虫)」と言います。
そのバグを取り除くことを、「デバッグ」と言います。


[edit]

CM: 1
TB: 0

page top

前回「今度は makefile について書きます」と宣言しましたが、急きょ変更です

偉大なる先人達のホームページ&ブログ(PSPプログラミング関連限定)を紹介します。
内容が濃いので、皆さん、しっかり学んでください。
ブックマークしておくと吉かもっ

[ 以下 ]

◇PSPでプログラミング (大御所のPSPプログラミング塾 / まず、登竜門です)

やねうらお PSPであそぼう! (PSPの偉い人、やねうらお サン のブログ)

ぶーにゃんのPSPプログラミング (大御所のPSPプログラミング塾)

PSP開発幼稚園.game.jp/(本館) (色々あるでよ)

PSP自作ソフトプログラミング/開発wiki (PSPプログラマー向け)

なんとなく実験 PSPプログラミングその2 (ズバリ、PSPプログラミング塾)

Ruka's homepage (PSP用 NesterJ 関連がダウンロード可能 / プログラム・ソースも)

QuickJump Downloads-Source-Code-Development-PSP- - (色々なプログラム・ソースがダウンロード可能)

PSPnfo / PSP software 2nd. (基本が学べます)

PS2DEV.ORG: Playstation Programming - psp PSPSDKの産みの元!必読せよっ!!

PSPwiki (PSPについてのイロハ)


次回予告「次回こそ、makefile について、学んだ事を、ほとんど書きます」

こう、ご期待!! バーーーーーーーーーーーーーーーーーーーン!!

[edit]

CM: 1
TB: 0

page top

※※※※※  重要事項  ※※※※※

ある 神プログラマー様にご意見を伺ったところ、「シフト演算の部分に誤りがあるよん」と指摘されました。ついポカミスしそうなのでよーく考えてみました。で、修正しましたので気になる方は読み返して下さい。
ご指摘ありがとうなのです、神プログラマー様!!


神プログラマー様 に 頂いたURL ↓↓
http://ja.wikipedia.org/wiki/ビット演算
ココを見ると、ビット操作について詳しく書かれています。ナイスですっ!神プログラマー様 !!


私はまたもや ポカミス をしてしまったのです……………。
今度こそ、正しい事を書きます。


今回使った物 ↓↓
Minimalist PSPSDK v0.8.10 (PSPソフト開発キット / C++コンパイラ)

MAKEFILE のコンパイルオプション ↓↓
CFLAGS = -Wall -G0 -O2 -fomit-frame-pointer -mgp32 -mlong32


■■■■■ 右へシフト ■■■■■
main() // 論理シフト
{
unsigned int i; // 符号無し

i = 0xC0000000;
printf("16進数:%8X 10進数:%d \n",i,i);
i=i>>1; // 下位(右)方向へ1ビット分シフト
printf("16進数:%8X 10進数:%d \n",i,i);
}
実行結果
16進数:C0000000 10進数:-1073741824
16進数:60000000 10進数:1610612736

解説
論理演算なので、最上位ビットには 0 が入る(基本パターン)
算術演算ではありません!!
2進数:11000000 00000000 00000000 00000000 b = 16進数:0xC00000000
↓↓↓↓ ↓↓↓↓ ↓↓↓↓ ↓↓↓↓   下位(右)方向へ1ビット分シフト
2進数:01100000 00000000 00000000 00000000 b = 16進数:0x600000000


main() // 算術シフト
{
int i; // 符号あり

i = 0xC0000000;
printf("16進数:%8X 10進数:%d \n",i,i);
i=i>>1; // 2分の1倍
printf("16進数:%8X 10進数:%d \n",i,i);
}
実行結果
16進数:C00000000 10進数:-1073741824
16進数:E00000000 10進数:-536870912

解説
算術演算なので、最上位ビットには符号ビットがコピーされて入る(ちょっと考えさせられるパターン)
10進数で見ると、ちゃんと2分の1倍になっています
2進数:11000000 00000000 00000000 00000000 b = 16進数:0xC00000000
↓↓↓↓ ↓↓↓↓ ↓↓↓↓ ↓↓↓↓   2分の1倍
2進数:11100000 00000000 00000000 00000000 b = 16進数:0xE00000000


main() // 論理シフト
{
unsigned int i; // 符号無し

i = 0xC0000000;

printf("16進数:%8X 10進数:%d \n",i,i);
i=i>>2; // 下位(右)方向へ2ビット分シフト
printf("16進数:%8X 10進数:%d \n",i,i);
}
実行結果
16進数:C00000000 10進数:-1073741824
16進数:300000000 10進数:805306368

解説
論理演算なので、最上位ビットには 0 が入る(基本パターーン)
4分の1倍ではありません!(符号注意)
2進数:11000000 00000000 00000000 00000000 b = 16進数:0xC00000000
↓↓↓↓ ↓↓↓↓ ↓↓↓↓ ↓↓↓↓   下位(右)方向へ2ビット分シフト
2進数:00110000 00000000 00000000 00000000 b = 16進数:0x300000000


main() // 算術シフト
{
int i; // 符号あり

i = 0xC0000000;
printf("16進数:%8X 10進数:%d \n",i,i);
i=i>>2; // 4分の1倍
printf("16進数:%8X 10進数:%d \n",i,i);
}
実行結果
16進数:C00000000 10進数:-1073741824
16進数:F00000000 10進数:-268435456

解説
算術演算なので、最上位ビットには符号ビットがコピーされて入る
ちゃんと4分の1倍になっています
2進数:11000000 00000000 00000000 00000000 b = 16進数:0xC00000000
↓↓↓↓ ↓↓↓↓ ↓↓↓↓ ↓↓↓↓   4分の1倍
2進数:11110000 00000000 00000000 00000000 b = 16進数:0xF00000000


main() // 論理シフト
{
unsigned int i; // 符号無し

i = 0xFFFFFFFF;
printf("10進数:%d 16進数:%8X \n",i,i);
i=i>>31; // 下位(右)方向へ31ビットシフト
printf("10進数:%d 16進数:%8X \n",i,i);
}
実行結果
10進数:-1 16進数:FFFFFFFF
10進数:1  16進数:1

解説
31ビット分 シフトして、最上位ビット の 1 だけが残って移動し、値 = 1 になりました
2進数:11111111 11111111 11111111 11111111 b = 16進数:0xFFFFFFFF
↓↓↓↓ ↓↓↓↓ ↓↓↓↓ ↓↓↓↓   下位(右)方向へ31ビットシフト
2進数:00000000 00000000 00000000 00000001 b = 16進数:0x00000001


main() // 論理シフト
{
unsigned int i; // 符号無し

i = 0xFA8759E5;
printf("16進数:%8X 10進数:%d \n",i,i);
i=i>>32; // 下位(右)方向へ32ビットシフト
printf("16進数:%8X 10進数:%d \n",i,i);
}
実行結果
16進数:FA8759E5 10進数:-91792923
16進数:FA8759E5 10進数:-91792923

解説
おや?変化がない??(値が変わってませんよ??)
2進数:11111010 10000111 01011001 11100101 b = 16進数:0xFA8759E5
↓↓↓↓ ↓↓↓↓ ↓↓↓↓ ↓↓↓↓   下位(右)方向へ32ビット分 シフト??
2進数:11111010 10000111 01011001 11100101 b = 16進数:0xFA8759E5


main() // 0 ビット右シフトはどうなるか?(実験1)
{
unsigned int i; // 符号無し

i = 0x4E5D7A05; // 適当な数値(何でも可能)
printf("16進数:%8X 10進数:%d \n",i,i);
i=i>>0; // 下位(右)方向へ 0ビットシフト
printf("16進数:%8X 10進数:%d \n",i,i);
}
実行結果
16進数:4E5D7A05 10進数:1314748933
16進数:4E5D7A05 10進数:1314748933

解説
変化がありません(0 ビットシフトは、2の0乗倍なので1倍です。変化なしは当然)。
ビット移動してませんから、ね。
2進数:01001110 01011101 01111010 00000101 b = 16進数:0x4E5D7A05
↓↓↓↓ ↓↓↓↓ ↓↓↓↓ ↓↓↓↓   下位(右)方向へ 0ビットシフト
2進数:01001110 01011101 01111010 00000101 b = 16進数:0x4E5D7A05


main() // 0 ビット左シフトはどうなるか?(実験2)
{
unsigned int i; // 符号無し

i = 0x12345678; // 適当な数値(何でも可能)
printf("16進数:%8X 10進数:%d \n",i,i);
i=i<<0; // 上位(左)方向へ 0ビットシフト
printf("16進数:%8X 10進数:%d \n",i,i);
}
実行結果
16進数:12345678 10進数:305419896
16進数:12345678 10進数:305419896

解説
変化がありません(0 ビットシフトは、2の0乗倍なので1倍です。変化なしは当然)。
下位(右)方向へ 0ビットシフトと同じ結果でした。
2進数:00010010 00110100 01010110 01111000 b = 16進数:0x12345678
↓↓↓↓ ↓↓↓↓ ↓↓↓↓ ↓↓↓↓   上位(左)方向へ 0ビットシフト
2進数:00010010 00110100 01010110 01111000 b = 16進数:0x12345678


main() // 32ビットを越えるビットシフト(実験)
{
unsigned int i; // 符号無し

i = 0xFFFFFFFF;
printf("10進数:%d 16進数:%8X \n",i,i);
i=i>>49; // 下位(右)方向へ49ビットシフト
printf("10進数:%d 16進数:%8X \n",i,i);
}
実行結果
10進数:-1  16進数:FFFFFFFF
10進数:32767 16進数:00007FFF

解説
17ビット分だけ下位(右)方向へシフトしているッ!!!!
ひょっとして、49 を 32 で割った余り = 17 ビット分だけ論理シフトしているのかな?
2進数:11111111 11111111 11111111 11111111 b = 16進数:0xFFFFFFFF
↓↓↓↓ ↓↓↓↓ ↓↓↓↓ ↓↓↓↓   下位(右)方向へ17ビット分だけシフト
2進数:00000000 00000000 01111111 11111111 b = 16進数:0x00007FFF


■■■■■ 左へシフト ■■■■■
main() // 算術演算 [正の数の場合]

int i = 123; // 正の値で 123

printf("10進数:%d 16進数:%8X \n",i,i);
i=i<<4; // 16倍
printf("10進数:%d 16進数:%8X \n",i,i);
}
実行結果
10進数: 123  16進数: 7B
10進数:1968  16進数: 7B0

解説
ちゃんと16倍されている
2進数:00000000 00000000 00000000 01111011 b = 16進数:0x00000007B
↓↓↓↓ ↓↓↓↓ ↓↓↓↓ ↓↓↓↓   16倍
2進数:00000000 00000000 00000111 10110000 b = 16進数:0x0000007B0


main() // 算術演算 [負の数の場合]
{
int i = -10; // 負の値で -10

printf("10進数:%d 16進数:%8X \n",i,i);
i=i<<2; // 4倍
printf("10進数:%d 16進数:%8X \n",i,i);
}
実行結果
10進数:-10 16進数:FFFFFFF6
10進数:-40 16進数:FFFFFFD8

解説
ちゃんと4倍になっている
2進数:11111111 11111111 11111111 11110110 b = 16進数:0xFFFFFFF6
↓↓↓↓ ↓↓↓↓ ↓↓↓↓ ↓↓↓↓   4倍
2進数:11111111 11111111 11111111 11011000 b = 16進数:0xFFFFFFD8


main() // 算術演算 [負の数の場合] 桁あふれ例1
{
int i = 0x90000000;

printf("10進数:%d 16進数:%8X \n",i,i);
i=i<<1; // 2倍
printf("10進数:%d 16進数:%8X \n",i,i);
}
実行結果
10進数:-1879048192 16進数:900000000
10進数:536870912  16進数:200000000

解説
これは、演算結果が 桁あふれ になった為。エラーです。
2進数:10010000 00000000 00000000 00000000 b = 16進数:0x90000000
↓↓↓↓ ↓↓↓↓ ↓↓↓↓ ↓↓↓↓   2倍
2進数:00100000 00000000 00000000 00000000 b = 16進数:0x20000000


main() // 算術演算 [負の数の場合] 桁あふれ例2
{
int i = 0x80000000;

printf("16進数:%8X 10進数:%d \n",i,i);
i=i<<1; // 2倍
printf("16進数:%8X 10進数:%d \n",i,i);
}
実行結果
16進数:800000000 10進数:-2147483648
16進数:0  10進数:0

解説
これも、演算結果が 桁あふれ になった為。エラーです。
2進数:10000000 00000000 00000000 00000000 b = 16進数:0x80000000
↓↓↓↓ ↓↓↓↓ ↓↓↓↓ ↓↓↓↓   2倍
2進数:00000000 00000000 00000000 00000000 b = 16進数:0x00000000


main() // 32ビットを越えるビットシフト(実験1)
{
unsigned int i = 0xFFFFFFFF;

printf("16進数:%8X 10進数:%d \n",i,i);
i=i<<50; // 上位(左)方向へ 50ビット分シフト
printf("16進数:%8X 10進数:%d \n",i,i);
}
実行結果
16進数:FFFFFFFF 10進数:-1
16進数:FFFC0000 10進数:-262144

解説
これも、50 を 32 で割った余り = 18 ビット分だけ シフトしています
2進数:11111111 11111111 11111111 11111111 b = 16進数:0xFFFFFFFF
↓↓↓↓ ↓↓↓↓ ↓↓↓↓ ↓↓↓↓   上位(左)方向へ18ビット分だけシフト
2進数:11111111 11111100 00000000 00000000 b = 16進数:0xFFFC0000


main() // 負の数ビット分シフト(実験1)
{
unsigned int i = 0xFF39E421;

printf("16進数:%8X 10進数:%d \n",i,i);
i=i>>(-3); // 下位(右)方向へ、-3ビット分シフト
printf("16進数:%8X 10進数:%d \n",i,i);
}
実行結果
16進数:FF39E421 10進数:-12983263
16進数:F9CF2108 10進数:-103866104

解説
負の数ビット分のシフトは、逆方向への正の数ビット分のシフトになる様です
2進数:11111111 00111001 11100100 00100001 b = 16進数:0xFF39E421
↓↓↓↓ ↓↓↓↓ ↓↓↓↓ ↓↓↓↓   上位(左)方向へ 3ビット分シフト
2進数:11111001 11001111 00100001 00001000 b = 16進数:0xF9CF2108


main() // 負の数ビット分シフト(実験2)
{
unsigned int i = 0xFA47D8B1;

printf("16進数:%8X 10進数:%d \n",i,i);
i=i<<(-8); // 上位(左)方向へ、-8ビット分シフト
printf("16進数:%8X 10進数:%d \n",i,i);
}
実行結果
16進数:FA47D8B1 10進数:-95954767
16進数:0FA47D8B 10進数:16402392

解説
負の数ビット分のシフトは、逆方向への正の数ビット分のシフトになる様です
2進数:11111010 01000111 11011000 10110001 b = 16進数:0xFA47D8B1
↓↓↓↓ ↓↓↓↓ ↓↓↓↓ ↓↓↓↓   下位(左)方向へ 8ビット分シフト
2進数:00001111 10100100 01111101 10001011 b = 16進数:0x0FA47D8B


32ビット以上のシフト演算についての参考文献(神プログラマー様 から頂いたURL)
http://www.cpptalk.net/shifting-bits-shift-32-bits-on-32-bit-int-vt35538.html
抜粋すると、こう書いてあります。
> uint32_t x = 5;
> uint32_t y = x << 32;
> uint32_t z = x << 32;
> 
> In the above example y and z are both still 5. Why is this?

  翻訳 : シフト演算の結果、値が変化しないのは何故?

32ビット長の値(変数)を 32ビット左にシフトして 0 にしたかったんでしょうね、気持ちは解かります。
でも、そういう規則(?)はコンパイラーの設計側での問題なので、プログラマーにはコーディングで頑張るしかないですよ。
こまめにデバッグして調べるしか無いようですね。
コンパイラの変な動作を発見したら、原始的な方法で対処するとかした方が良いかもです。
それと、変テコなプログラムは書かないことが鉄則です!



念の為、もう一回 書いておきます 。
今回使った物 ↓↓
Minimalist PSPSDK v0.8.10 (Win32アプリ / PSPソフト開発キット)

MAKEFILE のコンパイルオプション ↓↓
CFLAGS = -Wall -G0 -O2 -fomit-frame-pointer -mgp32 -mlong32

ちょっと一言

今回、こういう結果になりましたが、他のC++コンパイラでも必ずしもこういう結果になるとは限りません。
更に、同じコンパイラでも、コンパイルオプションが違うと 微妙に異なる実行ファイル(EBOOT.PBPや****.prx)が出来上がるので要注意です。



◆◆◆◆◆  まとめ  ◆◆◆◆◆

・キャスト(型宣言)は正しく記述しましょう。

・シフト演算には、論理演算と算術演算があります。
・論理演算は、符号を無視します。nビットシフト。
・算術演算は、符号を有視します。上位(左)方向へは2のn乗倍。下位(左)方向へは2のn乗分の1倍。
・論理演算か、算術演算かは、指定した 変数のキャストを見れば解かります。

・PSPSDKでの ビットシフト演算の処理は、どうやらシフトするビット数を 32 で割った余りの値だけシフトするっぽいです(多分)。
・32ビット分シフトの場合は、0ビット分シフトという事で変化がありません(PSPSDKで検証)。

・負の数ビット(-n)分のシフトは、逆方向への正の数ビット(n) 分のシフトになる様です
 (例1) num>>(-5) は num<<5 の様に処理される
 (例2) num<<(-7) は num>>7 の様に処理される

値は 32ビット長なので、桁あふれする場合があります。警告!!
 が、しかし、桁あふれしても、PSPはエラーだと気付かないのです。
 桁あふれしたらエラー処理をする、というプログラムにての値チェックをするしか無いようです。

 (シフト演算に桁あふれエラー処理を記述するって、聞いた事ありませんが………)


■■■ コンパイル中のメッセージは良く見て下さい ■■■
32ビットを越えるシフト演算を記述したプログラムソースをコンパイルすると、
warning: left shift count >= width of type
warning: right shift count >= width of type
↑↑のような ウォーニング(警告) が表示されます。

負の数ビット分のシフト演算を記述したプログラムソースをコンパイルすると、
warning: left shift count is negative
↑↑のような ウォーニング(警告)が表示されます。

WARNING は、警告でありまして、エラーではありません。その証拠に、コンパイルが継続します。
神プログラマー様によると、"WARNING"は正しくは ウォーニング と発音するのだそうです。

うーーん、勉強になりました。サンキューですぞ。ウホ。

[edit]

CM: 2
TB: 0

page top

PSPプログラミング講座です。

さて、次に行く前に、ちょっと脱線しますよ。

mediumgauge氏 製作 の 『全角文字表示ライブラリ』が、何故 こんなに たくさんの文字群を描画できるかについての謎を紐解くために、
ここに パソコンの日本語文字 & コード 一覧表(ASCII & SHIFT-JIS) [Windows版] というテキストファイルを配布します。

日本語文字 & コード 一覧表 [Windows版]
83.2 KB (85,206 バイト)
ALL_MOJI_[JPN].zip
ダウンロード

PASS:窓辺ななみ


特別付録として、WindowsXP の 文字のスクリーンショット(一部抜粋)が収録されています。

各自ダウンロードしてから解凍して閲覧してチョ。

印刷する場合は、不要部分をデリートしてからで お願いしますよ。

ブログをお持ちの方で、『所有の端末にて このテキストを表示させてみると、面白い文字が表示されたっ』とかありましたら、ブログの記事にしてみて下さい。

今の狙い目は、PSPファイラーです。どこかに絵文字が隠れています。
発見したら、あなたのブログの記事にして下さい(スクリーンショット写真も添えてねん)。

添え忘れましたが、このテキストは PDS(著作権放棄のフリーウェア)です。転載、改変、削除、再配布許可。


このテキストは、『Windowsパソコン & Turbo C++コンパイラ』 にて作成しました。


【 関連記事 】
PSPプログラミング 全角文字表示ライブラリをダウンロード
PSPプログラミング [ 番外編 ] 日本語の文字 一覧表(ASCII & SHIFT-JIS) 完全版
PSPプログラミング 東雲フォント文字を全部表示しちゃうプログラム
PSPプログラミング 東雲フォントのデータ構造を調べました
PSPプログラミング 全角文字表示ライブラリ公開停止中のお知らせ
PSPプログラミング 『東雲フォント』が動画になった

[edit]

CM: 0
TB: 0

page top

全角文字表示ライブラリの解析。

大雑把ですが、解析してみました。

この記事は、知らなくても良い事を記述していますので、深く考えて混乱しないようにお願いします。
mh_print( );関数で 文字が書ける、という事だけ知っていればおっけーです。



東雲フォントのデータ構造は 至って単純で、文字の形があれば「1」、文字の形が無ければ「0」、という点の情報の連続で、この「1」と「0」を並べると、モノクロのビットマップの図形でした。

つまり、東雲フォントのデータ = 2色ビットマップ。

サイズは、
半角文字=ヨコ:6ピクセル×高さ:12ピクセル
全角文字=(左側半分)ヨコ:6ピクセル×高さ:12ピクセル、(右側半分)ヨコ:6ピクセル×高さ:12ピクセル

でした。

これを図におこすと、このようになります。


SHINONOME_SHARP.png

SHINONOME_NEKO.png

ここで、mediumgauge氏 製作の 全角文字表示ライブラリから「shinonomefont.c」というファイル(C言語のソース)を開いて見て頂きたいです。

まず、5行目。ここは、半角文字で「#」のデータが格納されています。16進数ですね。何でしょう?機械語でしょうか? 謎の9バイト・データ。

いえいえ、これは、文字のビットマップデータ:( )なのです。

ひも解く手段として、まず、2進数に置き換えます。

16進数 0x01,0x45,0x3E,0x51,0x45,0x3E,0x51,0x40,0x00
     ↓↓↓↓↓↓↓↓↓↓↓↓
2進数 0000 0001 0100 0101 0011 1110 0101 0001 0100 0101 0011 1110 0101 0001 0100 0000 0000 0000

んー、ますます解かりませんね(汗)。
でも、この2進数データを分解して 6ビットづつ並べると・・・。

2進数 000000 010100 010100 111110 010100 010100 010100 111110 010100 000000 000000 000000

↑↑ これですよ、これ。この2進数は、上の図の左側の数値列と同じですね。
この数値列の「1」を青色に、「0」を白色で、塗りつぶすと上の図の「#」の左側の絵になります。

解かりましたね。(^o^)ノ
「#」を構成する点の情報(ビットマップ)が、左から右へ、上から下へ、の順番に並んでいます。
この9バイト・データは、ヨコ:6ピクセル×高さ:12ピクセル=72ピクセル=9バイト・データ長だったのです。謎は解けたっっ(笑)。
これで、「#」についての解析は おしまいです。

次に、全角文字の場合。( )=シフトJISコードで 0x944C なので、3438行目を見て下さい。

>3438行目:/*944C*/0x95,0x72,0x59,0xAC,0xA3,0x9B,0xA8,0xA2,0xF0,
0x13,0xE2,0x08,0xF9,0x24,0xBE,0x49,0x2F,0x80,

まず、9バイト単位に分割します。
何故かと言うと、mh_print( ); という関数は、全角文字を書く作業の実態は、左側 ヨコ:6ピクセル×高さ:12ピクセル を書いてから、右側 ヨコ:6ピクセル×高さ:12ピクセル を書いている、という事実だからです。

だから、データも、
前半の9バイト=ヨコ:6ピクセル×高さ:12ピクセル → 全角文字の、左側半分
前半の9バイト=ヨコ:6ピクセル×高さ:12ピクセル → 全角文字の、右側半分
のように分割されている、という事なのです。

ゆえに、この18バイト・データを2進数に変換すると・・・。

前半:2進数 1001 0101 0111 0010 0101 1001 1010 1100 0101 0011 1001 1011 1010 1000 1010 0010 1111 0000
後半:2進数 0001 0011 1110 0010 0000 1000 1111 1001 0010 0100 1011 1110 0100 1001 0010 1111 1000 0000

これらも、モノクロのビットマップ画像なので、6ピクセル単位に区切って並べると・・・
前半:2進数 100101 010111 001001 011001 101011 000101 001110 011011 101010 001010 001011 110000
後半:2進数 000100 111110 001000 001000 111110 010010 010010 111110 010010 010010 111110 000000

これは、「猫」の図の右側の数値列と同一ですね、ねっ。
縦長で見づらいですね、ごめんなさい。

「猫」を構成する点の情報(ビットマップ)が、左右6ピクセルづつに分割されて、左から右へ、上から下へ、の順番に並んでいます。
この18バイト・データは、左側半分 ヨコ:6ピクセル×高さ:12ピクセル、右側半分 ヨコ:6ピクセル×高さ:12ピクセル=144ピクセル=18バイト・データ長だったのです。



で、文字データってナニ?という方の為に、解説します。
簡単に言うと、文字群の情報を、少ない情報量で分かりやすく表現したデータです。
つまり、半角文字は1バイトで、全角文字は2バイト、と、簡単に分類できます。
(ただし、2バイト長の半角文字もあったようですが、Windowsには2バイト半角文字は存在せず)

詳しく知りたい方は、「文字コード(完全版)」の一覧表をダウンロードして 解凍して 見てください。

それには、文字一覧表の左側に 2桁 or 4桁 の16進数が記載されていますね?
それは、該当の文字が 1バイト、もしくは2バイト、で表現できるデータである、という事を表し、ACIIコード(アスキーコード)や、シフトJISコード(シフトジスコード)等の文字一覧表として表現されます。

その一覧表を見ると、半角文字で「A」は 0x41(16進数) というアスキーコード番号である事が分かるかと存じます。同様に、全角文字で「亜」は 0x889F(16進数) というシフトJISコード番号である事が分かるハズ。

更に、バイナリエディター(テキストエディターに対抗して、文字以外の16進数データも全て扱える数値エディター)で、テキスト文書(拡張子.TXT)を覗いてみると、半角文字=1バイト長、全角文字=2バイト長、で延々と書き連ねられている、という事が分かるかと存じます。

昔のパソコンでは、テキストV-RAMというメモリが存在して、そのテキストV-RAMに、例えば1バイトの 0x42(16進数) というデータを書き込めば、画面に「B」という半角文字が表示されました。
昔のパソコンでは、文字のフォントは、ROMで用意されていましたので、フォントの事を気にせずに文字をバンバン書き込めたのです。しかも、1文字が1バイト。
その1バイトの情報が、ASCIIコード であり、テキストデータの原理(?)であったのです。
同様に、全角文字は、2バイトの情報で、シフトJISコードが一般的でした。

これ以上、つまらないハナシをしても無駄なので要約すると、文字は、1バイト長、もしくは2バイト長、のデータとして扱える、という事を覚えておいて下さい。


全角文字表示ライブラリは、東雲フォントの文字を描画する事が目的です。

している事は、簡単に解説しますと、文字のコード番号を読み取って、その文字に対応するフォントデータのアドレス(番地)を割り出して、フォントのビットマップ情報に従って、指定された色で 点を打ったり点を打たなかったりして1文字ずつ文字を描画しています。

Windows や PSP にはテキストV-RAM が存在しないので、グラフィック画面に絵を描く原理で文字を描画しないと、文字が書けない、という事実も覚えておいて下さい。
その為の、全角文字表示ライブラリなのです。解かりましたか?

それでは、これで、東雲フォントのデータ解析についての講釈を終わります。

上にも書きましたが、もう一回書いておきます。
この記事の内容は、知らなくても良い事なので深く考えて混乱しないようにお願いします。
mh_print( );関数で 文字が書ける、という事だけ分かってもらえればおっけーです。



さあ、つぎに行こう!今回はダウンロード物は ありません。


【 関連記事 】
PSPプログラミング 全角文字表示ライブラリをダウンロード
PSPプログラミング [ 番外編 ] 日本語の文字 一覧表(ASCII & SHIFT-JIS) 完全版
PSPプログラミング 東雲フォント文字を全部表示しちゃうプログラム
PSPプログラミング 東雲フォントのデータ構造を調べました
PSPプログラミング 全角文字表示ライブラリ公開停止中のお知らせ
PSPプログラミング 『東雲フォント』が動画になった

[edit]

CM: 2
TB: 0

page top

ある心無いユーザーによる、著作権表示をしないでの使用による理由(?)で、ただ今、全角文字表示ライブラリが公開停止中になっております。

詳細
http://www.geocities.jp/mediumgauge/


困ったモノである…。


その後の 2011/10/30 現在では・・・迷惑かけてた首謀者のサイトが閉鎖してます



【 関連記事 】
PSPプログラミング 全角文字表示ライブラリをダウンロード
PSPプログラミング [ 番外編 ] 日本語の文字 一覧表(ASCII & SHIFT-JIS) 完全版
PSPプログラミング 東雲フォント文字を全部表示しちゃうプログラム
PSPプログラミング 東雲フォントのデータ構造を調べました
PSPプログラミング 全角文字表示ライブラリ公開停止中のお知らせ
PSPプログラミング 『東雲フォント』が動画になった

[edit]

CM: 2
TB: 0

page top

2010年01月10日 更新


一般の C++言語におけるプログラムの記述は、main( ) 関数を

int main( int argc , char * argv[ ] )
{
    なるべく短く簡単に!
}

と記述するのが良い、とされています。

C++ 言語のプログラムは、標準では、まず、main( ) という関数から実行されます。
main 関数は、ソースコードのどの位置にあっても良いのです。main( )関数を一番最後に記述しても良いのですが、見づらい記述方法なので、私は 最初に main( ) 関数を書くように改めました。


  コマンドライン引数の変数には "argc", "argv" が使われます

    argc = argument count
    argv = argument vector

一般では、下記のようになります

    int argc ………… 引数の個数が入ってきます
    char *argv[] …… 引数の文字列が入ってきます


Windowsの場合では、コマンドライン上で 『ファイル名を指定して実行』 を行う際、実行するファイルに、引数(パラメータ類)を渡すことが可能です。


例:COPY コマンド

記述例:  C:> COPY OMAKE.TXT OMAKEDAYO.TXT
目的: OMAKE.TXT をコピーして OMAKEDAYO.TXT というファイルを作成(コピー)

こう記述した場合の 引数は、


引数1 = COPY
引数2 = OMAKE.TXT
引数3 = OMAKEDAYO.TXT
(これらの引数の末尾は、NULL文字 = 0x00 で終わっています)

引数の個数 = 3個


となります。引数の区切りは、半角の空白文字です。



この main( )関数の書き方は、PSPではどうなのでしょうか?

PSPにはコマンドラインは存在しないので、ゲームから EBOOT.PBP を起動させた時の引数を調べます


#include <pspkernel.h>
#include <pspdebug.h>

/* Define printf, just to make typing easier */
#define printf pspDebugScreenPrintf

PSP_MODULE_INFO("TEST",0,1,1);
PSP_MAIN_THREAD_ATTR(THREAD_ATTR_USER | THREAD_ATTR_VFPU);

int main(int argc , char * argv[ ])
{
pspDebugScreenInit();

printf("argc = %d\n",argc); // 引数の個数を表示
printf("argv[0] = %s\n",argv[0]); // 引数の1個目の文字列を表示

return 0;
}

↑↑ このプログラムを終了するには PSPの電源を切って下さい(手抜きです、ごめんなさい)。

↓↓実行結果(/GAME150/の下に、/Where/フォルダーを作って その中にEBOOT.PBP を貼り付けてみました)
実行結果サンプル.png

この結果、argc は常に 1 で、argv[0] には、EBOOT.PBP の在り処(フルPATH) が入る事が判明しました。

上記結果を参考にして、引数の 'EBOOT.PBP'文字 の手前(フォルダPATH)までを グローバル変数に退避しておく事により、下記のことが可能

ms0:/PSP/GAME150/HoeHoe/EBOOT.PBP
ms0:/PSP/GAME150/HoeHoe/image/画像_0001.png

/HoeHoe/ は、使用者が勝手に作るフォルダで、製作者は まさか /HoeHoe/ フォルダに入れられるとは予想もしなかった。だが、image/画像_0001.pngファイル名は固定で分かっているので、image/画像_0001.png のフルPATH を突き止めたい!!

    'ms0:/PSP/GAME150/HoeHoe/EBOOT.PBP'

(1) argv[0]の文字列情報から、EBOOT.PBP のフルPATH を取得します
(2) そのフルPATHから、EBOOT.PBPの文字列を削除します
(3) すると、EBOOT.PBP のあるフォルダPATHが判明するので、そのPATH以下に image/画像_0001.png 文字列を付け足します
(4) 完成!

'ms0:/PSP/GAME150/HoeHoe/EBOOT.PBP'
         ↓('EBOOT.PBP'文字列を削除)
'ms0:/PSP/GAME150/HoeHoe/'
         ↓('image/画像_0001.png'文字列を付け足す)
'ms0:/PSP/GAME150/HoeHoe/image/画像_0001.png'

作成した PATH へアクセスして、データを取得可能!!


main( ) の引数から 実行した EBOOT.PBP の入っているフォルダ(在り処)を突き止める関数が、既にRukaさま(NesterJ作者さま)により開発済みですので、紹介します。

NesterJ のソース内の、 pg.c中 の pgMain( ) という関数がそうです。

NesterJ 関連のダウンロード
http://rukapsp.hp.infoseek.co.jp/PSPSoftware/NesterJ.htm
↑↑ ここから、NesterJ for PSP Ver 1.11 source というのをダウンロードして下さい。

無許可ですが、続きに その関数を改変したソースを貼り付けておきます(Rukaさん、改変禁止でしたらご一報下さいませ)

-- 続きを読む --

[edit]

CM: 5
TB: 1

page top

いきなりですがスーファミのソフトをEBOOT.PBPに変換してPSPに移植することは可能でしょうか?

なんか、こういう質問を受けたので、答えてみます。


変換するのは移植であるかどうか、議論をかましたい今日この頃(笑)

スーパーファミコンとPSPは、まず、プラットフォームが違います。

プラットフォーム (コンピューティング) - Wikipedia
スーパーファミコン - Wikipedia
プレイステーション・ポータブル - Wikipedia

PSPのエミュレータで、スーパーファミコンのROMを実機に近い動作で遊べますが、それはエミュレーションしているのであって、移植では無いですな。

エミュレーションとは、機械語で書かれた実行ファイルを 一語 一語 解析して、何をする命令か判断をして、更に BIOS やハードウェアなどに照らし合わせて、結局、『このような動作になるハズだッッッ』という処理を、絶えず やってのける作業です。人間にはとても出来ない作業でっす(^^;;;;;


日本には、エミュレータについて こんな法律があります。

原則として、ゲームエミュレータ本体に関しては、実物の動作をリバースエンジニアリングして開発する限りは違法性はないとされる。ただし、ハードウェアベンダから提供される、ハードウェア情報やソフトウェア開発キットなど、ベンダとの守秘義務契約に該当する情報を流用した場合は、守秘義務契約を違反した開発者に対して違法性を問われることになる。
リバースエンジニアリング -Wikipedia


EBOOT.PBP に変換というのは、PSP用の実行形式のファイルにするという事なので、スーパーファミコンのゲームソフトのプログラム・ソースを用意して、PSP用のコードに書き直してコンパイルして EBOOT.PBP を作成するのであれば、『可能です』という回答です。それを移植といいます。ええ。

オープンソースで頑張るしかっ!!



近況報告

リンクにある DXライブラリPortable を導入してみました。今後、お世話になりますよ~♪
画像表示プログラムを作っていたら、『画像インフォ』になった。
まず、画像を表示する前に、画像の情報が正しく読めているか確認しているのであった・・・・・。

[edit]

CM: 8
TB: 0

page top

PSPプログラミング ビット操作の一覧表 

2009/09/19
Sat. 17:40

前回、AND とか OR とかが出てきたので、ご紹介

ビットとは、CPU が扱う数値の基礎です。

真 = ON = 1
偽 = OFF = 0

2進数なので、簡単かと。


ビット操作とは、所定のビットをONにしたり、OFFにしたり、反転する作業です

候補として、AND、OR、XOR、NOT などがあります。

AND ( A かつ B ) アンド
OR ( A または B ) オア
XOR ( A あるいは B のどちらか ) エクスクルーシブ・オア
NOT ( A でなくて ) ノット


以下、一覧表で見てください

AND ( A かつ B )
      ┏━━━━━┓
      ┃  B  ┃
      ┣━━┳━━┫
      ┃ 0 ┃ 1 ┃
┏━━┳━━╋━━╋━━┫
┃  ┃ 0 ┃ 0 │ 0 │
┃ A ┣━━╋──┼──┤
┃  ┃ 1 ┃ 0 │ 1 │
┗━━┻━━┻──┴──┘
A と B が真のとき、1


OR ( A または B )
      ┏━━━━━┓
      ┃  B  ┃
      ┣━━┳━━┫
      ┃ 0 ┃ 1 ┃
┏━━┳━━╋━━╋━━┫
┃  ┃ 0 ┃ 0 │ 1 │
┃ A ┣━━╋──┼──┤
┃  ┃ 1 ┃ 1 │ 1 │
┗━━┻━━┻──┴──┘
A または B が真のとき、1


XOR ( A あるいは B のどちらか)
      ┏━━━━━┓
      ┃  B  ┃
      ┣━━┳━━┫
      ┃ 0 ┃ 1 ┃
┏━━┳━━╋━━╋━━┫
┃  ┃ 0 ┃ 0 │ 1 │
┃ A ┣━━╋──┼──┤
┃  ┃ 1 ┃ 1 │ 0 │
┗━━┻━━┻──┴──┘
A のみが真、もしくは B のみが真のとき、1


NOT( A でなくて )
      ┏━━┓
      ┃反転┃
┏━━┳━━╋━━┫
┃  ┃ 0 ┃ 1 │
┃ A ┣━━╋──┤
┃  ┃ 1 ┃ 0 │
┗━━┻━━┻──┘
A の反転





算術式では、ビット演算と呼ばれます。
ビット演算
┏━━┳━━┳━━┳━━┳━━┳━━━━┳━━━━┓
┃演算┃AND ┃ OR ┃XOR ┃NOT ┃左シフト┃右シフト┃
┣━━╋━━╋━━╋━━╋━━╋━━━━╋━━━━┫
┃記号┃ & ┃ | ┃ ^ ┃ ~ ┃ << ┃ >> ┃
┗━━┻━━┻━━┻━━┻━━┻━━━━┻━━━━┛


条件式では、論理演算と呼ばれます。
論理演算
┏━━┳━━┳━━┳━━┓
┃演算┃AND ┃ OR ┃NOT ┃
┣━━╋━━╋━━╋━━┫
┃記号┃ && ┃ || ┃ ! ┃
┗━━┻━━┻━━┻━━┛
条件式における演算子については、こちらをどうぞ
演算子 - Wikipedia


ちなみに、条件式の記述について うっかりミスとか

if( state = 1 )
{
printf("やったぜ、加トちゃん!\n");
state++;
}

上記を行なうと、state に 1 が代入されてから、+1 加算されます。
何故かというと、if 文が代入式になっているからです。
この場合、

if( (state = 1) != 0)
{
printf("やったぜ、加トちゃん!\n");
state++;
}

という風に、コンパイラに解釈されちゃいます。
こういう記述の間違いは、コンパイル時にもエラーにならないので、自分でトレースして見付けるしかないようですね。
↑↑ ごめんなさい。コンパイルしたら「if文では代入しないほうが良いよん」警告がでますね。なんてカシコイPSPSDK!

さて、次回は ファイルの書き換え へ突入~~っ♪


[edit]

CM: 0
TB: 1

page top

現在、配布停止中の『全角文字表示ライブラリ』

mediumgauge氏に申請して、東雲フォントの動画サイトへの公開許諾を得ました。
で、作った動画がコレでっす。





拡大しないと文字が潰れるので、寸法 大きめの動画なのです。ソースは、1280x720 (HD) です。


【 関連記事 】
PSPプログラミング 全角文字表示ライブラリをダウンロード
PSPプログラミング [ 番外編 ] 日本語の文字 一覧表(ASCII & SHIFT-JIS) 完全版
PSPプログラミング 東雲フォント文字を全部表示しちゃうプログラム
PSPプログラミング 東雲フォントのデータ構造を調べました
PSPプログラミング 全角文字表示ライブラリ公開停止中のお知らせ
PSPプログラミング 『東雲フォント』が動画になった

[edit]

CM: 0
TB: 0

page top

2011年6月17日更新

私の書いた この記事がどこかオカシイとの ご意見により、記事を 分かりやすいように加筆修正します。以下
この際ですので、一般に使われている、変なPSP用語も掲載して指摘します。

・1.50カーネル
  これは、システムソフトウェア v1.50という OS が、Homebew起動可能である、という事から
  1.50 の カーネル という意味づけで 1.50カーネルという言葉になったのか?

・カーネル3.xx以降
  これは、1.50カーネル に対して 3.xx以降カーネル と呼ばれなければならないと思う。

・カーネル ってなんだ?
  Wiki で調べて再認識 → カーネル(コンピュータ用語) - Wikipedia
  Wikiの記事を要約すると、カーネルとは、OS の 非常に大事な部分(核に相当する)で、仲介屋ってトコ。
  アプリケーションの起動可否は、カーネル次第でどうともなるそうだ。
  各自、お勉強して下さい。


以下、PSPのCPUについて知っているコトを書きます。

PSP に採用されている、MIPS系 R4400 というMPU(CPU)には、2種類の動作モードがあります。

「カーネルモード」と、「ユーザーモード」

さらに、プログラムの書き方では VSHモードというのもあります(現在調査中)

PSPの実行ファイルにも カーネルモードのプログラム と、ユーザーモードのプログラム が存在します

●CPUがカーネルモードの場合 別名:特権モード
 PSPの全てのメモリやハードウェアに対して無制限にアクセス可能。取り扱いは 多少危険です。

●CPUがユーザーモードの場合 別名:保護モード。
 PSPのメモリやハードウェアの内、保護されている部分だけのみアクセス可能。


実行ファイルが カーネルモード記述の場合は、冒頭で「特権モードである」という宣言がされています。
初期のPSP、PSP-1000でのエミュレータ等のカーネルモード記述のHomebrewが起動してしまうシステムソフトウェア v1.00や v1.50 のOS が、カーネルモード推進していた模様。

PSP-1000用のエミュレータが登場してしまったので、メーカーは緊急に対策を取り、ユーザーモードのOSである、システムソフトウェア1.51以降に切り替えていき、現在のシステムソフトウェア6.39に至る(2011/06/17現在)。
PSPのメーカーは、PSP Homebrewを認めていません。


実行ファイルが ユーザーモード記述の場合は、冒頭で「保護モードである」という宣言がされています。

PSPのメーカーは、OS(システムソフトウェア)だけでは物足らず、ハードウェアまでユーザーモードがメインの、PSP-2000を製作し、PSP2号とした。




ところで、皆さんは、PSPのリカバリーモードの Configuration 項目、

> Game folder homebrew (currentry: 5.XX kernel)

の部分を、1.50カーネル や 5.XXカーネル にする方法は知っていても、本来、何を意味するのか考えたことがありますか?偉そうなこと言ってますが、私は、PSPのCPUの動作モードを、カーネルモード(1.50Kernel)とユーザーモード(3.xxKernel)に切り替える処理をしているのだと考えています。

この答えは、カスタムファームウェアの開発者のみ知ることなのですが、QJ.net さんにて、カスタムファームウェア3.10OE-Aと3.40OE-A のプログラムソースコードが配布中なので、機会があったら解読してみようと思います。 ソースは削除されているっぽいです。アメリカのGoogle でも見つかりませんでした。

ちなみに、1.50カーネルとか、3.xxカーネル、4.XXカーネル、5.XXカーネルとかのカーネル数値は、PSPのシステムソフトウェアのバージョンを意味します。

・1.50カーネル
  システムソフトウェア1.50にちなんで付けられた カーネル名。PSP Homebrew の起動を推進する。

・3.xx以降カーネル
  システムソフトウェア3.xx等の後期システムソフトウェアにちなんで、私が勝手に呼んでみるカーネル名。
 一般では、カーネル3.xx以降とか言うらしい。1.50カーネル用のアプリの起動を抑止する。


1.50カーネル上でしか起動しない事になっているカーネルモードの自作ソフトを、3.xx以降のカーネル上で起動させるには、色々な手段が生み出されました

◆エミュレート
・eLoader v1.000 を起動させて、そこから自作ソフトを起動させる方法
(リバースエンジニアリングして調べたわけではありませんが、多分こんなことをやっているのだろうと推測)
まず、読み込まれる予定のカーネルモードのPRXモジュールなどを、ユーザーモードのPRXモジュールを読み込むように置き換える。
実行ファイルはエミュレートする。ユーザーモードで実行できる処理は行なわれるが カーネルモードでしか実行できない処理はエミュレートできず そこで停止してしまう。

◆ユーザーモードへ実行ファイルを変換
(「カーネル1.50のソフトをCFW3.xx用に変換するソフト」というアプリを使用)
実際は、実行ファイルに eLoaderを埋め込む処理がされます。eLoaderで実行できないカーネルソフトには、この変換をやっても無駄なだけです

◆OSにカーネルモードの動作をサポートする機能を追加
・カスタムファームウェア5.00M33-6 に LEDA Legacy Software Loader beta0.2 を導入し、カーネルモードを1.50固定にしておく方法
カーネルモードを切り替える必要が無くなり、どっちのモードのソフトでも、ある程度 起動可能にさせてしまう

私の製作した PSP自作ソフトは、殆ど ユーザーモード(保護モード)の仕様です。

なので、PSP-2000 でも 素で起動したりします(笑)。カーネルモードで作っていたらPSP-2000では起動できなかったハズ…。eLoader使用で起動したよ報告が あったな。


判明している事は、PSPのソフトウェアには、3種類のタイプがあるという事実です。
・カーネルモード専用(カーネルハードウェアやカーネルメモリなどにアクセスするアプリとか)
・ユーザーモード専用(メディアエンジンを作動させるアプリとか)
・どっちのモードでも動作する

俺作PSPソフウェア
「じゃんけんゲーム for PSP パワードX」 1.50 or 3.xx どっちでも起動可能
「みくねぎっと。」 初音ミクで ハタあげならぬネギあげゲーム 3.xx以降専用(配布終了)
「PSPデスクトップ ドドド 改」 1.50 or 3.xx どっちでも起動可能
「千早が765衣装で吹っ切れた!? PSP」 3.xx以降専用


おまけで書いておくこと。
この記事は、「PSPそうごう」カテゴリだったけど、「PSPプログラミング」カテゴリに引越ししました。

PSPの、カーネルモード、並びに、ユーザーモード の プログラムの書き方。
参考したもの = CPS1/CPS2 のソース

プログラムの冒頭で、こう記述します。↓↓

カーネルモード発動!

PSP_MODULE_INFO("プログラム名", PSP_MODULE_KERNEL, VERSION_MAJOR, VERSION_MINOR);
PSP_MAIN_THREAD_ATTR(0);


解説
(赤い文字の部分は、自由に書き換えて下さい)
PSP_MODULE_KERNELは、ヘッダーファイルにて、0x1000 という数値が記述されています。
カーネルモードのプログラムである、と宣言しています。

"プログラム名" の部分は、半角の英数字記号で、好きな名前を記述して下さい。

VERSION_MAJOR は、整数 数値。そのプログラムのバージョンの、整数部分(値は何でも可能)
VERSION_MINOR は、整数 数値。そのプログラムのバージョンの、小数点以下部分(値は何でも可能)

PSP_MAIN_THREAD_ATTR(0); は、このプログラムが、CPUをカーネルモードにして実行するというおまじない。


ユーザーモード発動!

PSP_MODULE_INFO("プログラム名", PSP_MODULE_USER, VERSION_MAJOR, VERSION_MINOR);
PSP_MAIN_THREAD_ATTR(THREAD_ATTR_USER);


解説
(赤い文字の部分は、自由に書き換えて下さい)
PSP_MODULE_USER は、ヘッダーファイルにて、0 という数値が記述されています。
ユーザーモードのプログラムである、と宣言しています。

"プログラム名" の部分は、半角の英数字記号で、好きな名前を記述して下さい。

VERSION_MAJOR は、整数 数値。そのプログラムのバージョンの、整数部分(値は何でも可能)
VERSION_MINOR は、整数 数値。そのプログラムのバージョンの、小数点以下部分(値は何でも可能)

PSP_MAIN_THREAD_ATTR(THREAD_ATTR_USER); は、このプログラムが、CPUをユーザーモードにして実行するというおまじない。


本来、R4400というCPUは、カーネルモード動作時にはカーネルモードのプログラム、あるいは、ユーザーモードのプログラムを実行でき、ユーザーモード動作時にはユーザーモードのプログラムを実行できる、というお約束があるみたいです。どっちのモードでも動作するのは、ユーザーモード記述のプログラムです。
プログラマーが正しくコードを記述して使い分けないと、R4400は悩んでしまうカモ知れず。

PSP-2000のCPUもR4400なので、カーネルモードがあります(メーカー側が、抑止させているだけなのか?)

現に、PSP-2000で カーネルモードのプラグインは動作できるし(例:PSP画面キャプチャ・プラグイン)


本日は、ここまで。では、明日!


皆さん、意見をどうぞ。 コメント欄へ

[edit]

CM: 17
TB: 0

page top

PSPプログラミング 8進数の罠 

2009/10/18
Sun. 00:25

プログラミングの際は、扱う数値にも気を付けて下さい。

sceIoOpen( , , 0777);
0777 は、8進数の値です。

C++では8進数は、数値の左端に 0 を付けます。
C++では16進数は、数値の左端に 0x を付けます。

8進数は、0、1、2、3、4、5、6、7 の数字を使って表現します。
16進数は、0、1、2、3、4、5、6、7、8、9、A、B、C、D、E、F の英数字を使って表現します。


ポカミスしそうなので書いてみました。

【 関連記事 】
PSPプログラミング [ 番外編 ] シフト演算に潜む罠 (重要問題)
PSPプログラミング - 準備編 1 2進数に慣れよう
PSPプログラミング - 準備編 2 「ビット」と「バイト」、「16進数」について
PSPプログラミング - 準備編 3 バイト・ワード・ダブルワード、符号、変数

[edit]

CM: 0
TB: 0

page top

まず、PSPSDK に同梱されているライブラリの一覧を紹介します。

● C:\pspsdk\psp\lib の中にあるライブラリ
crt0.o crt0_prx.o (←念のために記述してあります/使用できるかは未確認)
libbulletml.a libbz2.a libc.a libfreetype.a libfreetype.la libg.a libGL.a libGLU.a libglut.a
libglut.a libjpeg.a liblua.a liblualib.a libm.a libmad.a libmikmod.a libobjc.a libobjc.la
libogg.a libogg.la libpng.a libpspvalloc.a libpspvram.a libSDL.a libSDL.la libSDL_gfx.a
libSDL_gfx.la libSDL_image.a libSDL_image.la libSDL_mixer.a libSDL_mixer.la libSDL_ttf.a
libSDL_ttf.la libSDLmain.a libsmpeg.a libsqlite3.a libsqlite3.la libssp.a libssp.la
libssp_nonshared.a libssp_nonshared.la libstdc++.a libstdc++.la libsupc++.a libsupc++.la
libvorbis.a libvorbis.la libvorbisenc.a libvorbisenc.la libvorbisfile.a libvorbisfile.la
libvorbisidec.a libvorbisidec.la libz.a libzzip.a libzzip.la libzzipfseeko.a libzzipfseeko.la
libzzipmmapped.a libzzipmmapped.la libzzipwrap.a libzzipwrap.la

○ C:\pspsdk\psp\lib の 各ライブラリのリンクの書き方 @MAKEFILE
(注)拡張子が ’.la’の物は、LIGHT版か、LITTLE版かのどちらかだと推測したので割愛
ライブラリ名        リンク記述
libbulletml.a -lbulletml
libbz2.a -lbz2
libc.a -lc
libfreetype.a -lfreetype
libg.a -lg
libGL.a -lGL
libGLU.a -lGLU
libglut.a -lglut
libglut.a -lglut
libjpeg.a -ljpeg
liblua.a -llua
liblualib.a -llualib
libm.a -lm
libmad.a -lmad
libmikmod.a -lmikmod
libobjc.a -lobjc
libogg.a -logg
libpng.a -lpng
libpspvalloc.a -lpspvalloc
libpspvram.a -lpspvram
libSDL.a -lSDL
libSDL_gfx.a -lSDL_gfx
libSDL_image.a -lSDL_image
libSDL_mixer.a -lSDL_mixer
libSDL_ttf.a -lSDL_ttf
libSDLmain.a -lSDLmain
libsmpeg.a -lsmpeg
libsqlite3.a -lsqlite3
libssp.a -lssp
libssp_nonshared.a -lssp_nonshared
libstdc++.a -lstdc++
libsupc++.a -lsupc++
libvorbis.a -lvorbis
libvorbisenc.a -lvorbisenc
libvorbisfile.a -lvorbisfile
libvorbisidec.a -lvorbisidec
libz.a -lz
libzzip.a -lzzip
libzzipfseeko.a -lzzipfseeko
libzzipmmapped.a -lzzipmmapped
libzzipwrap.a -lzzipwrap

[ 説明 ]
libzzipwrap.a というライブラリをリンクしたい場合は、MAKEFILE の "LIBS=” の次の行に下記の記述をします。

# libzzipwrap.a を追加します
LIBS += -lzzipwrap




● C:\pspsdk\psp\sdk\lib の中にあるライブラリ
libpspatrac3.a libpspaudio.a libpspaudio_driver.a libpspaudiocodec.a libpspaudiolib.a
ibpspchnnlsv.a libpspctrl.a libpspctrl_driver.a libpspdebug.a libpspdebugkb.a libpspdisplay.a
libpspdisplay_driver.a libpspfpu.a libpspgdb.a libpspgdb_kernel.a libpspgdb_user.a libpspge.a
ibpspge_driver.a libpspgu.a libpspgum.a libpspgum_vfpu.a libpsphprm.a libpsphprm_driver.a
ibpsphttp.a libpspirkeyb.a libpspjpeg.a libpspkernel.a libpsplibc.a libpspmp3.a libpspmpeg.a
libpspmpegbase.a libpspmpegbase_driver.a libpspnand_driver.a libpspnet.a libpspnet_adhoc.a
ibpspnet_adhocctl.a libpspnet_adhocmatching.a libpspnet_apctl.a libpspnet_inet.a
libpspnet_resolver.a libpspopenpsid.a libpsppaf.a libpsppower.a libpsppower_driver.a
libpspprof.a libpspreg.a libpspreg_driver.a libpsprtc.a libpsprtc_driver.a libpspsdk.a
libpspsircs.a libpspssl.a libpspumd.a libpspumd_driver.a libpspusb.a libpspusb_driver.a
libpspusbbus_driver.a libpspusbcam.a libpspusbstor.a libpspuser.a libpsputility.a libpspvfpu.a
libpspvideocodec.a libpspvshbridge.a libpspwlan.a

○ C:\pspsdk\psp\sdk\lib の 各ライブラリのリンクの書き方 @MAKEFILE
ライブラリ名                 リンク記述
libpspatrac3.a -lpspatrac3
libpspaudio.a -lpspaudio
libpspaudio_driver.a -lpspaudio_driver
libpspaudiocodec.a -lpspaudiocodec
libpspaudiolib.a -lpspaudiolib
libpspchnnlsv.a -lpspchnnlsv
libpspctrl.a -lpspctrl
libpspctrl_driver.a -lpspctrl_driver
libpspdebug.a -lpspdebug
libpspdebugkb.a -lpspdebugkb
libpspdisplay.a -lpspdisplay
libpspdisplay_driver.a -lpspdisplay_driver
libpspfpu.a -lpspfpu
libpspgdb.a -lpspgdb
libpspgdb_kernel.a -lpspgdb_kernel
libpspgdb_user.a -lpspgdb_user
libpspge.a -lpspge
libpspge_driver.a -lpspge_driver
libpspgu.a -lpspgu
libpspgum.a -lpspgum
libpspgum_vfpu.a -lpspgum_vfpu
libpsphprm.a -lpsphprm
libpsphprm_driver.a -lpsphprm_driver
libpsphttp.a -lpsphttp
libpspirkeyb.a -lpspirkeyb
libpspjpeg.a -lpspjpeg
libpspkernel.a -lpspkernel
libpsplibc.a -lpsplibc
libpspmp3.a -lpspmp3
libpspmpeg.a -lpspmpeg
libpspmpegbase.a -lpspmpegbase
libpspmpegbase_driver.a -lpspmpegbase_driver
libpspnand_driver.a -lpspnand_driver
libpspnet.a -lpspnet
libpspnet_adhoc.a -lpspnet_adhoc
libpspnet_adhocctl.a -lpspnet_adhocctl
libpspnet_adhocmatching.a -lpspnet_adhocmatching
libpspnet_apctl.a -lpspnet_apctl
libpspnet_inet.a -lpspnet_inet
libpspnet_resolver.a -lpspnet_resolver
libpspopenpsid.a -lpspopenpsid
libpsppaf.a -lpsppaf
libpsppower.a -lpsppower
libpsppower_driver.a -lpsppower_driver
libpspprof.a -lpspprof
libpspreg.a -lpspreg
libpspreg_driver.a -lpspreg_driver
libpsprtc.a -lpsprtc
libpsprtc_driver.a -lpsprtc_driver
libpspsdk.a -lpspsdk
libpspsircs.a -lpspsircs
libpspssl.a -lpspssl
libpspumd.a -lpspumd
libpspumd_driver.a -lpspumd_driver
libpspusb.a -lpspusb
libpspusb_driver.a -lpspusb_driver
libpspusbbus_driver.a -lpspusbbus_driver
libpspusbcam.a -lpspusbcam
libpspusbstor.a -lpspusbstor
libpspuser.a -lpspuser
libpsputility.a -lpsputility
libpspvfpu.a -lpspvfpu
libpspvideocodec.a -lpspvideocodec
libpspvshbridge.a -lpspvshbridge
libpspwlan.a -lpspwlan


[ 説明 ]
libpspwlan.a というライブラリをリンクしたい場合は、MAKEFILE の "LIBS=” の次の行に下記の記述をします。

# libpspwlan.a を追加します
LIBS += -lpspwlan




PSPSDK のライブラリ全部をリンクさせる例 @MAKEFILE(ファイルの存在チェック用)
(警告) ライブラリを全部リンクさせると、起動できない実行ファイルが生成される場合があります。
     必要最低限のライブラリをリンクする様に勤めて下さい。
 検証しました@猫山

# ライブラリファイルの存在チェック用です。これをメインで使用しないようにお願いします!
# ===== C:\pspsdk\psp\lib section =====
LIBS += -lbulletml -lbz2 -lc -lfreetype -lg -lGL -lGLU -lglut -lglut -ljpeg -llua\
-llualib -lm -lmad -lmikmod -lobjc -logg -lpng -lpspvalloc -lpspvram\
-lSDL -lSDL_gfx -lSDL_image -lSDL_mixer -lSDL_ttf -lSDLmain -lsmpeg\
-lsqlite3 -lssp -lssp_nonshared -lstdc++ -lsupc++ -lvorbis -lvorbisenc\
-lvorbisfile -lvorbisidec -lz -lzzip -lzzipfseeko -lzzipmmapped -lzzipwrap
# ===== C:\pspsdk\psp\sdk\lib section =====
LIBS += -lpspatrac3 -lpspaudio -lpspaudio_driver -lpspaudiocodec\
-lpspaudiolib -lpspchnnlsv -lpspctrl -lpspctrl_driver\
-lpspdebug -lpspdebugkb -lpspdisplay -lpspdisplay_driver\
-lpspfpu -lpspgdb -lpspgdb_kernel -lpspgdb_user\
-lpspge -lpspge_driver -lpspgu -lpspgum -lpspgum_vfpu\
-lpsphprm -lpsphprm_driver -lpsphttp -lpspirkeyb\
-lpspjpeg -lpspkernel -lpsplibc -lpspmp3 -lpspmpeg\
-lpspmpegbase -lpspmpegbase_driver -lpspnand_driver\
-lpspnet -lpspnet_adhoc -lpspnet_adhocctl -lpspnet_adhocmatching\
-lpspnet_apctl -lpspnet_inet -lpspnet_resolver -lpspopenpsid\
-lpsppaf -lpsppower -lpsppower_driver -lpspprof\
-lpspreg -lpspreg_driver -lpsprtc -lpsprtc_driver\
-lpspsdk -lpspsircs -lpspssl -lpspumd -lpspumd_driver\
-lpspusb -lpspusb_driver -lpspusbbus_driver -lpspusbcam\
-lpspusbstor -lpspuser -lpsputility -lpspvfpu\
-lpspvideocodec -lpspvshbridge -lpspwlan




通常のビルド時に、標準でリンクされるライブラリについて

リンク ライブラリ名
-lpspdebug libpspdebug.a
-lpspdisplay libpspdisplay.a
-lpspge libpspge.a
-lpspctrl libpspctrl.a
-lpspsdk libpspsdk.a
-lc libc.a
-lpspnet libpspnet.a
-lpspnet_inet libpspnet_inet.a
-lpspnet_apctl libpspnet_apctl.a
-lpspnet_resolver libpspnet_resolver.a
-lpsputility libpsputility.a
-lpspuser libpspuser.a
-lpspkernel libpspkernel.a



[edit]

CM: 5
TB: 0

page top

コンパイラに渡すコンパイルオプションは、実行ファイルの生成に色々と影響を与えます。

以前 私は -O パラメータの値によって int のサイズが可変するらしいと書きましたが、実際に調べてみると、変化はありませんでした(4バイト固定)。
-O は、最適化を行なうオプションです。


数日、試行錯誤して私が下したコンパイルオプションは、下記のようになりました(MAKEFILE)。

CFLAGS = -march=allegrex -mips2 -mabi=eabi -Wall -G0 -O3\
     -fomit-frame-pointer -mgp32 -mlong32



以下に、解説を書きます。

参考にしたページ(部分引用&部分コピペ)

  http://www.sra.co.jp/wingnut/gcc/gcc-j.html




psp-gcc の コンパイルオプション

-c コンパイル、アセンブルするが、リンクを行なわない
-S コンパイルのみ -- アセンブル、リンクを行なわない
-E プリプロセスのみ -- コンパイル、アセンブル、リンクを行なわない
-pass-exit-codes フェーズからのエラーコードの最大値を exitコードとして返す
--help ヘルプ情報を表示
--target-help ターゲット固有のコマンドラインオプションを表示
--help={target|optimizers|warnings|undocumented|params}[,{[^]joined|[^]separate}]
特定のタイプのコマンドラインオプションを表示する
-dumpspecs 組み込まれた spec 文字列を全て表示
-dumpversion コンパイラのバージョンを表示
-dumpmachine コンパイラのターゲットプロセッサを表示
-print-search-dirs コンパイラのサーチパスにあるディレクトリを表示
-print-libgcc-file-name コンパイラのコンパニオンライブラリ名を表示
-print-file-name=<lib> ライブラリ <lib> へのフルパスを表示
-print-prog-name=<prog> コンパイラの部品 <prog> へのフルパスを表示
-print-multi-directory libgcc のバージョンディレクトリルートを表示
-print-multi-lib コマンドラインオプションと複数のライブラリ探索
-print-multi-os-directory ディレクトリとの対応を表示
-print-sysroot-headers-suffix ヘッダー探しに使われるシスルートサフィックスを表示
-Wa,<options> カンマ区切りの <options> をアセンブラに渡す
-Wp,<options> カンマ区切りの <options> をプリプロセッサに渡す
-Wl,<options> カンマ区切りの <options> をリンカに渡す
-Xassembler <arg> <arg> をアセンブラに渡す
-Xpreprocessor <arg> <arg> をプリプロセッサに渡す
-Xlinker <arg> <arg> をリンカに渡す
-combine すぐにコンパイラに多数のソースファイルを渡す
-save-temps 中間ファイルを削除しない
-pipe 中間ファイルではなくパイプを使う
-time 子プロセスごとの実行時間を計測する
-specs=<file> 標準の specs ファイルを読み込んだ後に <file> を処理し、
     ドライバプログラムである psp-gcc が、コンパイラやアセンブラやリンカ等に
     渡すべきオプションを決定するときに使うデフォルトを変更する。
-std=<standard> 入力ソースを <standard> と見なす
--sysroot=<directory> ヘッダーとライブラリのルートディレクトリとして<directory>を
             使用する
-B <directory> <directory> をコンパイラの探索パスに追加する
-b <machine> インストールされていればターゲット <machine> として
gcc を実行する
-V <version> インストールされていれば <version> バージョン番号の
gcc として実行する
-v コンパイラによって起動されるプログラムを表示
-### -vに似ているがオプションは引用されず、コマンドは実行されない
-x <language> 次のインプットファイルの言語を<language>に指定
許される言語は C C++ アセンブラ 'none' を含む
'none' は、ファイル拡張子に従った言語




警告メッセージ関連のオプション

-w すべての警告メッセージを表示しない
-Wall 殆んどの警告メッセージを有効にする




MIPS用オプション

PSPに採用されているCPUは、MIPS社のR4000の32bitカスタムCPU「Allegrex」。
対応クロックは1~333MHz。パワーセービングのための拡張命令を持ち、FPUとVFPUが直結されている。


一覧
-EB -EL -g -g2 -G<num> -mips1 -mips2 -mips3 -mips4 -mips5 -mips32
-mips32r2 -mips64 -mips64r2
-march=<CPU> -mtune=<CPU> -m<CPU>
-no-m<CPU> -mips16 -no-mips16 -mfix-vr4120 -mfix-vr4130 -mgp32
-mfp32 -mno-shared -msym32 -O0 -O --[no-]construct-floats --trap
--no-break --break --no-trap -KPIC -call_shared -non_shared -xgot -mpdr
-mno-pdr -mshared -mno-shared -mabi=<ABI> -32 -n32 -64

解説
-march=<CPU>
  命令スケジューリングの際の機種のデフォルトを <CPU> と想定する。
  <CPU> は、
  mips1, mips2, mips3, mips4, mips5, mips32, mips32r2, mips64, mips64r2, r3000
  , r2000, r3900, r6000, allegrex, r4000, r4010, vr4100, vr4111, vr4120, vr4130
  , vr4181, vr4300, r4400, r4600, orion, r4650, r8000, r10000, r12000, vr5000
  , vr5400, vr5500, rm5200, rm5230, rm5231, rm5261, rm5721, rm7000, rm9000
  , 4kc, 4km, 4kp, 5kc, 20kc, sb1, from-abi
  のどれかである。

ある特定の <CPU> を選ぶとその特定のチップに適したスケジューリングを行なう一方で、-mipsX や -mabi を指定しない限り、MIPS ISA(Instruction Set Architecture、命令セットアーキテクチャ)のレベル 1 に合わないコードは何も生成しない。

-mips1
  MIPS ISA のレベル 1 の命令を発行する。これがデフォルトである。r3000 が、この ISA レベルのデフォルトの CPU タイプである。

-mips2
  MIPS ISA のレベル 2 の命令(branch likely, square root 命令)を発行する。r6000 が、この ISA レベルのデフォルトの CPU タイプである。

-mips3
  MIPS ISA のレベル 3 の命令(64ビット命令)を発行する。r4000 が、この ISA レベルのデフォルトの CPU タイプである。

-mips4
  MIPS ISA のレベル 4 の命令(条件付き move 命令、プリフェッチ命令、強化された FPU 命令)を発行する。r8000 は、この ISA レベルのデフォルトの <CPU> である。

-mgp32
  32個の32ビット汎用レジスタが利用可能であることを仮定する。これはデフォルトである。

-mlong32
  long 型を int 型と同じ 32 ビットにする。

-EB ビッグエンディアンのバイト順を使用する
-EL  リトルエンディアンのバイト順を使用する

-G<number>
  <number> バイト以下の大きさのグローバルなデータ項目と静的なデータ項目を、普通のデータセクションや bss セクションではなく、小データセクションや小 bss セクションに置く。これにより、アセンブラが、通常の 2 命令のメモリ参照の代わりに、グローバルポインタ(gp あるいは $28)に基づいた一命令のメモリ参照を生成することが可能になる。<number> のデフォルト値は、MIPS のアセンブラを使う場合は 8。


-G<number> オプションはアセンブラとリンカにも渡される。
全てのモジュールは、同じ値の -G<number> でコンパイルしなければならない。


最適化オプションとして -O2 を使う場合は、-Olimit 3000 も使う必要がある。この二つのオプションはどちらも、configure が構築するMakefile には自動的に追加される。make の変数 CC を上書きして MIPS のコンパイラを使うには、-Wf,-XNg1500 -Olimit 3000 を追加する必要がある。





最適化オプション

-O0
  最適化を行なわない。

-O
-O1

  完成したコードのサイズを小さくし、実行速度が速くなるよう最適化処理を施す。
  最適化を行なう。最適化を行なうコンパイルには幾らか余計に時間がかかり、大きな関数についてはたくさんのメモリを余計に使う。
  -O を指定しない場合は、コンパイラの目標はコンパイルのコストを小さくすることとデバッグが期待どおりの結果にすることである。各文は独立している。文と文の間にブレークポイントを設定してプログラムを止めたとき、どの変数にも新たな値を代入できるし、プログラムカウンタを変更して、その関数内の他のどの文にも飛ばすことができ、そしてソースコードから期待できる結果と全く同じものが得られる。
  -O を指定しないと、register 宣言した変数しかレジスタに割り当てない。コンパイル結果のコードは、-O なしの PCC で作られるよりもやや悪い。
  -O を指定すると、コードサイズと実行時間を小さくしようとする。
  -O を指定すると、全機種で -fthread-jumps と-fdefer-pop を有効にする。
-fthread-jumps は、ジャンプスレッドの最適化を行なう
-fdefer-pop は、関数引数をスタックから pop するのを呼び出し後まで遅らせる
遅延スロットのある機種では-fdelayed-branch をオンにし、フレームポインタなしでもデバッグをサポートできる機種では -fomit-frame-pointer をオンにする。機種によっては、他のオプションをオンにするものもある。
-fdelayed-branch は、分岐命令の遅延スロットを使うことを試みる
-fomit-frame-pointer は、可能な場合、スタックフレームを生成しない

-O2
  -O1 よりも頑張って最適化する。psp-gcc の持つほとんどの最適化が有効になる。
  さらなる最適化を行なう。GCC は、スペース-速度のトレードオフを含まないほとんど全ての最適化を実行する。-O2 を指定した場合は、ループ展開や関数のインライン展開を行なわない。-O と比べると、このオプションはコンパイル時間が増え、生成コードの効率が良くなる。
  -O2 を指定すると、ループ展開と関数のインライン展開、それに厳密なエイリアシングを除いた全ての最適化が有効になる。また、全ての機種で -fforce-mem オプションを付け、デバッグと干渉しない機種ではフレームポインタの削除を行なう。
-fforce-mem は、メモリオペランドについて算術演算を行なう前に、そのメモリオペランドをレジスタに強制的にコピーさせる。この結果、全てのメモリ参照を潜在的な共通部分式とすることにより、生成コードが良くなる。これらのメモリ参照が共通部分式でない場合は、命令組合せフェーズが独立したレジスタへのロードを削除する必要がある。-O2 を指定するとこのオプションが有効になる。

-O3
  さらに頑張る。関数のインライン化、レジスタリネーミングが有効となる。
  -O3 は -O2 で指定される全ての最適化を行ない、かつ inline-functions オプションを行なう。
inline-functions は、単純な関数を呼び出し側に統合する

-Os
  -O2 の最適化と同じ程度であるが、完成するコードのサイズを小さくするように頑張る。
  サイズについて最適化する。-Os を指定すると、普通はコードサイズを大きくしない -O2 の最適化を全て有効にする。また、コードサイズを小さくするよう設計されたさらなる最適化を実行する。

● -O オプションを複数指定した場合は、最適化レベルの数字が付いていてもいなくても、最後に指定したオプションが有効になる ●

-fomit-frame-pointer
  フレームポインタを必要としない関数については、フレームポインタをレジスタに保持しないようにする。これにより、フレームポインタをセーブ、設定、リストアする命令をなくすことができる。また、多くの関数で利用可能なレジスタが一つ増える。また、機種によってはデバッグが不可能になる。

  機種によっては、Vax のように、このオプションの効果がないものもある。標準の呼び出しシーケンスが自動的にフレームポインタを取扱うので、フレームポインタが存在しない振りをしても何もセーブされないからである。



全てのモジュールは、同じ値の -G<number> でコンパイルしなければならない。



参考までに、他の Cコンパイラ のコンパイルオプションの解説ページを貼り付けておきます。

GCC の コンパイルオプション解説
http://www.sra.co.jp/wingnut/gcc/gcc-j.html#Invoking%20GCC
http://argent.shinshu-u.ac.jp/lab/math/note/gcc-option.pdf

BCC の コンパイルオプション解説
http://docs.embarcadero.com/products/rad_studio/radstudio2007/RS2007_helpupdates/HUpdate4/JA/html/devwin32/bcc32_xml.html


【 関連記事 】
PSPプログラミング EBOOT.PBP 生成用 Makefile 記述方法
PSPプログラミング プラグイン生成用 Makefile 記述方法
PSPプログラミング PSPSDK に同梱されているライブラリの一覧とリンク記述

[edit]

CM: 2
TB: 0

page top

PSPの実行モジュールは、PlayStation2 の様に、ELF形式のモジュールをベースにしています。


カーネルは、ネイティブコードで書かれた3通りのファイルを実行可能。

【 実行可能なファイル形式 】

ELF - ベーシックELF形式
      ハードコードされたアドレスにリンクされる(一般的には0x8900000番地以降へ)
prx - カスタマイズされたELF形式
      メモリ中のどこにでもリロケートできる。プラグイン等が そう。
~PSP - 暗号化された実行モジュール

PSPSDK では、ELF や prx は生成できるが、~PSPへの暗号化は出来ません。

【 モジュール情報の構成 】
・モジュール名
・モジュールの属性。カーネルモジュールなど
・関数テーブル(未調査/情報求む)
・ヴァージョン

書き方

PSP_MODULE_INFO(モジュール名, モジュールの属性, ヴァージョン正数, ヴァージョン小数);
PSP_MAIN_THREAD_ATTR( メインスレッドの属性 );


書き方の説明
PSP_MODULE_INFO( )
 モジュール情報を設定するマクロ
  ・モジュール名
    英数記号での文字列(モジュールの名前 を 記述)
  ・モジュールの属性
    PSP_MODULE_KERNEL もしくは 0x1000 で カーネルモード
    PSP_MODULE_USER もしくは 0 で ユーザーモード
    0x0800 で VSH モード
    0x1006 もあります (詳細不明)
  ・ヴァージョン正数
    モジュールのヴァージョン情報(正数部分)/おまけで記述する
  ・ヴァージョン小数
    モジュールのヴァージョン情報(小数点以下部分)/おまけで記述する

PSP_MAIN_THREAD_ATTR( )
 メインスレッド(main関数を実行するスレッド)の属性を設定するマクロ
   カーネルモードなら 0 を記述
   ユーザーモードなら THREAD_ATTR_USER を記述


サンプルを書いてみる

カーネルモードのサンプル

PSP_MODULE_INFO("NICEGAME1", PSP_MODULE_KERNEL, 0, 0);
PSP_MAIN_THREAD_ATTR(0);


ユーザーモードのサンプル

PSP_MODULE_INFO("NICEGAME2", PSP_MODULE_USER, 0, 0);
PSP_MAIN_THREAD_ATTR(THREAD_ATTR_USER);




実行モジュールをバイナリダンプしてみた。

150.PBP
0000:0000 00 50 42 50  PBP
0000:3251 7E 50 53 50 ~PSP

330.PBP , 550.PBP
0000:0000 00 50 42 50  PBP
0000:3445 7E 50 53 50 ~PSP

某.PBP (Homebrew)
0000:0000 00 50 42 50 PBP
0000:1BFB 45 4C 46   ELF

俺作ゲーム.PBP
000000 00 50 42 50  PBP
003C6C 45 4C 46   ELF

music.prx
000000 7F 45 4C 46  ELF

ScreenShot2.prx
000000 7E 53 43 45 40 ~SCE@
000040 7E 50 53 50   ~PSP


【 参考にしたページ 】
アセンブリではじめるPSPセミナー(資料)

【 関連記事 】
PSPプログラミング EBOOT.PBPの構造を知ろう!
PSPプログラミング PSP の 1.50カーネルとか、3.xxカーネルとか についての講釈
PSPプログラミング EBOOT.PBP 生成用 Makefile 記述方法
PSPプログラミング プラグイン生成用 Makefile 記述方法

[edit]

CM: 0
TB: 0

page top

この記事は、PSP各種 に対応した Homebrew の作成方法について書きます。


CFW導入済みPSP-1000 は、カーネルモードの抑止機能が無いので、カーネルモードで書かれたプログラムの起動と、ユーザーモードで書かれたプログラムの起動が出来ます。

CFW導入済みPSP-2000 以降では、カーネルモードに対して抑止機能が働くので、ユーザーモードで書かれたプログラムの起動しか出来ません。

ただし、eLoader v1.000LEDA - Legacy Software Loader beta 0.2カーネル1.50のソフトをCFW3.xx用に変換するソフト Ver.0.2 などのアプリによって、カーネルモードのプログラムを CFW導入済みPSP-2000 でも起動させる事は可能です。

2009年 2月 5日に QJ.net に登録された LEDA - Legacy Software Loader beta 0.2 は、ベータ版ですが、バージョン2ですYO!



CFW導入済みPSP-1000専用のコーディング方法は、カーネルモードで作成すればよいので、プログラムソースの冒頭にて、下記の例のように記述します。

PSP_MODULE_INFO("NICEGAME1", PSP_MODULE_KERNEL, 0, 0);
PSP_MAIN_THREAD_ATTR(0);

↑↑ 赤色部分は自由に書き換えて下さい。

CFW導入済みPSP-2000以降にも対応した実行モジュールを作成するコーディング方法は、ユーザーモードで作成します。
プログラムソースの冒頭にて、下記の例のように記述します。

PSP_MODULE_INFO("NICEGAME2", PSP_MODULE_USER, 0, 0);
PSP_MAIN_THREAD_ATTR(THREAD_ATTR_USER);

↑↑ 赤色部分は自由に書き換えて下さい。
↑↑ この記述でプログラムをコーディングすると、全ての CFW導入済みPSP に対応した Homebrew の作成が可能です。


P.S.
コンパイルオプションのパラメータにて、
 -D_PSP_FW_VERSION=300

MAKEFILE内での記述にて、
 PSP_FW_VERSION=300

のどっちかを指定すると、CFW導入済みPSP-2000 にも対応した(ファームウェア3.00用) Homebrew が作れる、というのは間違いです(検証済み@カーネルモードのには無意味でした)。

PSPSDK では、暗号化された ~PSP は生成できませんよ、と書いておきます(前の記事を参照)。
暗号化で どう違うのかは バイナリエディタでダンプして閲覧したり、逆アセンブラで閲覧したりすると解るかも知れません。

[注意] PSP関連に対しては、リバースエンジニアリングの禁止という禁止項目が無いようですが(UMDソフトの説明書には書かれていませんが)、ソフトウェア一般には適応されている事が多いのです。
 リバースエンジニアリングの禁止とは、ソフトウェアを逆アセンブルとか逆コンパイルしてソースにしたり、解析しちゃ、ダメよ、って命令の事です。

リバースエンジニアリング
「リバースエンジニアリング禁止」の是非
つまり、PSPのファームウェアのリバースエンジニアリングが禁止と宣言されていたら、解析しちゃダメなのでっす。新しいカスタムファームウェアが作れない、という罠…Orz。


後で紹介する、DXライブラリPortable を利用してのプログラミングでは、mp3 をハードウェアエンコードさせる処理があるので、MediaEngine側のCPUでmp3音声をデコードしているので、ユーザーモードで記述しないとダメですよっ

訂正。

【 関連記事 】
PSP の 1.50カーネルとか、3.xxカーネルとか についての講釈
PSPプログラミング EBOOT.PBP 生成用 Makefile 記述方法
PSPプログラミング プラグイン生成用 Makefile 記述方法

[edit]

CM: 2
TB: 0

page top

Ryushi さんが、ニコニコ動画にて PSPプログラミング というコミュニティを開設しておられます。

今週の月曜日には、そのコミュニティで 憂煉さん(DXライブラリPortableの作者さん)が、ニコ生放送 PONG(ホッケー)を作る過程を実況して下さいました。

乙です!

こんな感じで(クリックで拡大)
PONG(ホッケー).png

コミュに参加したい方は、下記URLにアクセスして下さい(参加申請後、自動承認)。
http://ch.nicovideo.jp/community/co45104


[edit]

CM: 0
TB: 0

page top

PSP dev kit


UMDドライブが付いてるし、どうやらコレが正式な開発マシンみたいです。

↓↓ これ(写真)
http://www.eurasia.nu/wiki/index.php?pagename=PspDevKitPic


なんか、普通のパソコンと変わらない外見だなwww


[edit]

CM: 0
TB: 0

page top

きまぐれblog の Takka氏が、全角文字表示ライブラリを公開しました。

いろいろ調べてみます。


以下、記事を転載
Rockbox用のフォントファイルが利用出来ます

>利用制限は特にありませんが、利用したことを教えていただければありがたいです


該当記事
fnt_print 1.00


[edit]

CM: 0
TB: 0

page top

調べておいたC言語/C++言語に関する良質サイトリンクを一挙紹介しました。

右の棚に陳列してありますので各自勉強しに行ってみて下さい。


あと、「ここは良いサイトです~」とかのサイトの紹介を受け付けます。


[edit]

CM: 0
TB: 1

page top

ニコニコ動画のコミュニティ「巻尾工房(まきおこうぼう)」さんにて、

第一回 初心者向け C言語+Win32API講座【ウィンドウを表示してみよう】
という生放送が行なわれます。要チェックですよー!!

URLは、http://com.nicovideo.jp/community/co72768

生放送の日時
2010年4月17日(土曜日) AM 8:00~
終了時刻未定

以前もこの時間帯に生放送がありました。私はタイムシフト予約をして観ました。
忙しい人はタイムシフト機能を使えば良いと思います。


[edit]

CM: 0
TB: 0

page top

ニコニコ動画のコミュニティ「巻尾工房(まきおこうぼう)」さんにて、

第二回 初心者向け C言語+Win32API講座【何かグリグリ動けばいいね】
という生放送が行なわれます。要チェックですよー!!

URLは、http://com.nicovideo.jp/community/co72768

生放送の日時
2010年4月24日(土曜日) AM 8:30~
終了時刻未定

以前もこの時間帯に生放送がありました。
忙しい人はタイムシフト機能を使えば良いと思います。

[edit]

CM: 0
TB: 0

page top

PSPプログラミング 噂 の Half-Byte Loader 検証 

2010/05/01
Sat. 07:29

GNU General Public License なライセンスの ソフトウェア Half-Byte Loader を使って、PSP Homebrew の起動実験をしてみました.

古いデジカメで撮影したので画質が悪いです、ゴメンなさい.


実験に使った環境
・正規ファームウェア6.20 の PSP-2000
・パタポン2体験版(英語版)
・exploitセーブデータ(4/16の日付のん)
・パタポン2体験版(英語版) Half-Byte Loader Revision 109

起動成功したPSP自作ソフト
・PSP Revolution v0.4
・JzBMSPlayer v051222
・じゃんけんゲーム パワードX
・PSPデスクトップ ドドド 改



実験に使った環境
・正規ファームウェア6.20 の PSP-2000
・みんなのGOLF(市販ゲームソフト)
・exploitセーブデータ(新版)
・みんなのGOLF Half-Byte Loader Revision 110

起動成功したPSP自作ソフト
・みくねぎっと。お試し版
・イントラフォント・テスト


詳しく知りたい方は、私のホームページの無駄ニュースへどうぞ.
>> 自作ゲームを正規PSPで遊ぶ方法 ~ Half-Byte Loader の解説


[edit]

CM: 5
TB: 0

page top

私は、ゲーム開発にはお金がかかる、と書きました。
でも、無駄な出費を抑える事は賢いことです。

ゲームに必要な要素として、絵と音があげられます。
絵が無いと、何も表示させる事ができません
音が無いと、さみしいゲームになります(無音だから静かに遊べるかも?)
その、絵や音の素材を、当ブログでも リソースと呼ぶ事にします。
リソースは、CGと録音した音で十分ですが、一般のユーザーには そう簡単に用意は出来ません。

そこで、いつか書こうと思っていた、無料で使えるボーカロイドソフトのような個人作成のソフトウェアをご紹介します。
丁度、2日前に重音テトさんの利用条件が明確に更新されたのですよ。ツインドリルがんばってるなw

歌声合成ツールUTAU

正確にはシェアウェアなのですが、無料での使用が許可されています。
支払わなければ無料、という作戦(^^;;;;;

とりあえず、どんなアプリなのか紹介ページへ動画を観に行きましょう。
>> http://utau2008.web.fc2.com/

このページを順番に読みます。
下側に動画があるので観て下さい。


なるほど、「人力ボーカロイド」というモノらしいですね。
クリプトン社製のボーカロイドシリーズの代用に使えます!
ボカロ製品を購入している人も使って損はありませんよ。色んな声が使えるのだから(300種類以上だという話です)

[ ダウンロード&導入手順 ]
1.ページの上側の、ダウンロード をクリックします
2.インストーラをダウンロードして保存し、ダブルクリックでインストールします
  > DOWNLOAD
  > ■2010/05/25 最新版 v0.2.76
  > v0.2.76 インストーラ
3.VB6.0ランタイムは要りませんよ
4.歌声データ defaultvoice.uar(デフォルトv1.0) をクリックしてダウンロード保存
5.UTAUを起動します
6.4でダウンロードした defaultvoice.uar(デフォルトv1.0)を、UTAUの画面内にドラッグ&ドロップします
7.デフォ子の歌声データがインストールされます
    defoko.png
8.デフォ子以外の 歌声データのダウンロードやインストールは お好みで!
  ZIPファイルでも、まず、ドラッグ&ドロップしてインストール出来るか試してください
  出来ない場合は、解凍して ~~\UTAU\voice\ 以下へ入れます

[ 操作方法 ]
これは、各自で使ってもらい、慣れるしかありません
今日紹介した理由は、みくねぎっと。の改造をする際の予行で、今のうちに色々なツールを使いこなせるようにしてもらう為です
みくねぎっと。のソースコード公開は、学生さんが 夏休み に入る頃から徐々に始めようかと考えてますが、まだDXライブラリPortable の基礎準備の解説をやるので夏が過ぎちゃうかも知れません


UTAUの音源は300種類以上と書きました

Q.「どこで配布してるのか教えてください」
A.「UTAU ユーザー互助会@ ウィキ」さん にて紹介されていますので、利用規約を良くお読みの上でご利用下さい

ボクは、デフォ子さん と 重音テトさん と 桃音モモさん だけ頂きましたが(^^;;;;;

どんな歌声なのか、動画で 観て 聴いて下さい

デフォ子さん サンプル動画リンク @ニコニコ動画
重音テトさん サンプル動画リンク @ニコニコ動画
桃音モモさん サンプル動画リンク @ニコニコ動画


【重音テト】おちゃめ機能【アニメ風PV】



[edit]

CM: 0
TB: 0

page top

PSPは、32ビットのコンピュータです。よって、扱うデータは全て、まず32ビット単位で得られます。

例えば CHARキャストは8ビットですが、この値も、まず 32ビットで取り出されてから 8ビットデータへと削られます。
プログラミングでは、符号あり8ビット、符号無し8ビット、と区別されますが、元が32ビット数値ですので 8ビットデータへ削る際には、符号が重要視されます。

マイナス1は、32ビット2進数では 111111111111111111111111111111 です。
これを 8ビット化すると、2進数表記では 11111111 です。
この 11111111 という2進数は、符号無し8ビットでは 255 と解釈され、符号あり8ビットでは -1 と解釈されます。
一般に、符号は「解釈」です

-2,147,483,648 という10進数 数値は、2進数では 1000000000000000000000000000 です。
これを 8ビット化する場合、符号無し8ビット化では 元の数値を符号無し32ビット数値と捕らえられ 2,147,483,648 という正数数値に解釈して、00000000(桁あふれ)と8ビット化されます(コンパイラが判断します)。
符号あり8ビット化では 10000000 と、最上位のマイナスを示すビットが1になる数値に修正されて8ビット化されます(コンパイラが判断します)。
「符号あり」では、最上位ビットが符号を現していますので、符号ビット+7桁ビットという構成ですね。

signed int A = -2,147,483,648;
unsigned char U8;
signed char S8;

[edit]

CM: 0
TB: 0

page top

PS3 NEWS - PlayStation 3 News - PS3News - PS3 Games - PS3 Hacks - PS3 Homebrew

↑↑ PS3 NEWS(お気に入りに入れようとすると、こんな名前です)で、アカウントを取得してサーフィンしてから いざファイルのダウンロードをしようとしたら、「ファイルをダウンロードする許可権利を購入しないとダメっ」ってメッセージがでました。ぐはっ、有料なのね。お値段は、$13.96のようなので、$1=¥120円で換算すると、$13.96=¥1675.2円です。
ボクの作ったPSP同人ゲームより微妙に高い値段だなw

まぁ、その程度の額は、すぐ払えますよ。問題は、クレジットカードを持ってないよ、というユーザーさん。

仕方ないので、そこでダウンロードした物については記事にしない方針にしようと思いました。
UMDISOのフォーマットが書かれている書物とかあるみたいだけどな(未調査)

[edit]

CM: 0
TB: 0

page top




憂煉氏の新ライブラリ製作中の実験動画です
憂煉氏ががんばってくれています。C++版 DXライブラリPortable のリリースが待ち遠しいぞ!

ボクはねんどろいど風のMikuMikuDanceモデルを使って何かを開発中。

ボクの場合、Windows7 32Bit Ultimate で MikuMikuDance をするには、Windows2000互換モードにして「管理者モードで起動する」のチェックを入れなければ起動しました。


毎日少しずつ書き物をする時間を作って記事を製作してますが、読みやすい分かりやすい文章は苦労します
みくねぎっと乙。の開発講座はちゃんとやりますので見捨てないでね

今週中に1ページ追加したいですが

[edit]

CM: 0
TB: 0

page top

一応、プログラミング技術に関わることだと思うので、実験。

過去記事 PSPプログラミング EBOOT.PBPの構造 とりあえずここまで調べたよ版 を参考に、バイナリエディタで操作。

カスタムファームウェアは 年齢制限が解除されているので 年齢制限を設定しておきます


オフセット値(アドレス):00000130 の値を、0x01 から 0x0B の間で変更してみると……。


↑ こんな風になりました。実験成功!
紛らわしいですが、PS1 のEBOOT.PBP を弄ったのではなく、PSPSDKで出力された EBOOT.PBP を弄ったのですよ

この実験は、バイナリエディタで簡単に出来るので、トライしてみては如何かな?


ちゅうい:この実験は、年齢制限の解除を目的としているのではありません

[edit]

CM: 0
TB: 0

page top

2010年9月23日更新

PSPSDKで作成される EBOOT.PBP ファイルの構造を、もっと詳しく調べてみました。
余計なファイルを含まない状態の EBOOT.PBP を解析して書いていますので、他の自作ソフトとはアドレスが異なる場合があります。

知っておいて欲しい事
PSPは32ビットCPUです。指定アドレスからの32ビットデータの4バイトはリトルエンディアン方式で並びます。左の値から右の値を、下位から上位、という風に解釈して下さい

つまり、下記の場合は
アドレス 00000000:AA 01 C8 22
 0x22C801AA という値が入っている、という事です


NAGAOKASTATIONさんの資料を参考にしました。
http://nagaokastation.com/psp_ebootpbp.html

先頭40バイトが EBOOT.PBPヘッダー部分
アドレス   値
00000000 00 50 42 50 "\0PBP"
00000004 00 00 01 00
00000008 (PARAM.SFO の先頭アドレスへのオフセット値:28 00 00 00)
0000000C (ICON0.PNG の先頭アドレスへのオフセット値:NULLだと C0 01 00 00)
00000010 (ICON1.PMF の先頭アドレスへのオフセット値:NULLだと C0 01 00 00)
00000014 (ICON1.PNG の先頭アドレスへのオフセット値:NULLだと C0 01 00 00)
00000018 (PIC1.PNG の先頭アドレスへのオフセット値:NULLだと C0 01 00 00)
0000001C (SND0.AT3 の先頭アドレスへのオフセット値:NULLだと C0 01 00 00)
00000020 (DATA.PSP の先頭アドレスへのオフセット値:プログラム部分 C0 01 00 00)
00000024 (DATA.PSAR の先頭アドレスへのオフセット値:大抵、ここで終わる)

次の41バイト目からは PARAM.SFO ファイルの内容です
PARAM.SFO の先頭16バイト部分の内訳は資料参考しました
アドレス  値
00000028 00 50 53 46 "\0PSF"
0000002C 01 01 00 00
00000030 ?? ?? ?? ?? ラベル(Key)が格納されている先頭アドレス
00000034 ?? ?? ?? ?? データ(Keyの値)が格納されている先頭アドレス
00000038 ?? ?? ?? ?? ラベル数(ソースコード中の関数の個数)
その後、ラベル数×16バイトの構成でデータが存在(データ長が可変します)
↓↓(16バイト の うちわけ)
:0000 ?? ?? ラベルが格納されているオフセットアドレス
:0002 ?? 0 (不明)
:0003 ?? 2:文字列(unicode)/4:数値/0:バイナリ
:0004 ?? ?? ?? ?? 実際のデータ領域
:0008 ?? ?? ?? ?? データ領域
:000C ?? ?? ?? ?? データが格納されているオフセットアドレス
 ↑↑この構成が、ラベル数の分だけ存在して、次のセクションへ

-- ↓↓この位置(000000BC)は、アドレス:00000038 の 内容値に
16をかけて計算で求める事ができます --

アドレス 値(文字列)
000000BC "BOOTABLE" 00
000000C5 "CATEGORY" 00
000000CE "DISC_ID" 00
000000D6 "DISK_VERSION" 00
000000E3 "PARENTAL_LEVEL" 00
000000F2 "PSP_SYSTEM_VER" 00
00000101 "REGION" 00
00000108 "TITLE"
0000010C 00 00 00 00 01 00 00 00
00000114 4D 47 00 00 ← "MG.."

アドレス  値
00000118 "UCJS10041" 00 00 00 00 00 00 00 ← ゲームID(16バイト)
00000128 "1.00"
0000012C 00 00 00 00
00000130 01 00 00 00 ← (視聴年齢制限レベル:0x01~0x0B)
00000134 "1.00"
00000138 00 00 00 00 00 80 00 00

ゲーム名セクション(短い場合もあります。可変長)
00000140 最長128バイトのUTF-8文字列。
000001BF 末尾は 0x00

(ICON0.PNG セクション:ファイルサイズの分だけ追加されます)
(ICON1.PMF セクション:ファイルサイズの分だけ追加されます)
(ICON1.PNG セクション:ファイルサイズの分だけ追加されます)
(PIC1.PNG セクション:ファイルサイズの分だけ追加されます)
(SND0.AT3 セクション:ファイルサイズの分だけ追加されます)

(DATA.PSP セクション:ELFセクション)
参考サイト:http://d.hatena.ne.jp/tatsu_pc/20100501/1272709062
アドレス  値
000001C0 7F 45 4C 46 マジックナンバー "\127ELF"
000001C4 01 32bitアーキテクチャ(ELFCLASS32)
000001C5 01 2の補数、リトルエンディアン(ELFDATA2LSB)
000001C6 01 ELF仕様のバージョン(EV_CURRENT)
000001C7 00 ターゲットOSとアーキテクチャ(ELFOSABI_ARM)
000001C8 00 ABIのバージョン(ELFOSABI_ARMに準拠する)
000001C9 00 00 00 以降、予約済み
000001CC 00 00 00 00 ( 〃 )
000001D0 02 00 08 00 ( 〃 )

プログラム部分展開 開始位置セクション
000011D8 暗号化されてないのでニーモニックコードが良く分かります
     メインメモリーに読み込まれる部分です

(DATA.PSARセクション)


年齢制限PSPゲームを作るなら、視聴年齢制限レベルの部分を弄ってやればイイという結論。
しかし、カスタムファームウェアって、視聴年齢制限レベルを切った状態がデフォルトなのですが(^^;;;


[edit]

CM: 2
TB: 0

page top


h o m e | n e x t  »


 

2017-09