Palm OS Programmer’s Companion Volume I/6-1 - project-enigma

Palm OS Programmer’s Companion Volume I/6-1

>> Site top >> Misc >> In my palm >> Palm開発ドキュメントの和訳 >> Palm OS Programmer’s Companion Volume I >> Palm OS Programmer’s Companion Volume I/6-1

最終更新日付:2014/01/01 00:00:00

↑6 章トップへ 2 節に進む →

6-1 データマネージャ

 

伝統的なファイルシステムでは、まずディスクからメモリ上のバッファにファイルの全部または一部を読み込み、次にそのバッファ上の情報を参照したり更新(あるいはその両方を)し、最後に更新されたメモリバッファをディスクに書き戻します。Palm ハンドヘルドはダイナミックRAMの大きさに制限があり、またディスクストレージのかわりに不揮発性のRAMを使用しているため、伝統的なファイルシステムは Palm OS のユーザーデータを保存したり読み出したりするのに適してはいません。

Palm OS は全ての情報に対してインプレイスでアクセス、および編集を行ないます。これにより、ダイナミックメモリの必要量を減らし、ファイルシステムを含むメモリバッファ間のデータ転送のオーバーヘッドを取り除くことができます。

さらに利点として、Palm ハンドヘルド内のデータは、メモリ空間全体に散在させられる有限サイズの複数のレコードに分割することができます。これにより、レコードの追加、削除、リサイズにおいてメモリ中の他のレコードを移動させる必要がありません。データベース内の各レコードは、実際にはメモリマネージャのチャンクです。データマネージャはデータベースレコードのアロケート、削除、リサイズを行なうためにメモリマネージャ関数を使用します。

このセクションではデータマネージャの使い方を説明します。以下のトピックがあります。

 

レコードとデータベース

データベースは関連するレコードをまとめています。全てのレコードは1つの、そして1つだけのデータベースに所属します。データベースはアドレス帳や予定表などの全エントリのコレクションであったりします。Palm OS アプリケーションは、伝統的なファイルシステムにおいてファイルの作成、削除、オープン、クローズができるように、必要に応じてデータベースの作成、削除、オープン、クローズを行なうことができます。同じメモリカード上にある限り、特定のデータベースのレコードを配置する場所に制限はありません。あるデータベースのレコードが、メモリ内で1つ以上の他のデータベースのレコードと一緒に散らばっていることもできます。

データベースによってデータを保存するのは、Palm OS メモリマネージャのデザインにうまくフィットしています。ダイナミックヒープを除く全てのヒープは不揮発性なので、データベースのレコードはダイナミックヒープ以外の全てのヒープに保存することができます(「5 メモリ」の"ヒープの概要"を参照して下さい)。レコードはメモリカード上のどこにでも保存できるので、データベースは物理RAM上の不連続な複数の領域に分散させることができます。

 

ローカルIDを使ったデータアクセス

データベースは自身に含まれる全レコードのリストを、データベースヘッダに各レコードのレコードIDを保存することで保持しています。ローカルIDが使われているため、メモリカードをPalmハンドヘルドのどのメモリスロットにでも挿すことができます。アプリケーションはデータベース内のレコードをインデックスによって検索します。アプリケーションがあるレコードをリクエストすると、データマネージャはデータベースヘッダからインデックスによってレコードのローカルIDを取得し、データベースヘッダのカードナンバーを使用してそれをハンドルに変換して返します。

 

データベースヘッダの構造

データベースヘッダは、いくつかの基本的なデータベース情報とデータベース内のレコードのリストで構成されています。ヘッダ内の各レコードのエントリは、レコードのローカルID、属性を示す8ビット値、および3バイトのレコードのユニークIDからなっています。

このセクションではデータベースヘッダについて説明します。以下のトピックがあります。

IMPORTANT

データベースヘッダの構造は将来変更される可能性があります。データベースの操作にはAPIを使用して下さい。

 

データベースヘッダのフィールド

データベースヘッダには以下のフィールドがあります。

図 6.1 レコード属性

 

 

データベースヘッダ内のレコードエントリの構造

それぞれのレコードエントリはレコードのローカル ID、8 ビットからなる属性、およびレコードのユニーク ID(3 バイト)を保有しています。

Palmハンドヘルド上でレコードを"削除"すると、レコードのデータチャンクは開放され、レコードエントリのローカルIDには 0 がセットされます。また、attributesフィールドの delete ビットがセットされます。レコードをアーカイブした場合、delete ビットはセットされますがチャンクは開放されず、ローカル IDも保存されます。これにより、デスクトップと次に同期した際、デスクトップは(まだレコードエントリがPalmハンドヘルド上に残っているために)どのレコードが削除されたのかを素早く知ることができます。レコードをアーカイブした場合は、デスクトップはPalmハンドヘルドからレコードエントリとデータが完全に削除される前にレコードデータをPCに保存します。レコードの削除の場合、PCはPalmハンドヘルドからレコードエントリが完全に削除される前に対応するレコードを削除しなければなりません。

 

データマネージャの使用

データマネージャの使い方は、データがひと続きの連続するチャンクに保存されずに複数のレコードに分割されることを除けば、伝統的なファイルマネージャと同じです。データベースの作成および削除には、DmCreateDatabase と DmDeleteDatabase をコールします。

それぞれのメモリカードはディスクドライブのようなもので、複数のデータベースを格納することができます。読み取りまたは書込みのためにデータベースをオープンするには、まずデータベースIDを取得しなければなりません。これは単純にデータベースヘッダのローカルIDです。DmFindDatabase をコールすることでメモリカード上のデータベースを名前で検索し、データベースヘッダのローカルIDを返します。別の方法として、DmGetDatabase をコールすると、指定されたカード上のインデックスを持つデータベースの ID を取得できます。

