0

sdl_rwops を使用するとアクセス違反が発生する大きなプログラムがあります。そこで、sdl_rwops をテストするためだけに小さなプログラムを作成することにしましたが、同じアクセス違反が発生しています。fopen_s() の部分が原因であることがわかりましたが、その理由はわかりませんでした。たぶん、皆さんは私が行方不明になっているものを見つけることができます。コードは次のとおりです。

#include "SDL.h"
#include < stdio.h >

int main(int argc, char *argv[]) 
{
  FILE *file;
  SDL_Surface *screen;
  SDL_Surface *one;
  SDL_Rect rect;
  errno_t err;

/* This is the RWops structure we'll be using */

  SDL_RWops *rw;
  SDL_Init(SDL_INIT_VIDEO);
  atexit(SDL_Quit);
  screen = SDL_SetVideoMode(640, 480, 16, SDL_DOUBLEBUF);

/* Here we get a file pointer to a bitmap */

  if ( (err = fopen_s(&file,"penguin.bmp", "r")) != 0)
  {
     printf("Couldn't load penguin.bmp\n");
     exit(1);
  }

/* This is where we actually create our RWops structure.  Here we're
 instructing SDL to get it from the file pointer we just opened */

rw = SDL_RWFromFP(file, 0);

/* SDL_LoadBMP_RW is the RWops version of the old standby,
 SDL_LoadBMP.  This will get the image from the RWops you passed
 in; in this case the file you've opened */

one = SDL_LoadBMP_RW(rw, 0); // This line calls fopen.c and causes the crash

/* Clean up after ourselves */
SDL_FreeRW(rw);
fclose(file);

/* Haphazard way of getting stuff to the screen */
rect.x = rect.y = 20;
rect.w = one -> w;
rect.y = one -> h;
SDL_BlitSurface(one, NULL, screen, &rect);

SDL_Flip(screen);

SDL_Delay(3000);
}

そして、プログラムのクラッシュを引き起こす fopen.c の部分は次のとおりです。

errno_t __cdecl _tfopen_s (
FILE ** pfile,
const _TSCHAR *file,
const _TSCHAR *mode)
{

_VALIDATE_RETURN_ERRCODE((pfile != NULL), EINVAL);

*pfile = _tfsopen(file, mode, _SH_SECURE); // This line causes the access violation

if(*pfile != NULL)
   return 0;

return errno;
}

この線

one = SDL_LoadBMP_RW(rw, 0);

fopen.c とその行にジャンプします

*pfile = _tfsopen(file, mode, _SH_SECURE);

そのファイルでクラッシュします。

私は Visual Studio 2012 を使用しており、画像は実行可能ファイルと同じフォルダーにあります。SDL.dll と SDL_image.dll もそこにあります。Google で同じ問題の投稿を見つけたところ、その人は、(penguin.bmp" だけでなく) パス全体を入力するとクラッシュしないと言っていました。 SDL の初期化に問題がある可能性がありますが、Google で見つけたものはすべて実行しましたが、何も機能しませんでした.マルチスレッド DLL (/Md)、マルチスレッド デバッグ DLL (/MDd) で実行してみました。64 ビットで実行してみました。 、サブシステムをWindowsとコンソールに変更するのに苦労しました...すべてが同じクラッシュを引き起こしました。

4

1 に答える 1

3

SDL_RWFromFP のドキュメントを読むと

説明

SDL_RWFromFP は、stdio で開かれたファイル ポインタから新しい SDL_RWops 構造体を作成します。autoclose がゼロ以外の場合、RWops 構造が閉じられると、ファイルは自動的に閉じられます。

注: これは、Win32 では使用できません。そのプラットフォームのアプリケーションで開かれたファイルは、動的にリンクされたライブラリでは使用できないためです。

注: この関数は SDL-1.2-svn4446 にはありません

したがって、RWOps を使用する場合は SDL_RWFromFile を使用する必要があります。

また、SDL 2 には SDL 1.* に比べて多くの改善点があり、SDL 2 に切り替えることを強くお勧めします。

于 2013-08-23T18:57:28.163 に答える