DXライブラリで非同期読み込みが終わらないことがあります。

フォーラム(掲示板)ルール
フォーラム(掲示板)ルールはこちら  ※コードを貼り付ける場合は [code][/code] で囲って下さい。詳しくはこちら
derok
記事: 51
登録日時: 12年前

DXライブラリで非同期読み込みが終わらないことがあります。

#1

投稿記事 by derok » 9年前

コード:

#include "DxLib.h"

int WINAPI WinMain(HINSTANCE, HINSTANCE, LPSTR, int){
	ChangeWindowMode(TRUE), DxLib_Init(), SetDrawScreen(DX_SCREEN_BACK);
	char* FileName= "Data\\testEffect.txt";
	int id;
	char*Str;
	LONGLONG size;
	SetUseASyncLoadFlag(FALSE);
	id = FileRead_open(FileName);
	if (id == -1) {
		FileRead_close(id);
		DxLib_End();
		return 0;
	}
	size = FileRead_size(FileName);
	printfDx("(%d,%d)\n",id,size);
	Str = (char*)malloc(size + 1);
	int count=0;
	SetUseASyncLoadFlag(TRUE);
	bool is_flag=false;
	while (ProcessMessage() == 0 && ClearDrawScreen() == 0){
		if(is_flag==false){
			FileRead_read(Str, size, id);
			if (CheckHandleASyncLoad(id) == -1)printfDx("error");
			if (CheckHandleASyncLoad(id) == FALSE) {
				Str[size] = '\0';
				printfDx(Str);
				is_flag=true;
				FileRead_close(id);
				free(Str);
				Str=nullptr;
			}
			count++;
		}
		DrawFormatString(100, 100, GetColor(255, 255, 255), "%d", count);
        ScreenFlip();
	}
	if (Str != nullptr) {
		FileRead_close(id);
		free(Str);
	}
	DxLib_End();
	return 0;
}

DXライブラリv3.15c、windows10、visual studio 2015 Communityです。
以上のコードで非同期読み込みを行うと終わらないことがあります。
厄介なことに成功することもあるので、ファイルが存在しないというとはないと思います。
Debug、Releaseともに失敗しますが、Releaseだと成功したことがありません。

コード:

#include "DxLib.h"
#include <malloc.h>

int WINAPI WinMain(HINSTANCE, HINSTANCE, LPSTR, int){
	ChangeWindowMode(TRUE), DxLib_Init(), SetDrawScreen(DX_SCREEN_BACK);
	char* FileName= "Data\\testEffect.txt";
	int id;
	char*Str;
	LONGLONG size;
	int  heapstatus;
	SetUseASyncLoadFlag(FALSE);
	id = FileRead_open(FileName);
	if (id == -1) {
		FileRead_close(id);
		DxLib_End();
		return 0;
	}
	size = FileRead_size(FileName);
	printfDx("(%d,%d)\n",id,size);
	Str = (char*)malloc(size + 1);
	int count=0;
	SetUseASyncLoadFlag(TRUE);
	bool is_flag=false;
	while (ProcessMessage() == 0 && ClearDrawScreen() == 0){
		clsDx();
		if(is_flag==false){
			heapstatus = _heapchk();
			switch (heapstatus) {
			case _HEAPOK:
				printfDx(" OK - heap is fine\n");
				break;
			case _HEAPEMPTY:
				printfDx(" OK - heap is empty\n");
				break;
			case _HEAPBADBEGIN:
				printfDx("ERROR - bad start of heap\n");
				break;
			case _HEAPBADNODE:
				printfDx("ERROR - bad node in heap\n");
				break;
			}
			FileRead_read(Str, size, id);
			if (CheckHandleASyncLoad(id) == -1)printfDx("error");
			if (CheckHandleASyncLoad(id) == FALSE) {
				Str[size] = '\0';
				printfDx(Str);
				is_flag=true;
				FileRead_close(id);
				free(Str);
				Str=nullptr;
			}
			count++;
		}
		DrawFormatString(100, 100, GetColor(255, 255, 255), "%d", count);
        ScreenFlip();
	}
	if (Str != nullptr) {
		FileRead_close(id);
		free(Str);
	}
	DxLib_End();
	return 0;
}

のように_heapchk関数を使ってみましてもOKとしかでません。
一体何が原因なんでしょうか?
管理者として実行、互換モード(window 7)で実行も試してみましたが駄目でした。

djann
記事: 27
登録日時: 12年前

Re: DXライブラリで非同期読み込みが終わらないことがあります。

#2

投稿記事 by djann » 9年前

多分非同期モードの挙動は

1. FileRead_xxxx()等で指令を与える
2. 与えた指令が終わっていればCheckHandleASyncLoad( handle )がFALSEを戻し、他の指令を与えられるようになる。

といった形かと思われます。

あなたの書いたコードでは毎フレーム指令を与え(24行目のFileRead_read())、その直後にチェックを行っていますので、ファイル読み込み用スレッドがよほど上手いタイミングで入ってこない限り「終わっていない」という認識になってしまうものだと思われます(Releaseビルドの方がその間の命令数が少い、速そうなので尚更運よく終了となりづらいか。

試しにFileRead_read()に渡している格納先のバッファをDrawString()ででも表示してみてください。多分読み終わっている or 読み込まれていく流れが見えるので。

コード:

// 同期読み込み.
char buf[ 8 ];

// ...ひらいたりなんたり.

FileRead_read( buf, 8, handle );
// この瞬間から使える!

// 非同期読み込み.
char buf[ 8 ];

// 開いたりなんたりかんたり

FileRead_read( buf, 8, handle );
// まだ使えない!

// CheckHandleASyncLoad( handle ) がFALSEを戻した!その時から完全に使えるようになる!

derok
記事: 51
登録日時: 12年前

Re: DXライブラリで非同期読み込みが終わらないことがあります。

#3

投稿記事 by derok » 9年前

>> djannさん
ありがとうございます。お陰でちゃんと動くようになりました。

コード:

#include "DxLib.h"


int WINAPI WinMain(HINSTANCE, HINSTANCE, LPSTR, int){
	ChangeWindowMode(TRUE), DxLib_Init(), SetDrawScreen(DX_SCREEN_BACK);
	char* FileName= "Data\\testEffect.txt";
	int id;
	char*Str;
	LONGLONG size;
	int  heapstatus;
	SetUseASyncLoadFlag(FALSE);
	id = FileRead_open(FileName);
	if (id == -1) {
		FileRead_close(id);
		DxLib_End();
		return 0;
	}
	size = FileRead_size(FileName);
	printfDx("(%d,%d)\n",id,size);
	Str = (char*)malloc(size + 1);
	FileRead_read(Str, size, id);
	int count=0;
	SetUseASyncLoadFlag(TRUE);
	bool is_flag=false;
	while (ProcessMessage() == 0 && ClearDrawScreen() == 0){
		if(is_flag==false){
			if (CheckHandleASyncLoad(id) == -1)printfDx("error");
			if (CheckHandleASyncLoad(id) == FALSE) {
				Str[size] = '\0';
				printfDx(Str);
				is_flag=true;
				FileRead_close(id);
				free(Str);
				Str=nullptr;
			}
			count++;
		}
		DrawFormatString(100, 100, GetColor(255, 255, 255), "%d", count);
        ScreenFlip();
	}
	if (Str != nullptr) {
		FileRead_close(id);
		free(Str);
	}
	DxLib_End();
	return 0;
}

閉鎖

“C言語何でも質問掲示板” へ戻る