1

I'm trying to understand Simple DirectMedia Layer (SDL) for my own projects and I've encountered an issue I'm not able to solve. The issue arises with Windows 7, but not with Windows 10 (both 64bit machines). The project compiles fine on both OS without warnings, but during runtime (at the beginning) on Windows 7 a popup window appear stating that it's not possible to find the entry point for ScriptFreeCache procedure in GDI32.dll.

The original message in Italian states: "Impossibile trovare il punto di ingresso ScriptFreeCache della procedura nella libreria di collegamento dinamico GDI32.dll"

The issue is related to sdl_tff. Commenting those lines, the program runs fine.

The gdi32.dll is present in both system32 and in sysWOW64 folders (windows 7). On Windows 10 there is also a dll named gdifull.dll. I've tried to put all the libraries from the two machine system folders, and others from internet (different versions and both 32 and 64bit), in the execution folder. No change, same error during runtime.

The setup on the two machine is (should be) the same.

Mingw 64 bit
SDL2 64 bit
SDL_Image 64 bit
SDL_TTF 64 bit
Developer SDL libraries correclty installed

Here the minimal source code that reproduces the error

#include <exception>
#include <string>
#include <iostream>
#include <SDL2\SDL.h>
#include <SDL2\SDL_image.h>
#include <SDL2\SDL_ttf.h>

int main(int argc, char* argv[]){
    /* Create a window */
    SDL_Window* window=nullptr;

    /* Grab the window surface */
    SDL_Surface* screen;

    /* Initialize the video subsystem */
    if(SDL_Init(SDL_INIT_VIDEO) < 0)
    {
        std::cout << "SDL could not be initialized: " << SDL_GetError();
    }
    else
    {
        std::cout << "SDL video system ready" << std::endl;
    }

    /* Allocate Window pointer */
    window = SDL_CreateWindow("SDL2 Window", 200, 200, 640, 480, SDL_WINDOW_SHOWN);
    screen = SDL_GetWindowSurface(window);

    SDL_Surface* image;
    image = SDL_LoadBMP("Test.bmp");
    /* Check loaded image */
    if (!image)
    {
        std::cout << "Failed to load image: Test.bmp" << std::endl;
    }

    SDL_BlitSurface(image,NULL,screen,NULL);
    SDL_FreeSurface(image);
    SDL_UpdateWindowSurface(window);

    /* Delay for splash screen. */
    SDL_Delay(1000);

    /* Printing on screen some information */
    TTF_Font *font = NULL;
    SDL_Color color={0,255,0};

    if(TTF_Init()==-1) {
        printf("TTF_Init: %s\n", TTF_GetError());
        exit(2);
    }

    font = TTF_OpenFont(".\\calibri.ttf", 14);
    if(font == NULL)
       std::cout << "Failed to load font" << std::endl;

    // Render some text
    SDL_Surface *text_surface;
    if(!(text_surface=TTF_RenderText_Solid(font,"Hello World!\n",color)))
    {
        std::cout << "Error writing text on surface" << std::endl;
    }
    else
    {
        SDL_BlitSurface(text_surface,NULL,screen,NULL);
        SDL_FreeSurface(text_surface);
    }

    SDL_UpdateWindowSurface(window);

    SDL_FreeSurface(screen);

    /* Delay for screen. */
    SDL_Delay(1000);

    // Destroy the window.
    SDL_DestroyWindow(window);

    SDL_Quit();
    return 0;
}

Here the Codeblocks project

<?xml version="1.0" encoding="UTF-8" standalone="yes" ?>
<CodeBlocks_project_file>
    <FileVersion major="1" minor="6" />
    <Project>
        <Option title="SDL_TTF_gdi_issue" />
        <Option pch_mode="2" />
        <Option compiler="gnu_gcc_compiler_x64_64bit" />
        <Build>
            <Target title="Debug">
                <Option output="../Test/GDI_Issue" prefix_auto="1" extension_auto="1" />
                <Option working_dir="../Test/" />
                <Option object_output="obj/Debug/" />
                <Option type="1" />
                <Option compiler="gnu_gcc_compiler_x64_64bit" />
                <Compiler>
                    <Add option="-g" />
                </Compiler>
            </Target>
            <Target title="Release">
                <Option output="../Test/GDI_Issue" prefix_auto="1" extension_auto="1" />
                <Option object_output="obj/Release/" />
                <Option type="0" />
                <Option compiler="gnu_gcc_compiler_x64_64bit" />
                <Compiler>
                    <Add option="-O2" />
                </Compiler>
                <Linker>
                    <Add option="-s" />
                </Linker>
            </Target>
        </Build>
        <Compiler>
            <Add option="-Wall" />
            <Add directory="C:/x86_64-w64-mingw32/include" />
        </Compiler>
        <Linker>
            <Add library="mingw32" />
            <Add library="SDL2main" />
            <Add library="SDL2.dll" />
            <Add library="user32" />
            <Add library="gdi32" />
            <Add library="winmm" />
            <Add library="dxguid" />
            <Add directory="C:/x86_64-w64-mingw32/lib" />
        </Linker>
        <ExtraCommands>
            <Add after="XCOPY $(#sdl2)\bin\*.dll $(TARGET_OUTPUT_DIR) /D /Y" />
        </ExtraCommands>
        <Unit filename="main.cpp" />
        <Extensions>
            <code_completion />
            <envvars />
            <debugger />
            <lib_finder disable_auto="1" />
        </Extensions>
    </Project>
</CodeBlocks_project_file>

What am I doing wrong?

jonrsharpe
  • 115,751
  • 26
  • 228
  • 437
Nem
  • 41
  • 3
  • 1
    It's actually stated in the docu of [ScriptFreeCache](https://learn.microsoft.com/en-us/windows/win32/api/usp10/nf-usp10-scriptfreecache) as **Important**: `Starting with Windows 8: To maintain the ability to run on Windows 7, a module that uses Uniscribe must specify Usp10.lib before gdi32.lib in its library list.` – ssbssa May 03 '22 at 10:26
  • @ssbssa: Thank you, seems that you solved my problem. I've checked it with the minimal code on Windows 7 and it works. Today I can't check it with Windows 10 to see if it still works, I'll do it tomorrow. – Nem May 03 '22 at 10:35

0 Answers0