データベースIDを取得したら、データベースを読み取り専用または読み書き両用でオープンすることができます。データベースをオープンすると、システムはデータベースヘッダをロックし、データベースアクセス構造体の参照を返します。これはオープンしているデータベースの情報を管理し、パフォーマンスを最適化するために情報をキャッシュするものです。データベースアクセス構造体はダイナミックヒープ上にアロケートされる比較的小さな構造体(100 バイト未満)で、データベースをクローズした時点で破棄されます。

データベースの名前、サイズ、作成日や更新日、属性、クリエータといった情報を問合せ、あるいは設定するには、DmDatabaseInfo、DmSetDatabaseInfo、および DmDatabaseSize をコールします。

データベースを参照・更新するには、DmGetRecord、DmQueryRecord、および DmReleaseRecord をコールします。

内容を増減させるためにレコードをリサイズするには、DmResizeRecord をコールします。この関数は現在のヒープに十分な空き領域がなければ、自動的に同一カード内の別のヒープにレコードをアロケートしなおします。データマネージャがリサイズのためにレコードを別のヒープに移動させる場合、レコードのハンドルが変わることに注意して下さい。DmResizeRecord はレコードの新しいハンドルを返します。

データベースに新しいレコードを追加するには、DmNewRecord をコールします。この関数は新しいレコードをどのインデックス位置にでも追加できますし、末尾に追加することもできます。また、インデックス位置にある既存のレコードを置き換えることもできます。この関数は新しいレコードのハンドルを返します。

レコードを削除する関数は3種類あります。DmRemoveRecord と DmDeleteRecord、および DmArchiveRecord です。

DmDeleteRecord と DmArchiveRecord は、ともにデスクトップ PC との情報の同期に有用です。削除またはアーカイブされたレコードのユニーク ID はデータベースヘッダにまだ保存されているため、デスクトップ PC は Palm OS データベースからレコードが完全に削除される前に、自身が保有するデータベースのコピーに対して必要な処理を行なうことができます。

データベースヘッダに保存されているレコードの属性、ユニークID、およびローカルIDといった情報を取得あるいは指定するには、DmRecordInfo と DmSetRecordInfo をコールします。通常これらのルーチンは、attribute フィールドの下位 4 ビットに保存されているレコードのカテゴリを取得または設定するために使用します(リスト 6.1 を参照)。

Listing 6.1 Determining the category for a record

UInt16 category;
DmRecordInfo (MyDB, CurrentRecord, &attr, NULL, NULL);
category = attr & dmRecAttrCategoryMask;
//category now contains the index of the category to which
// CurrentRecord belongs.

 

レコードをあるインデックスから他の位置へ、あるいはあるデータベースから他のデータベースへ移動するには、DmMoveRecord、DmAttachRecord、および DmDetachRecord をコールします。DmDetachRecord はデータベースヘッダからレコードエントリを削除し、レコードハンドルを返します。新しいレコードのハンドルを与えると、DmAttachRecord は新しいレコードをデータベースに追加または挿入するか、あるいは既存のレコードを新しいレコードで置き換えます。DmMoveRecord は同じデータベース内であるインデックスから別のインデックスにレコードを移動するための最適な方法です。

NOTE

Palm OS Cobalt では、PIM アプリケーションのデータベースは"スキーマ"データベースです。互換性のために、Palm OS Cobalt で PIM アプリケーションデータベースのいずれかにアクセスする場合、多くのデータマネージャコールは PACE にインターセプトされ、PIM アプリケーションのデータベースがクラシックな Palm データベースと同じに見えるようにします。この問題と Palm OS Cobalt が採用している解決法の詳細については、「Palm OS Programmer’s API Reference」の"Accessing the PIM Application Databases"を参照して下さい。

 

データベースの自動バックアップおよびレストア

様々なバージョンの Palm OS で、RAM ストレージヒープの内容をなんらかの不揮発性 NAND フラッシュにバックアップするようにライセンシーによって設定することができます。RAM ストレージヒープがなんらかの理由で汚損したり消失した場合に、ストレージヒープを保存した時の状態にレストアすることができます。これにより、既に HotSync によって提供されているものを越えるレベルの信頼性が提供されます。バックアップバッテリを持たないデバイスは、このバックアップとレストアの機能により、電源の on/off 間にデータを失うことを防止できます。

セキュリティのために、バックアップはデータマネージャだけがアクセスできるプライベートな内部 VFS ボリュームに対して行なわれます。このボリュームはバックアップとレストアのためだけに使用されます。

バックアップは限られたイベントによって起動されます。

デバイスのリセット時に RAM の内容が失われた形跡があると、バックアップボリュームの内容が RAM にレストアされます。バックアップをレストアする前に、整合性チェックがバックアップに対して行なわれ、不整合を回復する試みが行なわれます。これら全てを通じてのみバックアップはレストアされます。開発者はプログラム的にデータベースのレストアを起動することはできません。

デバイスがこの自動バックアップ機能を備えているかどうかを調べるには、sysFtrNumDmAutoBackup フィーチャが存在するかどうかをチェックします。

 

データマネージャのヒント

データベースを正しく処理できていれば、アプリケーションは高速に動作し、問題なく同期できるはずです。以下の忠告に従うようにして下さい。

 

 

 

↑6 章トップへ 2 節に進む →

 

 


Copyright(C) 2005-2017 project-enigma.
Generated by CL-PREFAB.