diff --git a/configure b/configure index 993c9e93b77..d7fe6f9f376 100755 --- a/configure +++ b/configure @@ -3091,12 +3091,6 @@ XFILES="" OPENGLFILES="" OPENGL32_DLL="" - -DGA_SRCS="" - -DGA2_SRCS="" - -MESA_SRCS="" if test "$have_x" = "yes" then XLIB="-lXext -lX11" @@ -3107,17 +3101,17 @@ then do ac_safe=`echo "$ac_hdr" | sed 'y%./+-%__p_%'` echo $ac_n "checking for $ac_hdr""... $ac_c" 1>&6 -echo "configure:3111: checking for $ac_hdr" >&5 +echo "configure:3105: checking for $ac_hdr" >&5 if eval "test \"`echo '$''{'ac_cv_header_$ac_safe'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:3121: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:3115: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* @@ -3138,7 +3132,7 @@ if eval "test \"`echo '$ac_cv_header_'$ac_safe`\" = yes"; then #define $ac_tr_hdr 1 EOF echo $ac_n "checking for XpmCreatePixmapFromData in -lXpm""... $ac_c" 1>&6 -echo "configure:3142: checking for XpmCreatePixmapFromData in -lXpm" >&5 +echo "configure:3136: checking for XpmCreatePixmapFromData in -lXpm" >&5 ac_lib_var=`echo Xpm'_'XpmCreatePixmapFromData | sed 'y%./+-%__p_%'` if eval "test \"`echo '$''{'ac_cv_lib_$ac_lib_var'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 @@ -3147,7 +3141,7 @@ else LIBS="-lXpm $X_LIBS -lXext -lX11 $X_EXTRA_LIBS $LIBS" cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:3156: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -3203,17 +3197,17 @@ done do ac_safe=`echo "$ac_hdr" | sed 'y%./+-%__p_%'` echo $ac_n "checking for $ac_hdr""... $ac_c" 1>&6 -echo "configure:3207: checking for $ac_hdr" >&5 +echo "configure:3201: checking for $ac_hdr" >&5 if eval "test \"`echo '$''{'ac_cv_header_$ac_safe'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:3217: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:3211: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* @@ -3238,17 +3232,17 @@ EOF do ac_safe=`echo "$ac_hdr" | sed 'y%./+-%__p_%'` echo $ac_n "checking for $ac_hdr""... $ac_c" 1>&6 -echo "configure:3242: checking for $ac_hdr" >&5 +echo "configure:3236: checking for $ac_hdr" >&5 if eval "test \"`echo '$''{'ac_cv_header_$ac_safe'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:3252: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:3246: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* @@ -3269,7 +3263,7 @@ if eval "test \"`echo '$ac_cv_header_'$ac_safe`\" = yes"; then #define $ac_tr_hdr 1 EOF echo $ac_n "checking for XkbQueryExtension in -lX11""... $ac_c" 1>&6 -echo "configure:3273: checking for XkbQueryExtension in -lX11" >&5 +echo "configure:3267: checking for XkbQueryExtension in -lX11" >&5 ac_lib_var=`echo X11'_'XkbQueryExtension | sed 'y%./+-%__p_%'` if eval "test \"`echo '$''{'ac_cv_lib_$ac_lib_var'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 @@ -3277,7 +3271,7 @@ else ac_save_LIBS="$LIBS" LIBS="-lX11 $X_LIBS -lXext -lX11 $X_EXTRA_LIBS $LIBS" cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:3286: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -3324,17 +3318,17 @@ done do ac_safe=`echo "$ac_hdr" | sed 'y%./+-%__p_%'` echo $ac_n "checking for $ac_hdr""... $ac_c" 1>&6 -echo "configure:3328: checking for $ac_hdr" >&5 +echo "configure:3322: checking for $ac_hdr" >&5 if eval "test \"`echo '$''{'ac_cv_header_$ac_safe'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:3338: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:3332: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* @@ -3355,7 +3349,7 @@ if eval "test \"`echo '$ac_cv_header_'$ac_safe`\" = yes"; then #define $ac_tr_hdr 1 EOF echo $ac_n "checking for XShmQueryExtension in -lXext""... $ac_c" 1>&6 -echo "configure:3359: checking for XShmQueryExtension in -lXext" >&5 +echo "configure:3353: checking for XShmQueryExtension in -lXext" >&5 ac_lib_var=`echo Xext'_'XShmQueryExtension | sed 'y%./+-%__p_%'` if eval "test \"`echo '$''{'ac_cv_lib_$ac_lib_var'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 @@ -3363,7 +3357,7 @@ else ac_save_LIBS="$LIBS" LIBS="-lXext $X_LIBS -lXext -lX11 $X_EXTRA_LIBS $LIBS" cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:3372: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -3410,17 +3404,17 @@ done do ac_safe=`echo "$ac_hdr" | sed 'y%./+-%__p_%'` echo $ac_n "checking for $ac_hdr""... $ac_c" 1>&6 -echo "configure:3414: checking for $ac_hdr" >&5 +echo "configure:3408: checking for $ac_hdr" >&5 if eval "test \"`echo '$''{'ac_cv_header_$ac_safe'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:3424: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:3418: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* @@ -3441,7 +3435,7 @@ if eval "test \"`echo '$ac_cv_header_'$ac_safe`\" = yes"; then #define $ac_tr_hdr 1 EOF echo $ac_n "checking for XShapeQueryExtension in -lXext""... $ac_c" 1>&6 -echo "configure:3445: checking for XShapeQueryExtension in -lXext" >&5 +echo "configure:3439: checking for XShapeQueryExtension in -lXext" >&5 ac_lib_var=`echo Xext'_'XShapeQueryExtension | sed 'y%./+-%__p_%'` if eval "test \"`echo '$''{'ac_cv_lib_$ac_lib_var'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 @@ -3449,7 +3443,7 @@ else ac_save_LIBS="$LIBS" LIBS="-lXext $X_LIBS -lXext -lX11 $X_EXTRA_LIBS $LIBS" cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:3458: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -3496,17 +3490,17 @@ done do ac_safe=`echo "$ac_hdr" | sed 'y%./+-%__p_%'` echo $ac_n "checking for $ac_hdr""... $ac_c" 1>&6 -echo "configure:3500: checking for $ac_hdr" >&5 +echo "configure:3494: checking for $ac_hdr" >&5 if eval "test \"`echo '$''{'ac_cv_header_$ac_safe'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:3510: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:3504: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* @@ -3527,7 +3521,7 @@ if eval "test \"`echo '$ac_cv_header_'$ac_safe`\" = yes"; then #define $ac_tr_hdr 1 EOF echo $ac_n "checking for XDGAQueryExtension in -lXxf86dga""... $ac_c" 1>&6 -echo "configure:3531: checking for XDGAQueryExtension in -lXxf86dga" >&5 +echo "configure:3525: checking for XDGAQueryExtension in -lXxf86dga" >&5 ac_lib_var=`echo Xxf86dga'_'XDGAQueryExtension | sed 'y%./+-%__p_%'` if eval "test \"`echo '$''{'ac_cv_lib_$ac_lib_var'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 @@ -3536,7 +3530,7 @@ else LIBS="-lXxf86dga $X_LIBS -lXext -lX11 $X_EXTRA_LIBS $LIBS" cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:3545: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -3571,13 +3565,11 @@ EOF EOF X_PRE_LIBS="$X_PRE_LIBS -lXxf86dga" - DGA_SRCS='$(DGA_SRCS)' - DGA2_SRCS='$(DGA2_SRCS)' else echo "$ac_t""no" 1>&6 echo $ac_n "checking for XF86DGAQueryExtension in -lXxf86dga""... $ac_c" 1>&6 -echo "configure:3581: checking for XF86DGAQueryExtension in -lXxf86dga" >&5 +echo "configure:3573: checking for XF86DGAQueryExtension in -lXxf86dga" >&5 ac_lib_var=`echo Xxf86dga'_'XF86DGAQueryExtension | sed 'y%./+-%__p_%'` if eval "test \"`echo '$''{'ac_cv_lib_$ac_lib_var'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 @@ -3586,7 +3578,7 @@ else LIBS="-lXxf86dga $X_LIBS -lXext -lX11 $X_EXTRA_LIBS $LIBS" cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:3593: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -3617,7 +3609,6 @@ if eval "test \"`echo '$ac_cv_lib_'$ac_lib_var`\" = yes"; then EOF X_PRE_LIBS="$X_PRE_LIBS -lXxf86dga" - DGA_SRCS='$(DGA_SRCS)' else echo "$ac_t""no" 1>&6 @@ -3639,17 +3630,17 @@ done do ac_safe=`echo "$ac_hdr" | sed 'y%./+-%__p_%'` echo $ac_n "checking for $ac_hdr""... $ac_c" 1>&6 -echo "configure:3643: checking for $ac_hdr" >&5 +echo "configure:3634: checking for $ac_hdr" >&5 if eval "test \"`echo '$''{'ac_cv_header_$ac_safe'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:3653: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:3644: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* @@ -3670,7 +3661,7 @@ if eval "test \"`echo '$ac_cv_header_'$ac_safe`\" = yes"; then #define $ac_tr_hdr 1 EOF echo $ac_n "checking for XF86VidModeQueryExtension in -lXxf86vm""... $ac_c" 1>&6 -echo "configure:3674: checking for XF86VidModeQueryExtension in -lXxf86vm" >&5 +echo "configure:3665: checking for XF86VidModeQueryExtension in -lXxf86vm" >&5 ac_lib_var=`echo Xxf86vm'_'XF86VidModeQueryExtension | sed 'y%./+-%__p_%'` if eval "test \"`echo '$''{'ac_cv_lib_$ac_lib_var'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 @@ -3679,7 +3670,7 @@ else LIBS="-lXxf86vm $X_LIBS -lXext -lX11 $X_EXTRA_LIBS $LIBS" cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:3685: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -3728,17 +3719,17 @@ done do ac_safe=`echo "$ac_hdr" | sed 'y%./+-%__p_%'` echo $ac_n "checking for $ac_hdr""... $ac_c" 1>&6 -echo "configure:3732: checking for $ac_hdr" >&5 +echo "configure:3723: checking for $ac_hdr" >&5 if eval "test \"`echo '$''{'ac_cv_header_$ac_safe'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:3742: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:3733: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* @@ -3759,7 +3750,7 @@ if eval "test \"`echo '$ac_cv_header_'$ac_safe`\" = yes"; then #define $ac_tr_hdr 1 EOF echo $ac_n "checking for XvShmCreateImage in -lXv""... $ac_c" 1>&6 -echo "configure:3763: checking for XvShmCreateImage in -lXv" >&5 +echo "configure:3754: checking for XvShmCreateImage in -lXv" >&5 ac_lib_var=`echo Xv'_'XvShmCreateImage | sed 'y%./+-%__p_%'` if eval "test \"`echo '$''{'ac_cv_lib_$ac_lib_var'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 @@ -3768,7 +3759,7 @@ else LIBS="-lXv $X_LIBS -lXext -lX11 $X_EXTRA_LIBS $LIBS" cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:3774: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -3826,17 +3817,17 @@ done do ac_safe=`echo "$ac_hdr" | sed 'y%./+-%__p_%'` echo $ac_n "checking for $ac_hdr""... $ac_c" 1>&6 -echo "configure:3830: checking for $ac_hdr" >&5 +echo "configure:3821: checking for $ac_hdr" >&5 if eval "test \"`echo '$''{'ac_cv_header_$ac_safe'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:3840: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:3831: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* @@ -3865,19 +3856,19 @@ done if test "$ac_cv_header_GL_gl_h" = "yes" -a "$ac_cv_header_GL_glx_h" = "yes" then echo $ac_n "checking "for up-to-date OpenGL version"""... $ac_c" 1>&6 -echo "configure:3869: checking "for up-to-date OpenGL version"" >&5 +echo "configure:3860: checking "for up-to-date OpenGL version"" >&5 if eval "test \"`echo '$''{'wine_cv_opengl_version_OK'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext < int main() { GLenum test = GL_UNSIGNED_SHORT_5_6_5; ; return 0; } EOF -if { (eval echo configure:3881: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then +if { (eval echo configure:3872: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then rm -rf conftest* wine_cv_opengl_version_OK="yes" else @@ -3894,21 +3885,21 @@ fi echo "$ac_t""$wine_cv_opengl_version_OK" 1>&6 echo $ac_n "checking "for thread-safe OpenGL version"""... $ac_c" 1>&6 -echo "configure:3898: checking "for thread-safe OpenGL version"" >&5 +echo "configure:3889: checking "for thread-safe OpenGL version"" >&5 if eval "test \"`echo '$''{'wine_cv_opengl_version_threadsafe'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else saved_libs=$LIBS LIBS="$X_LIBS -lGL" cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:3903: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* wine_cv_opengl_version_threadsafe="yes" else @@ -3927,7 +3918,7 @@ echo "$ac_t""$wine_cv_opengl_version_threadsafe" 1>&6 if test "$wine_cv_opengl_version_OK" = "yes" -a \( "$wine_cv_opengl_version_threadsafe" = "no" -o $OPENGL = "yes" \) then echo $ac_n "checking for glXCreateContext in -lGL""... $ac_c" 1>&6 -echo "configure:3931: checking for glXCreateContext in -lGL" >&5 +echo "configure:3922: checking for glXCreateContext in -lGL" >&5 ac_lib_var=`echo GL'_'glXCreateContext | sed 'y%./+-%__p_%'` if eval "test \"`echo '$''{'ac_cv_lib_$ac_lib_var'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 @@ -3935,7 +3926,7 @@ else ac_save_LIBS="$LIBS" LIBS="-lGL $X_LIBS -lXext -lX11 -lm $X_EXTRA_LIBS $LIBS" cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:3941: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -3962,7 +3953,6 @@ fi if eval "test \"`echo '$ac_cv_lib_'$ac_lib_var`\" = yes"; then echo "$ac_t""yes" 1>&6 X_PRE_LIBS="$X_PRE_LIBS -lGL" - MESA_SRCS='$(MESA_SRCS)' else echo "$ac_t""no" 1>&6 @@ -3979,7 +3969,7 @@ EOF echo $ac_n "checking for glXGetProcAddressARB in -lGL""... $ac_c" 1>&6 -echo "configure:3983: checking for glXGetProcAddressARB in -lGL" >&5 +echo "configure:3973: checking for glXGetProcAddressARB in -lGL" >&5 ac_lib_var=`echo GL'_'glXGetProcAddressARB | sed 'y%./+-%__p_%'` if eval "test \"`echo '$''{'ac_cv_lib_$ac_lib_var'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 @@ -3987,7 +3977,7 @@ else ac_save_LIBS="$LIBS" LIBS="-lGL $X_LIBS -lXext -lX11 -lm $X_EXTRA_LIBS $LIBS" cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:3992: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -4025,12 +4015,12 @@ fi if test $ac_cv_lib_GL_glXGetProcAddressARB = "yes" then echo $ac_n "checking "for OpenGL extension functions prototypes"""... $ac_c" 1>&6 -echo "configure:4029: checking "for OpenGL extension functions prototypes"" >&5 +echo "configure:4019: checking "for OpenGL extension functions prototypes"" >&5 if eval "test \"`echo '$''{'wine_cv_extension_prototypes'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext < #ifdef HAVE_GL_GLEXT_H @@ -4041,7 +4031,7 @@ int main() { PFNGLCOLORTABLEEXTPROC test_proc; ; return 0; } EOF -if { (eval echo configure:4045: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then +if { (eval echo configure:4035: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then rm -rf conftest* wine_cv_extension_prototypes="yes" else @@ -4066,6 +4056,138 @@ EOF OPENGL32_DLL=opengl32 fi + + for ac_hdr in GL/osmesa.h +do +ac_safe=`echo "$ac_hdr" | sed 'y%./+-%__p_%'` +echo $ac_n "checking for $ac_hdr""... $ac_c" 1>&6 +echo "configure:4065: checking for $ac_hdr" >&5 +if eval "test \"`echo '$''{'ac_cv_header_$ac_safe'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + cat > conftest.$ac_ext < +EOF +ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" +{ (eval echo configure:4075: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` +if test -z "$ac_err"; then + rm -rf conftest* + eval "ac_cv_header_$ac_safe=yes" +else + echo "$ac_err" >&5 + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -rf conftest* + eval "ac_cv_header_$ac_safe=no" +fi +rm -f conftest* +fi +if eval "test \"`echo '$ac_cv_header_'$ac_safe`\" = yes"; then + echo "$ac_t""yes" 1>&6 + ac_tr_hdr=HAVE_`echo $ac_hdr | sed 'y%abcdefghijklmnopqrstuvwxyz./-%ABCDEFGHIJKLMNOPQRSTUVWXYZ___%'` + cat >> confdefs.h <&6 +echo "configure:4096: checking for OSMesaCreateContext in -lGL" >&5 +ac_lib_var=`echo GL'_'OSMesaCreateContext | sed 'y%./+-%__p_%'` +if eval "test \"`echo '$''{'ac_cv_lib_$ac_lib_var'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + ac_save_LIBS="$LIBS" +LIBS="-lGL $X_LIBS -lXext -lX11 $X_EXTRA_LIBS + $LIBS" +cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then + rm -rf conftest* + eval "ac_cv_lib_$ac_lib_var=yes" +else + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -rf conftest* + eval "ac_cv_lib_$ac_lib_var=no" +fi +rm -f conftest* +LIBS="$ac_save_LIBS" + +fi +if eval "test \"`echo '$ac_cv_lib_'$ac_lib_var`\" = yes"; then + echo "$ac_t""yes" 1>&6 + cat >> confdefs.h <<\EOF +#define HAVE_OSMESA 1 +EOF + +else + echo "$ac_t""no" 1>&6 +echo $ac_n "checking for OSMesaCreateContext in -lOSMesa""... $ac_c" 1>&6 +echo "configure:4138: checking for OSMesaCreateContext in -lOSMesa" >&5 +ac_lib_var=`echo OSMesa'_'OSMesaCreateContext | sed 'y%./+-%__p_%'` +if eval "test \"`echo '$''{'ac_cv_lib_$ac_lib_var'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + ac_save_LIBS="$LIBS" +LIBS="-lOSMesa $LIBS" +cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then + rm -rf conftest* + eval "ac_cv_lib_$ac_lib_var=yes" +else + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -rf conftest* + eval "ac_cv_lib_$ac_lib_var=no" +fi +rm -f conftest* +LIBS="$ac_save_LIBS" + +fi +if eval "test \"`echo '$ac_cv_lib_'$ac_lib_var`\" = yes"; then + echo "$ac_t""yes" 1>&6 + cat >> confdefs.h <<\EOF +#define HAVE_OSMESA 1 +EOF + + X_PRE_LIBS="$X_PRE_LIBS -lOSMesa" + +else + echo "$ac_t""no" 1>&6 +fi + +fi + + +else + echo "$ac_t""no" 1>&6 +echo "configure: warning: OSMesa not found!!" 1>&2 + +fi +done + fi fi fi @@ -4086,17 +4208,17 @@ then do ac_safe=`echo "$ac_hdr" | sed 'y%./+-%__p_%'` echo $ac_n "checking for $ac_hdr""... $ac_c" 1>&6 -echo "configure:4090: checking for $ac_hdr" >&5 +echo "configure:4212: checking for $ac_hdr" >&5 if eval "test \"`echo '$''{'ac_cv_header_$ac_safe'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:4100: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:4222: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* @@ -4125,7 +4247,7 @@ done if test "$ac_cv_header_ncurses_h" = "yes" then echo $ac_n "checking for waddch in -lncurses""... $ac_c" 1>&6 -echo "configure:4129: checking for waddch in -lncurses" >&5 +echo "configure:4251: checking for waddch in -lncurses" >&5 ac_lib_var=`echo ncurses'_'waddch | sed 'y%./+-%__p_%'` if eval "test \"`echo '$''{'ac_cv_lib_$ac_lib_var'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 @@ -4133,7 +4255,7 @@ else ac_save_LIBS="$LIBS" LIBS="-lncurses $LIBS" cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:4270: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -4175,7 +4297,7 @@ fi if test "$ac_cv_lib_ncurses_waddch" = "yes" then echo $ac_n "checking for resizeterm in -lncurses""... $ac_c" 1>&6 -echo "configure:4179: checking for resizeterm in -lncurses" >&5 +echo "configure:4301: checking for resizeterm in -lncurses" >&5 ac_lib_var=`echo ncurses'_'resizeterm | sed 'y%./+-%__p_%'` if eval "test \"`echo '$''{'ac_cv_lib_$ac_lib_var'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 @@ -4183,7 +4305,7 @@ else ac_save_LIBS="$LIBS" LIBS="-lncurses $LIBS" cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:4320: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -4218,7 +4340,7 @@ else fi echo $ac_n "checking for getbkgd in -lncurses""... $ac_c" 1>&6 -echo "configure:4222: checking for getbkgd in -lncurses" >&5 +echo "configure:4344: checking for getbkgd in -lncurses" >&5 ac_lib_var=`echo ncurses'_'getbkgd | sed 'y%./+-%__p_%'` if eval "test \"`echo '$''{'ac_cv_lib_$ac_lib_var'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 @@ -4226,7 +4348,7 @@ else ac_save_LIBS="$LIBS" LIBS="-lncurses $LIBS" cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:4363: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -4265,17 +4387,17 @@ fi do ac_safe=`echo "$ac_hdr" | sed 'y%./+-%__p_%'` echo $ac_n "checking for $ac_hdr""... $ac_c" 1>&6 -echo "configure:4269: checking for $ac_hdr" >&5 +echo "configure:4391: checking for $ac_hdr" >&5 if eval "test \"`echo '$''{'ac_cv_header_$ac_safe'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:4279: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:4401: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* @@ -4304,7 +4426,7 @@ done if test "$ac_cv_header_curses_h" = "yes" then echo $ac_n "checking for waddch in -lcurses""... $ac_c" 1>&6 -echo "configure:4308: checking for waddch in -lcurses" >&5 +echo "configure:4430: checking for waddch in -lcurses" >&5 ac_lib_var=`echo curses'_'waddch | sed 'y%./+-%__p_%'` if eval "test \"`echo '$''{'ac_cv_lib_$ac_lib_var'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 @@ -4312,7 +4434,7 @@ else ac_save_LIBS="$LIBS" LIBS="-lcurses $LIBS" cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:4449: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -4353,7 +4475,7 @@ fi if test "$ac_cv_lib_curses_waddch" = "yes" then echo $ac_n "checking for resizeterm in -lcurses""... $ac_c" 1>&6 -echo "configure:4357: checking for resizeterm in -lcurses" >&5 +echo "configure:4479: checking for resizeterm in -lcurses" >&5 ac_lib_var=`echo curses'_'resizeterm | sed 'y%./+-%__p_%'` if eval "test \"`echo '$''{'ac_cv_lib_$ac_lib_var'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 @@ -4361,7 +4483,7 @@ else ac_save_LIBS="$LIBS" LIBS="-lcurses $LIBS" cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:4498: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -4396,7 +4518,7 @@ else fi echo $ac_n "checking for getbkgd in -lcurses""... $ac_c" 1>&6 -echo "configure:4400: checking for getbkgd in -lcurses" >&5 +echo "configure:4522: checking for getbkgd in -lcurses" >&5 ac_lib_var=`echo curses'_'getbkgd | sed 'y%./+-%__p_%'` if eval "test \"`echo '$''{'ac_cv_lib_$ac_lib_var'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 @@ -4404,7 +4526,7 @@ else ac_save_LIBS="$LIBS" LIBS="-lcurses $LIBS" cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:4541: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -4444,12 +4566,12 @@ fi fi echo $ac_n "checking "for GNU style IPX support"""... $ac_c" 1>&6 -echo "configure:4448: checking "for GNU style IPX support"" >&5 +echo "configure:4570: checking "for GNU style IPX support"" >&5 if eval "test \"`echo '$''{'ac_cv_c_ipx_gnu'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext < #include @@ -4457,7 +4579,7 @@ int main() { ((struct sockaddr_ipx *)0)->sipx_family == AF_IPX ; return 0; } EOF -if { (eval echo configure:4461: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then +if { (eval echo configure:4583: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then rm -rf conftest* ac_cv_c_ipx_gnu="yes" else @@ -4482,12 +4604,12 @@ fi if test "$ac_cv_c_ipx_gnu" = "no" then echo $ac_n "checking "for linux style IPX support"""... $ac_c" 1>&6 -echo "configure:4486: checking "for linux style IPX support"" >&5 +echo "configure:4608: checking "for linux style IPX support"" >&5 if eval "test \"`echo '$''{'ac_cv_c_ipx_linux'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext < #include @@ -4496,7 +4618,7 @@ int main() { ((struct sockaddr_ipx *)0)->sipx_family == AF_IPX ; return 0; } EOF -if { (eval echo configure:4500: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then +if { (eval echo configure:4622: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then rm -rf conftest* ac_cv_c_ipx_linux="yes" else @@ -4523,17 +4645,17 @@ for ac_hdr in sys/soundcard.h machine/soundcard.h soundcard.h do ac_safe=`echo "$ac_hdr" | sed 'y%./+-%__p_%'` echo $ac_n "checking for $ac_hdr""... $ac_c" 1>&6 -echo "configure:4527: checking for $ac_hdr" >&5 +echo "configure:4649: checking for $ac_hdr" >&5 if eval "test \"`echo '$''{'ac_cv_header_$ac_safe'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:4537: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:4659: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* @@ -4561,12 +4683,12 @@ done echo $ac_n "checking "for Open Sound System"""... $ac_c" 1>&6 -echo "configure:4565: checking "for Open Sound System"" >&5 +echo "configure:4687: checking "for Open Sound System"" >&5 if eval "test \"`echo '$''{'ac_cv_c_opensoundsystem'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext <&5; (eval $ac_compile) 2>&5; }; then +if { (eval echo configure:4713: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then rm -rf conftest* ac_cv_c_opensoundsystem="yes" else @@ -4610,12 +4732,12 @@ EOF fi echo $ac_n "checking "for Open Sound System/MIDI interface"""... $ac_c" 1>&6 -echo "configure:4614: checking "for Open Sound System/MIDI interface"" >&5 +echo "configure:4736: checking "for Open Sound System/MIDI interface"" >&5 if eval "test \"`echo '$''{'ac_cv_c_opensoundsystem_midi'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext <&5; (eval $ac_compile) 2>&5; }; then +if { (eval echo configure:4762: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then rm -rf conftest* ac_cv_c_opensoundsystem_midi="yes" else @@ -4665,7 +4787,7 @@ if test "x${GCC}" = "xyes" then CFLAGS="$CFLAGS -Wall" echo $ac_n "checking "for gcc strength-reduce bug"""... $ac_c" 1>&6 -echo "configure:4669: checking "for gcc strength-reduce bug"" >&5 +echo "configure:4791: checking "for gcc strength-reduce bug"" >&5 if eval "test \"`echo '$''{'ac_cv_c_gcc_strength_bug'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else @@ -4673,7 +4795,7 @@ else ac_cv_c_gcc_strength_bug="yes" else cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext} && (./conftest; exit) 2>/dev/null +if { (eval echo configure:4814: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext} && (./conftest; exit) 2>/dev/null then ac_cv_c_gcc_strength_bug="no" else @@ -4709,21 +4831,21 @@ echo "$ac_t""$ac_cv_c_gcc_strength_bug" 1>&6 fi echo $ac_n "checking "for gcc -mpreferred-stack-boundary=2 support"""... $ac_c" 1>&6 -echo "configure:4713: checking "for gcc -mpreferred-stack-boundary=2 support"" >&5 +echo "configure:4835: checking "for gcc -mpreferred-stack-boundary=2 support"" >&5 if eval "test \"`echo '$''{'ac_cv_c_gcc_stack_boundary'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else saved_cflags=$CFLAGS CFLAGS="$CFLAGS -mpreferred-stack-boundary=2" cat > conftest.$ac_ext <&5; (eval $ac_compile) 2>&5; }; then +if { (eval echo configure:4849: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then rm -rf conftest* ac_cv_c_gcc_stack_boundary="yes" else @@ -4746,7 +4868,7 @@ fi echo $ac_n "checking "whether .type must sit inside a .def directive"""... $ac_c" 1>&6 -echo "configure:4750: checking "whether .type must sit inside a .def directive"" >&5 +echo "configure:4872: checking "whether .type must sit inside a .def directive"" >&5 if eval "test \"`echo '$''{'ac_cv_c_type_in_def'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else @@ -4759,14 +4881,14 @@ _ac_test: .long 0 EOF cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:4892: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* ac_cv_c_type_in_def="yes" else @@ -4790,7 +4912,7 @@ fi echo $ac_n "checking "whether external symbols need an underscore prefix"""... $ac_c" 1>&6 -echo "configure:4794: checking "whether external symbols need an underscore prefix"" >&5 +echo "configure:4916: checking "whether external symbols need an underscore prefix"" >&5 if eval "test \"`echo '$''{'ac_cv_c_extern_prefix'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else @@ -4802,14 +4924,14 @@ _ac_test: .long 0 EOF cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:4935: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* ac_cv_c_extern_prefix="yes" else @@ -4833,7 +4955,7 @@ fi echo $ac_n "checking "whether assembler accepts .string"""... $ac_c" 1>&6 -echo "configure:4837: checking "whether assembler accepts .string"" >&5 +echo "configure:4959: checking "whether assembler accepts .string"" >&5 if eval "test \"`echo '$''{'ac_cv_c_asm_string'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else @@ -4843,14 +4965,14 @@ cat > conftest_asm.s < conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:4976: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* ac_cv_c_asm_string="yes" else @@ -4878,21 +5000,21 @@ LDDLLFLAGS="" if test "$LIBEXT" = "so" then echo $ac_n "checking "whether we can build a Linux dll"""... $ac_c" 1>&6 -echo "configure:4882: checking "whether we can build a Linux dll"" >&5 +echo "configure:5004: checking "whether we can build a Linux dll"" >&5 if eval "test \"`echo '$''{'ac_cv_c_dll_linux'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else saved_cflags=$CFLAGS CFLAGS="$CFLAGS -fPIC -shared -Wl,-soname,conftest.so.1.0,-Bsymbolic" cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:5018: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* ac_cv_c_dll_linux="yes" else @@ -4913,21 +5035,21 @@ echo "$ac_t""$ac_cv_c_dll_linux" 1>&6 LDDLLFLAGS="-Wl,-Bsymbolic" else echo $ac_n "checking whether we can build a UnixWare (Solaris) dll""... $ac_c" 1>&6 -echo "configure:4917: checking whether we can build a UnixWare (Solaris) dll" >&5 +echo "configure:5039: checking whether we can build a UnixWare (Solaris) dll" >&5 if eval "test \"`echo '$''{'ac_cv_c_dll_unixware'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else saved_cflags=$CFLAGS CFLAGS="$CFLAGS -fPIC -Wl,-G,-h,conftest.so.1.0,-B,symbolic" cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:5053: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* ac_cv_c_dll_unixware="yes" else @@ -4948,21 +5070,21 @@ echo "$ac_t""$ac_cv_c_dll_unixware" 1>&6 LDDLLFLAGS="-Wl,-B,symbolic" else echo $ac_n "checking "whether we can build a NetBSD dll"""... $ac_c" 1>&6 -echo "configure:4952: checking "whether we can build a NetBSD dll"" >&5 +echo "configure:5074: checking "whether we can build a NetBSD dll"" >&5 if eval "test \"`echo '$''{'ac_cv_c_dll_netbsd'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else saved_cflags=$CFLAGS CFLAGS="$CFLAGS -fPIC -Wl,-Bshareable,-Bforcearchive" cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:5088: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* ac_cv_c_dll_netbsd="yes" else @@ -5018,21 +5140,21 @@ elif test "$LIBEXT" = "dll"; then else DLL_LINK="-L\$(DLLDIR) \$(DLLS:%=-l%) \$(LIBWINE) \$(LIBUNICODE) \$(X_LIBS) \$(XLIB)" echo $ac_n "checking whether the linker supports --[no]-whole-archive (Linux)""... $ac_c" 1>&6 -echo "configure:5022: checking whether the linker supports --[no]-whole-archive (Linux)" >&5 +echo "configure:5144: checking whether the linker supports --[no]-whole-archive (Linux)" >&5 if eval "test \"`echo '$''{'ac_cv_c_whole_archive'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else saved_cflags=$CFLAGS CFLAGS="$CFLAGS -Wl,--whole-archive -Wl,--no-whole-archive" cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:5158: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* ac_cv_c_whole_archive="yes" else @@ -5052,21 +5174,21 @@ echo "$ac_t""$ac_cv_c_whole_archive" 1>&6 DLL_LINK="-Wl,--whole-archive $DLL_LINK -Wl,--no-whole-archive" else echo $ac_n "checking whether the linker supports -z {all,default}extract (Linux)""... $ac_c" 1>&6 -echo "configure:5056: checking whether the linker supports -z {all,default}extract (Linux)" >&5 +echo "configure:5178: checking whether the linker supports -z {all,default}extract (Linux)" >&5 if eval "test \"`echo '$''{'ac_cv_c_allextract'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else saved_cflags=$CFLAGS CFLAGS="$CFLAGS -Wl,-z,allextract -Wl,-z,defaultextract" cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:5192: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* ac_cv_c_allextract="yes" else @@ -5098,7 +5220,7 @@ fi wine_cv_libc_reentrant=no echo $ac_n "checking "for reentrant libc: __errno_location"""... $ac_c" 1>&6 -echo "configure:5102: checking "for reentrant libc: __errno_location"" >&5 +echo "configure:5224: checking "for reentrant libc: __errno_location"" >&5 if eval "test \"`echo '$''{'wine_cv_libc_r__errno_location'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else @@ -5106,14 +5228,14 @@ else wine_cv_libc_r__errno_location=yes else cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext} && (./conftest; exit) 2>/dev/null +if { (eval echo configure:5239: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext} && (./conftest; exit) 2>/dev/null then wine_cv_libc_r__errno_location=yes else @@ -5138,7 +5260,7 @@ EOF wine_cv_libc_reentrant=__errno_location fi echo $ac_n "checking "for reentrant libc: __error"""... $ac_c" 1>&6 -echo "configure:5142: checking "for reentrant libc: __error"" >&5 +echo "configure:5264: checking "for reentrant libc: __error"" >&5 if eval "test \"`echo '$''{'wine_cv_libc_r__error'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else @@ -5146,14 +5268,14 @@ else wine_cv_libc_r__error=yes else cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext} && (./conftest; exit) 2>/dev/null +if { (eval echo configure:5279: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext} && (./conftest; exit) 2>/dev/null then wine_cv_libc_r__error=yes else @@ -5178,7 +5300,7 @@ EOF wine_cv_libc_reentrant=__error fi echo $ac_n "checking "for reentrant libc: ___errno"""... $ac_c" 1>&6 -echo "configure:5182: checking "for reentrant libc: ___errno"" >&5 +echo "configure:5304: checking "for reentrant libc: ___errno"" >&5 if eval "test \"`echo '$''{'wine_cv_libc_r___errno'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else @@ -5186,14 +5308,14 @@ else wine_cv_libc_r___errno=yes else cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext} && (./conftest; exit) 2>/dev/null +if { (eval echo configure:5319: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext} && (./conftest; exit) 2>/dev/null then wine_cv_libc_r___errno=yes else @@ -5218,7 +5340,7 @@ EOF wine_cv_libc_reentrant=___errno fi echo $ac_n "checking "for reentrant libc: __thr_errno"""... $ac_c" 1>&6 -echo "configure:5222: checking "for reentrant libc: __thr_errno"" >&5 +echo "configure:5344: checking "for reentrant libc: __thr_errno"" >&5 if eval "test \"`echo '$''{'wine_cv_libc_r__thr_errno'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else @@ -5226,14 +5348,14 @@ else wine_cv_libc_r__thr_errno=yes else cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext} && (./conftest; exit) 2>/dev/null +if { (eval echo configure:5359: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext} && (./conftest; exit) 2>/dev/null then wine_cv_libc_r__thr_errno=yes else @@ -5269,7 +5391,7 @@ fi if test "$have_x" = "yes" -a "$wine_cv_libc_reentrant" != "no" then echo $ac_n "checking "for reentrant X libraries"""... $ac_c" 1>&6 -echo "configure:5273: checking "for reentrant X libraries"" >&5 +echo "configure:5395: checking "for reentrant X libraries"" >&5 if eval "test \"`echo '$''{'wine_cv_x_reentrant'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else @@ -5315,14 +5437,14 @@ fi echo $ac_n "checking whether byte ordering is bigendian""... $ac_c" 1>&6 -echo "configure:5319: checking whether byte ordering is bigendian" >&5 +echo "configure:5441: checking whether byte ordering is bigendian" >&5 if eval "test \"`echo '$''{'ac_cv_c_bigendian'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else ac_cv_c_bigendian=unknown # See if sys/param.h defines the BYTE_ORDER macro. cat > conftest.$ac_ext < #include @@ -5333,11 +5455,11 @@ int main() { #endif ; return 0; } EOF -if { (eval echo configure:5337: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then +if { (eval echo configure:5459: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then rm -rf conftest* # It does; now see whether it defined to BIG_ENDIAN or not. cat > conftest.$ac_ext < #include @@ -5348,7 +5470,7 @@ int main() { #endif ; return 0; } EOF -if { (eval echo configure:5352: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then +if { (eval echo configure:5474: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then rm -rf conftest* ac_cv_c_bigendian=yes else @@ -5368,7 +5490,7 @@ if test "$cross_compiling" = yes; then { echo "configure: error: can not run test program while cross compiling" 1>&2; exit 1; } else cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext} && (./conftest; exit) 2>/dev/null +if { (eval echo configure:5507: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext} && (./conftest; exit) 2>/dev/null then ac_cv_c_bigendian=no else @@ -5406,7 +5528,7 @@ fi echo $ac_n "checking "whether bitfields are bigendian"""... $ac_c" 1>&6 -echo "configure:5410: checking "whether bitfields are bigendian"" >&5 +echo "configure:5532: checking "whether bitfields are bigendian"" >&5 if eval "test \"`echo '$''{'wine_cv_bitfields_bigendian'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else @@ -5414,7 +5536,7 @@ else wine_cv_bitfields_bigendian=no else cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext} && (./conftest; exit) 2>/dev/null +if { (eval echo configure:5554: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext} && (./conftest; exit) 2>/dev/null then wine_cv_bitfields_bigendian=yes else @@ -5452,7 +5574,7 @@ EOF fi echo $ac_n "checking "whether unaligned memory access is allowed"""... $ac_c" 1>&6 -echo "configure:5456: checking "whether unaligned memory access is allowed"" >&5 +echo "configure:5578: checking "whether unaligned memory access is allowed"" >&5 if eval "test \"`echo '$''{'wine_cv_allow_unaligned_access'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else @@ -5460,7 +5582,7 @@ else wine_cv_allow_unaligned_access=no else cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext} && (./conftest; exit) 2>/dev/null +if { (eval echo configure:5597: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext} && (./conftest; exit) 2>/dev/null then wine_cv_allow_unaligned_access=yes else @@ -5499,19 +5621,19 @@ fi # The Ultrix 4.2 mips builtin alloca declared by alloca.h only works # for constant arguments. Useless! echo $ac_n "checking for working alloca.h""... $ac_c" 1>&6 -echo "configure:5503: checking for working alloca.h" >&5 +echo "configure:5625: checking for working alloca.h" >&5 if eval "test \"`echo '$''{'ac_cv_header_alloca_h'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext < int main() { void *p = alloca(2 * sizeof(int)); ; return 0; } EOF -if { (eval echo configure:5515: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:5637: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* ac_cv_header_alloca_h=yes else @@ -5532,12 +5654,12 @@ EOF fi echo $ac_n "checking for alloca""... $ac_c" 1>&6 -echo "configure:5536: checking for alloca" >&5 +echo "configure:5658: checking for alloca" >&5 if eval "test \"`echo '$''{'ac_cv_func_alloca_works'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:5691: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* ac_cv_func_alloca_works=yes else @@ -5597,12 +5719,12 @@ EOF echo $ac_n "checking whether alloca needs Cray hooks""... $ac_c" 1>&6 -echo "configure:5601: checking whether alloca needs Cray hooks" >&5 +echo "configure:5723: checking whether alloca needs Cray hooks" >&5 if eval "test \"`echo '$''{'ac_cv_os_cray'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext <&6 if test $ac_cv_os_cray = yes; then for ac_func in _getb67 GETB67 getb67; do echo $ac_n "checking for $ac_func""... $ac_c" 1>&6 -echo "configure:5631: checking for $ac_func" >&5 +echo "configure:5753: checking for $ac_func" >&5 if eval "test \"`echo '$''{'ac_cv_func_$ac_func'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:5781: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_func_$ac_func=yes" else @@ -5682,7 +5804,7 @@ done fi echo $ac_n "checking stack direction for C alloca""... $ac_c" 1>&6 -echo "configure:5686: checking stack direction for C alloca" >&5 +echo "configure:5808: checking stack direction for C alloca" >&5 if eval "test \"`echo '$''{'ac_cv_c_stack_direction'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else @@ -5690,7 +5812,7 @@ else ac_cv_c_stack_direction=0 else cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext} && (./conftest; exit) 2>/dev/null +if { (eval echo configure:5835: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext} && (./conftest; exit) 2>/dev/null then ac_cv_c_stack_direction=1 else @@ -5766,12 +5888,12 @@ for ac_func in \ do echo $ac_n "checking for $ac_func""... $ac_c" 1>&6 -echo "configure:5770: checking for $ac_func" >&5 +echo "configure:5892: checking for $ac_func" >&5 if eval "test \"`echo '$''{'ac_cv_func_$ac_func'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:5920: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_func_$ac_func=yes" else @@ -5876,17 +5998,17 @@ for ac_hdr in \ do ac_safe=`echo "$ac_hdr" | sed 'y%./+-%__p_%'` echo $ac_n "checking for $ac_hdr""... $ac_c" 1>&6 -echo "configure:5880: checking for $ac_hdr" >&5 +echo "configure:6002: checking for $ac_hdr" >&5 if eval "test \"`echo '$''{'ac_cv_header_$ac_safe'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext < EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:5890: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:6012: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* @@ -5913,12 +6035,12 @@ fi done echo $ac_n "checking whether stat file-mode macros are broken""... $ac_c" 1>&6 -echo "configure:5917: checking whether stat file-mode macros are broken" >&5 +echo "configure:6039: checking whether stat file-mode macros are broken" >&5 if eval "test \"`echo '$''{'ac_cv_header_stat_broken'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext < #include @@ -5971,12 +6093,12 @@ fi echo $ac_n "checking for working const""... $ac_c" 1>&6 -echo "configure:5975: checking for working const" >&5 +echo "configure:6097: checking for working const" >&5 if eval "test \"`echo '$''{'ac_cv_c_const'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext <&5; (eval $ac_compile) 2>&5; }; then +if { (eval echo configure:6151: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then rm -rf conftest* ac_cv_c_const=yes else @@ -6046,21 +6168,21 @@ EOF fi echo $ac_n "checking for inline""... $ac_c" 1>&6 -echo "configure:6050: checking for inline" >&5 +echo "configure:6172: checking for inline" >&5 if eval "test \"`echo '$''{'ac_cv_c_inline'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else ac_cv_c_inline=no for ac_kw in inline __inline__ __inline; do cat > conftest.$ac_ext <&5; (eval $ac_compile) 2>&5; }; then +if { (eval echo configure:6186: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then rm -rf conftest* ac_cv_c_inline=$ac_kw; break else @@ -6086,12 +6208,12 @@ EOF esac echo $ac_n "checking for ANSI C header files""... $ac_c" 1>&6 -echo "configure:6090: checking for ANSI C header files" >&5 +echo "configure:6212: checking for ANSI C header files" >&5 if eval "test \"`echo '$''{'ac_cv_header_stdc'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext < #include @@ -6099,7 +6221,7 @@ else #include EOF ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" -{ (eval echo configure:6103: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +{ (eval echo configure:6225: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"` if test -z "$ac_err"; then rm -rf conftest* @@ -6116,7 +6238,7 @@ rm -f conftest* if test $ac_cv_header_stdc = yes; then # SunOS 4.x string.h does not declare mem*, contrary to ANSI. cat > conftest.$ac_ext < EOF @@ -6134,7 +6256,7 @@ fi if test $ac_cv_header_stdc = yes; then # ISC 2.0.2 stdlib.h does not declare free, contrary to ANSI. cat > conftest.$ac_ext < EOF @@ -6155,7 +6277,7 @@ if test "$cross_compiling" = yes; then : else cat > conftest.$ac_ext < #define ISLOWER(c) ('a' <= (c) && (c) <= 'z') @@ -6166,7 +6288,7 @@ if (XOR (islower (i), ISLOWER (i)) || toupper (i) != TOUPPER (i)) exit(2); exit (0); } EOF -if { (eval echo configure:6170: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext} && (./conftest; exit) 2>/dev/null +if { (eval echo configure:6292: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext} && (./conftest; exit) 2>/dev/null then : else @@ -6190,12 +6312,12 @@ EOF fi echo $ac_n "checking for size_t""... $ac_c" 1>&6 -echo "configure:6194: checking for size_t" >&5 +echo "configure:6316: checking for size_t" >&5 if eval "test \"`echo '$''{'ac_cv_type_size_t'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext < #if STDC_HEADERS @@ -6223,7 +6345,7 @@ EOF fi echo $ac_n "checking size of long long""... $ac_c" 1>&6 -echo "configure:6227: checking size of long long" >&5 +echo "configure:6349: checking size of long long" >&5 if eval "test \"`echo '$''{'ac_cv_sizeof_long_long'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else @@ -6231,7 +6353,7 @@ else ac_cv_sizeof_long_long=0 else cat > conftest.$ac_ext < main() @@ -6242,7 +6364,7 @@ main() exit(0); } EOF -if { (eval echo configure:6246: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext} && (./conftest; exit) 2>/dev/null +if { (eval echo configure:6368: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext} && (./conftest; exit) 2>/dev/null then ac_cv_sizeof_long_long=`cat conftestval` else @@ -6264,12 +6386,12 @@ EOF echo $ac_n "checking "whether we can use re-entrant gethostbyname_r Linux style"""... $ac_c" 1>&6 -echo "configure:6268: checking "whether we can use re-entrant gethostbyname_r Linux style"" >&5 +echo "configure:6390: checking "whether we can use re-entrant gethostbyname_r Linux style"" >&5 if eval "test \"`echo '$''{'wine_cv_linux_gethostbyname_r_6'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext < @@ -6290,7 +6412,7 @@ int main() { ; return 0; } EOF -if { (eval echo configure:6294: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then +if { (eval echo configure:6416: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then rm -rf conftest* wine_cv_linux_gethostbyname_r_6=yes else @@ -6316,12 +6438,12 @@ EOF if test "$ac_cv_header_linux_joystick_h" = "yes" then echo $ac_n "checking "whether linux/joystick.h uses the Linux 2.2+ API"""... $ac_c" 1>&6 -echo "configure:6320: checking "whether linux/joystick.h uses the Linux 2.2+ API"" >&5 +echo "configure:6442: checking "whether linux/joystick.h uses the Linux 2.2+ API"" >&5 if eval "test \"`echo '$''{'wine_cv_linux_joystick_22_api'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext < @@ -6336,7 +6458,7 @@ int main() { /*empty*/ ; return 0; } EOF -if { (eval echo configure:6340: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then +if { (eval echo configure:6462: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then rm -rf conftest* wine_cv_linux_joystick_22_api=yes else @@ -6363,12 +6485,12 @@ fi if test "$ac_cv_header_sys_vfs_h" = "yes" then echo $ac_n "checking "whether sys/vfs.h defines statfs"""... $ac_c" 1>&6 -echo "configure:6367: checking "whether sys/vfs.h defines statfs"" >&5 +echo "configure:6489: checking "whether sys/vfs.h defines statfs"" >&5 if eval "test \"`echo '$''{'wine_cv_sys_vfs_has_statfs'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext < @@ -6385,7 +6507,7 @@ int main() { ; return 0; } EOF -if { (eval echo configure:6389: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then +if { (eval echo configure:6511: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then rm -rf conftest* wine_cv_sys_vfs_has_statfs=yes else @@ -6412,12 +6534,12 @@ fi if test "$ac_cv_header_sys_statfs_h" = "yes" then echo $ac_n "checking "whether sys/statfs.h defines statfs"""... $ac_c" 1>&6 -echo "configure:6416: checking "whether sys/statfs.h defines statfs"" >&5 +echo "configure:6538: checking "whether sys/statfs.h defines statfs"" >&5 if eval "test \"`echo '$''{'wine_cv_sys_statfs_has_statfs'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext < @@ -6432,7 +6554,7 @@ int main() { ; return 0; } EOF -if { (eval echo configure:6436: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then +if { (eval echo configure:6558: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then rm -rf conftest* wine_cv_sys_statfs_has_statfs=yes else @@ -6459,12 +6581,12 @@ fi if test "$ac_cv_header_sys_mount_h" = "yes" then echo $ac_n "checking "whether sys/mount.h defines statfs"""... $ac_c" 1>&6 -echo "configure:6463: checking "whether sys/mount.h defines statfs"" >&5 +echo "configure:6585: checking "whether sys/mount.h defines statfs"" >&5 if eval "test \"`echo '$''{'wine_cv_sys_mount_has_statfs'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext < @@ -6479,7 +6601,7 @@ int main() { ; return 0; } EOF -if { (eval echo configure:6483: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then +if { (eval echo configure:6605: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then rm -rf conftest* wine_cv_sys_mount_has_statfs=yes else @@ -6505,7 +6627,7 @@ fi echo $ac_n "checking "for statfs.f_bfree"""... $ac_c" 1>&6 -echo "configure:6509: checking "for statfs.f_bfree"" >&5 +echo "configure:6631: checking "for statfs.f_bfree"" >&5 if eval "test \"`echo '$''{'wine_cv_statfs_bfree'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else @@ -6514,7 +6636,7 @@ else wine_cv_statfs_bfree=no else cat > conftest.$ac_ext < @@ -6541,7 +6663,7 @@ int main() { ; return 0; } EOF -if { (eval echo configure:6545: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then +if { (eval echo configure:6667: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then rm -rf conftest* wine_cv_statfs_bfree=yes else @@ -6565,7 +6687,7 @@ EOF fi echo $ac_n "checking "for statfs.f_bavail"""... $ac_c" 1>&6 -echo "configure:6569: checking "for statfs.f_bavail"" >&5 +echo "configure:6691: checking "for statfs.f_bavail"" >&5 if eval "test \"`echo '$''{'wine_cv_statfs_bavail'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else @@ -6574,7 +6696,7 @@ else wine_cv_statfs_bavail=no else cat > conftest.$ac_ext < @@ -6601,7 +6723,7 @@ int main() { ; return 0; } EOF -if { (eval echo configure:6605: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then +if { (eval echo configure:6727: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then rm -rf conftest* wine_cv_statfs_bavail=yes else @@ -6626,12 +6748,12 @@ fi echo $ac_n "checking "for msg_accrights in struct msghdr"""... $ac_c" 1>&6 -echo "configure:6630: checking "for msg_accrights in struct msghdr"" >&5 +echo "configure:6752: checking "for msg_accrights in struct msghdr"" >&5 if eval "test \"`echo '$''{'ac_cv_c_msg_accrights'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext < #include @@ -6639,7 +6761,7 @@ int main() { struct msghdr hdr; hdr.msg_accrights=0 ; return 0; } EOF -if { (eval echo configure:6643: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then +if { (eval echo configure:6765: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then rm -rf conftest* ac_cv_c_msg_accrights="yes" else @@ -6662,12 +6784,12 @@ fi echo $ac_n "checking "for sun_len in struct sockaddr_un"""... $ac_c" 1>&6 -echo "configure:6666: checking "for sun_len in struct sockaddr_un"" >&5 +echo "configure:6788: checking "for sun_len in struct sockaddr_un"" >&5 if eval "test \"`echo '$''{'ac_cv_c_sun_len'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext < #include @@ -6676,7 +6798,7 @@ int main() { static struct sockaddr_un addr; addr.sun_len = 1 ; return 0; } EOF -if { (eval echo configure:6680: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then +if { (eval echo configure:6802: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then rm -rf conftest* ac_cv_c_sun_len="yes" else @@ -6699,12 +6821,12 @@ fi echo $ac_n "checking "whether we need to define __i386__"""... $ac_c" 1>&6 -echo "configure:6703: checking "whether we need to define __i386__"" >&5 +echo "configure:6825: checking "whether we need to define __i386__"" >&5 if eval "test \"`echo '$''{'ac_cv_cpp_def_i386'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext <> 8) | + ((*c_src & 0x00FC00) >> 5) | + ((*c_src & 0x0000F8) >> 3)); + c_src++; + } + c_src+=((pitch/4)-width); + } +} + +Convert ModeEmulations[8] = { + { { 32, 24, 0x00FF0000, 0x0000FF00, 0x000000FF }, { 24, 24, 0xFF0000, 0x00FF00, 0x0000FF }, { pixel_convert_32_to_24, NULL } }, { { 32, 24, 0x00FF0000, 0x0000FF00, 0x000000FF }, { 16, 16, 0xF800, 0x07E0, 0x001F }, { pixel_convert_32_to_16, NULL } }, + { { 32, 24, 0x00FF0000, 0x0000FF00, 0x000000FF }, { 8, 8, 0x00, 0x00, 0x00 }, { pixel_convert_32_to_8, palette_convert_24_to_8 } }, { { 24, 24, 0xFF0000, 0x00FF00, 0x0000FF }, { 8, 8, 0x00, 0x00, 0x00 }, { pixel_convert_24_to_8, palette_convert_24_to_8 } }, { { 16, 15, 0x7C00, 0x03E0, 0x001F }, { 16,16, 0xf800, 0x07e0, 0x001f }, { pixel_convert_15_to_16, NULL } }, { { 16, 16, 0xF800, 0x07E0, 0x001F }, { 8, 8, 0x00, 0x00, 0x00 }, { pixel_convert_16_to_8, palette_convert_16_to_8 } }, { { 16, 15, 0x7C00, 0x03E0, 0x001F }, { 8, 8, 0x00, 0x00, 0x00 }, { pixel_convert_16_to_8, palette_convert_15_to_8 } }, + { { 16, 16, 0xF800, 0x07E0, 0x001F }, { 32, 24, 0x00FF0000, 0x0000FF00, 0x000000FF }, { pixel_convert_16_to_32, NULL } } }; diff --git a/dlls/ddraw/d3d_private.h b/dlls/ddraw/d3d_private.h index 0b630f7b8c1..82cdb9147c1 100644 --- a/dlls/ddraw/d3d_private.h +++ b/dlls/ddraw/d3d_private.h @@ -178,7 +178,7 @@ struct IDirect3DTexture2Impl /* IDirect3DTexture2 fields */ void* D3Ddevice; /* (void *) to use the same pointer * for both Direct3D and Direct3D2 */ - IDirectDrawSurface4Impl* surface; + IDirectDrawSurfaceImpl* surface; LPVOID private; }; @@ -535,8 +535,8 @@ extern HRESULT WINAPI IDirect3DDeviceImpl_GetDirect3D( ); /* All non-static functions 'exported' by various sub-objects */ -extern LPDIRECT3DTEXTURE2 d3dtexture2_create(IDirectDrawSurface4Impl* surf); -extern LPDIRECT3DTEXTURE d3dtexture_create(IDirectDrawSurface4Impl* surf); +extern LPDIRECT3DTEXTURE2 d3dtexture2_create(IDirectDrawSurfaceImpl* surf); +extern LPDIRECT3DTEXTURE d3dtexture_create(IDirectDrawSurfaceImpl* surf); extern LPDIRECT3DLIGHT d3dlight_create_dx3(IDirect3DImpl* d3d1); extern LPDIRECT3DLIGHT d3dlight_create(IDirect3D2Impl* d3d2); diff --git a/dlls/ddraw/d3ddevice/mesa.c b/dlls/ddraw/d3ddevice/mesa.c index ad3dc2962b5..63ea4e734b9 100644 --- a/dlls/ddraw/d3ddevice/mesa.c +++ b/dlls/ddraw/d3ddevice/mesa.c @@ -28,7 +28,6 @@ ICOM_VTABLE(IDirect3DDevice) OpenGL_vtable_dx3; #undef HAVE_BUGGY_MESAGL #define D3DDPRIVATE(x) mesa_d3dd_private *odev=((mesa_d3dd_private*)x->private) -#define DDPRIVATE(x) x11_dd_private *ddpriv=((x11_dd_private*)(x)->d->private) #ifndef HAVE_GLEXT_PROTOTYPES /* This is for non-OpenGL ABI compliant glext.h headers :-) */ @@ -48,8 +47,8 @@ static const float id_mat[16] = { * OpenGL static functions */ static void set_context(IDirect3DDevice2Impl* This) { +#if COMPILABLE D3DDPRIVATE(This); - DDPRIVATE(This->surface->s.ddraw); #ifdef USE_OSMESA OSMesaMakeCurrent(d3ddpriv->ctx, odev->buffer, GL_UNSIGNED_BYTE, @@ -59,7 +58,8 @@ static void set_context(IDirect3DDevice2Impl* This) { if (glXMakeCurrent(display,ddpriv->drawable, odev->ctx) == False) { ERR("Error in setting current context (context %p drawable %ld)!\n", odev->ctx, ddpriv->drawable); -} + } +#endif #endif } @@ -123,6 +123,7 @@ static void fill_opengl_caps(D3DDEVICEDESC *d1, D3DDEVICEDESC *d2) } static void fill_device_capabilities(IDirectDrawImpl* ddraw) { +#if COMPILABLE x11_dd_private *private = (x11_dd_private *) ddraw->d->private; const char *ext_string; Mesa_DeviceCapabilities *devcap; @@ -140,6 +141,7 @@ static void fill_device_capabilities(IDirectDrawImpl* ddraw) { TRACE("Color table extension not found.\n"); } LEAVE_GL(); +#endif } int d3d_OpenGL(LPD3DENUMDEVICESCALLBACK cb, LPVOID context) { @@ -201,6 +203,7 @@ is_OpenGL( else TRACE("Context created (%p)\n", odev->ctx); +#if COMPILABLE /* Now override the surface's Flip method (if in double buffering) */ ((x11_ds_private *) surface->private)->opengl_flip = TRUE; { @@ -210,6 +213,7 @@ is_OpenGL( if (chain->surfaces[i]->s.surface_desc.ddsCaps.dwCaps & DDSCAPS_FLIP) ((x11_ds_private *) chain->surfaces[i]->private)->opengl_flip = TRUE; } +#endif #endif odev->rs.src = GL_ONE; @@ -295,21 +299,21 @@ static HRESULT enum_texture_format_OpenGL(LPD3DENUMTEXTUREFORMATSCALLBACK cb, TRACE("Enumerating GL_RGBA unpacked (32)\n"); pformat->dwFlags = DDPF_RGB | DDPF_ALPHAPIXELS; - pformat->u.dwRGBBitCount = 32; - pformat->u1.dwRBitMask = 0xFF000000; - pformat->u2.dwGBitMask = 0x00FF0000; - pformat->u3.dwBBitMask = 0x0000FF00; - pformat->u4.dwRGBAlphaBitMask = 0x000000FF; + pformat->u1.dwRGBBitCount = 32; + pformat->u2.dwRBitMask = 0xFF000000; + pformat->u3.dwGBitMask = 0x00FF0000; + pformat->u4.dwBBitMask = 0x0000FF00; + pformat->u5.dwRGBAlphaBitMask = 0x000000FF; if (cb(&sdesc, context) == 0) return DD_OK; TRACE("Enumerating GL_RGB unpacked (24)\n"); pformat->dwFlags = DDPF_RGB; - pformat->u.dwRGBBitCount = 24; - pformat->u1.dwRBitMask = 0x00FF0000; - pformat->u2.dwGBitMask = 0x0000FF00; - pformat->u3.dwBBitMask = 0x000000FF; - pformat->u4.dwRGBAlphaBitMask = 0x00000000; + pformat->u1.dwRGBBitCount = 24; + pformat->u2.dwRBitMask = 0x00FF0000; + pformat->u3.dwGBitMask = 0x0000FF00; + pformat->u4.dwBBitMask = 0x000000FF; + pformat->u5.dwRGBAlphaBitMask = 0x00000000; if (cb(&sdesc, context) == 0) return DD_OK; @@ -318,62 +322,62 @@ static HRESULT enum_texture_format_OpenGL(LPD3DENUMTEXTUREFORMATSCALLBACK cb, so that future version will work great. */ TRACE("Enumerating GL_RGB packed GL_UNSIGNED_SHORT_5_6_5 (16)\n"); pformat->dwFlags = DDPF_RGB; - pformat->u.dwRGBBitCount = 16; - pformat->u1.dwRBitMask = 0x0000F800; - pformat->u2.dwGBitMask = 0x000007E0; - pformat->u3.dwBBitMask = 0x0000001F; - pformat->u4.dwRGBAlphaBitMask = 0x00000000; + pformat->u1.dwRGBBitCount = 16; + pformat->u2.dwRBitMask = 0x0000F800; + pformat->u3.dwGBitMask = 0x000007E0; + pformat->u4.dwBBitMask = 0x0000001F; + pformat->u5.dwRGBAlphaBitMask = 0x00000000; if (cb(&sdesc, context) == 0) return DD_OK; TRACE("Enumerating GL_RGBA packed GL_UNSIGNED_SHORT_5_5_5_1 (16)\n"); pformat->dwFlags = DDPF_RGB | DDPF_ALPHAPIXELS; - pformat->u.dwRGBBitCount = 16; - pformat->u1.dwRBitMask = 0x0000F800; - pformat->u2.dwGBitMask = 0x000007C0; - pformat->u3.dwBBitMask = 0x0000003E; - pformat->u4.dwRGBAlphaBitMask = 0x00000001; + pformat->u1.dwRGBBitCount = 16; + pformat->u2.dwRBitMask = 0x0000F800; + pformat->u3.dwGBitMask = 0x000007C0; + pformat->u4.dwBBitMask = 0x0000003E; + pformat->u5.dwRGBAlphaBitMask = 0x00000001; if (cb(&sdesc, context) == 0) return DD_OK; TRACE("Enumerating GL_RGBA packed GL_UNSIGNED_SHORT_4_4_4_4 (16)\n"); pformat->dwFlags = DDPF_RGB | DDPF_ALPHAPIXELS; - pformat->u.dwRGBBitCount = 16; - pformat->u1.dwRBitMask = 0x0000F000; - pformat->u2.dwGBitMask = 0x00000F00; - pformat->u3.dwBBitMask = 0x000000F0; - pformat->u4.dwRGBAlphaBitMask = 0x0000000F; + pformat->u1.dwRGBBitCount = 16; + pformat->u2.dwRBitMask = 0x0000F000; + pformat->u3.dwGBitMask = 0x00000F00; + pformat->u4.dwBBitMask = 0x000000F0; + pformat->u5.dwRGBAlphaBitMask = 0x0000000F; if (cb(&sdesc, context) == 0) return DD_OK; TRACE("Enumerating GL_RGB packed GL_UNSIGNED_BYTE_3_3_2 (8)\n"); pformat->dwFlags = DDPF_RGB; - pformat->u.dwRGBBitCount = 8; - pformat->u1.dwRBitMask = 0x0000F800; - pformat->u2.dwGBitMask = 0x000007C0; - pformat->u3.dwBBitMask = 0x0000003E; - pformat->u4.dwRGBAlphaBitMask = 0x00000001; + pformat->u1.dwRGBBitCount = 8; + pformat->u2.dwRBitMask = 0x0000F800; + pformat->u3.dwGBitMask = 0x000007C0; + pformat->u4.dwBBitMask = 0x0000003E; + pformat->u5.dwRGBAlphaBitMask = 0x00000001; if (cb(&sdesc, context) == 0) return DD_OK; #endif TRACE("Enumerating GL_ARGB (no direct OpenGL equivalent - conversion needed)\n"); pformat->dwFlags = DDPF_RGB | DDPF_ALPHAPIXELS; - pformat->u.dwRGBBitCount = 16; - pformat->u1.dwRBitMask = 0x00007C00; - pformat->u2.dwGBitMask = 0x000003E0; - pformat->u3.dwBBitMask = 0x0000001F; - pformat->u4.dwRGBAlphaBitMask = 0x00008000; + pformat->u1.dwRGBBitCount = 16; + pformat->u2.dwRBitMask = 0x00007C00; + pformat->u3.dwGBitMask = 0x000003E0; + pformat->u4.dwBBitMask = 0x0000001F; + pformat->u5.dwRGBAlphaBitMask = 0x00008000; if (cb(&sdesc, context) == 0) return DD_OK; TRACE("Enumerating Paletted (8)\n"); pformat->dwFlags = DDPF_PALETTEINDEXED8; - pformat->u.dwRGBBitCount = 8; - pformat->u1.dwRBitMask = 0x00000000; - pformat->u2.dwGBitMask = 0x00000000; - pformat->u3.dwBBitMask = 0x00000000; - pformat->u4.dwRGBAlphaBitMask = 0x00000000; + pformat->u1.dwRGBBitCount = 8; + pformat->u2.dwRBitMask = 0x00000000; + pformat->u3.dwGBitMask = 0x00000000; + pformat->u4.dwBBitMask = 0x00000000; + pformat->u5.dwRGBAlphaBitMask = 0x00000000; if (cb(&sdesc, context) == 0) return DD_OK; @@ -936,7 +940,7 @@ int is_OpenGL_dx3(REFCLSID rguid, IDirectDrawSurfaceImpl* surface, IDirect3DDevi glClearColor(0.0, 0.0, 0.0, 0.0); glColor3f(1.0, 1.0, 1.0); - fill_device_capabilities((IDirectDrawImpl *) surface->s.ddraw); + fill_device_capabilities((IDirectDrawImpl *) surface->ddraw_owner); return 1; } diff --git a/dlls/ddraw/d3dtexture.c b/dlls/ddraw/d3dtexture.c index 3013956b2f7..73b6f6d68e8 100644 --- a/dlls/ddraw/d3dtexture.c +++ b/dlls/ddraw/d3dtexture.c @@ -100,7 +100,7 @@ extern ICOM_VTABLE(IDirect3DTexture) mesa_texture_vtable; /******************************************************************************* * Texture2 Creation functions */ -LPDIRECT3DTEXTURE2 d3dtexture2_create(IDirectDrawSurface4Impl* surf) +LPDIRECT3DTEXTURE2 d3dtexture2_create(IDirectDrawSurfaceImpl* surf) { IDirect3DTexture2Impl* tex; @@ -117,7 +117,7 @@ LPDIRECT3DTEXTURE2 d3dtexture2_create(IDirectDrawSurface4Impl* surf) /******************************************************************************* * Texture Creation functions */ -LPDIRECT3DTEXTURE d3dtexture_create(IDirectDrawSurface4Impl* surf) +LPDIRECT3DTEXTURE d3dtexture_create(IDirectDrawSurfaceImpl* surf) { IDirect3DTexture2Impl* tex; @@ -144,10 +144,10 @@ HRESULT WINAPI SetColorKey_cb(IDirect3DTexture2Impl *texture, DWORD dwFlags, LP TRACE("(%p) : colorkey callback\n", texture); /* Get the texture description */ - tex_d = &(texture->surface->s.surface_desc); + tex_d = (DDSURFACEDESC *)&(texture->surface->surface_desc); bpp = (tex_d->ddpfPixelFormat.dwFlags & DDPF_PALETTEINDEXED8 ? 1 /* 8 bit of palette index */: - tex_d->ddpfPixelFormat.u.dwRGBBitCount / 8 /* RGB bits for each colors */ ); + tex_d->ddpfPixelFormat.u1.dwRGBBitCount / 8 /* RGB bits for each colors */ ); /* Now, save the current texture */ ENTER_GL(); @@ -164,15 +164,15 @@ HRESULT WINAPI SetColorKey_cb(IDirect3DTexture2Impl *texture, DWORD dwFlags, LP if (tex_d->ddpfPixelFormat.dwFlags & DDPF_PALETTEINDEXED8) { FIXME("Todo Paletted\n"); } else if (tex_d->ddpfPixelFormat.dwFlags & DDPF_RGB) { - if (tex_d->ddpfPixelFormat.u.dwRGBBitCount == 8) { + if (tex_d->ddpfPixelFormat.u1.dwRGBBitCount == 8) { FIXME("Todo 3_3_2_0\n"); - } else if (tex_d->ddpfPixelFormat.u.dwRGBBitCount == 16) { - if (tex_d->ddpfPixelFormat.u4.dwRGBAlphaBitMask == 0x00000000) { + } else if (tex_d->ddpfPixelFormat.u1.dwRGBBitCount == 16) { + if (tex_d->ddpfPixelFormat.u5.dwRGBAlphaBitMask == 0x00000000) { /* Now transform the 5_6_5 into a 5_5_5_1 surface to support color keying */ unsigned short *dest = (unsigned short *) HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, tex_d->dwWidth * tex_d->dwHeight * bpp); - unsigned short *src = (unsigned short *) tex_d->u1.lpSurface; + unsigned short *src = (unsigned short *) tex_d->lpSurface; int x, y; for (y = 0; y < tex_d->dwHeight; y++) { @@ -199,16 +199,16 @@ HRESULT WINAPI SetColorKey_cb(IDirect3DTexture2Impl *texture, DWORD dwFlags, LP /* Frees the temporary surface */ HeapFree(GetProcessHeap(),0,dest); - } else if (tex_d->ddpfPixelFormat.u4.dwRGBAlphaBitMask == 0x00000001) { + } else if (tex_d->ddpfPixelFormat.u5.dwRGBAlphaBitMask == 0x00000001) { FIXME("Todo 5_5_5_1\n"); - } else if (tex_d->ddpfPixelFormat.u4.dwRGBAlphaBitMask == 0x0000000F) { + } else if (tex_d->ddpfPixelFormat.u5.dwRGBAlphaBitMask == 0x0000000F) { FIXME("Todo 4_4_4_4\n"); } else { ERR("Unhandled texture format (bad Aplha channel for a 16 bit texture)\n"); } - } else if (tex_d->ddpfPixelFormat.u.dwRGBBitCount == 24) { + } else if (tex_d->ddpfPixelFormat.u1.dwRGBBitCount == 24) { FIXME("Todo 8_8_8_0\n"); - } else if (tex_d->ddpfPixelFormat.u.dwRGBBitCount == 32) { + } else if (tex_d->ddpfPixelFormat.u1.dwRGBBitCount == 32) { FIXME("Todo 8_8_8_8\n"); } else { ERR("Unhandled texture format (bad RGB count)\n"); @@ -366,15 +366,15 @@ HRESULT WINAPI IDirect3DTexture2Impl_Load( TRACE("Copied surface %p to surface %p\n", ilpD3DTexture2->surface, This->surface); /* Suppress the ALLOCONLOAD flag */ - This->surface->s.surface_desc.ddsCaps.dwCaps &= ~DDSCAPS_ALLOCONLOAD; + This->surface->surface_desc.ddsCaps.dwCaps &= ~DDSCAPS_ALLOCONLOAD; /* Copy one surface on the other */ - dst_d = &(This->surface->s.surface_desc); - src_d = &(ilpD3DTexture2->surface->s.surface_desc); + dst_d = (DDSURFACEDESC *)&(This->surface->surface_desc); + src_d = (DDSURFACEDESC *)&(ilpD3DTexture2->surface->surface_desc); /* Install the callbacks to the destination surface */ - This->surface->s.texture = This; - This->surface->s.SetColorKey_cb = SetColorKey_cb; + This->surface->texture = This; + This->surface->SetColorKey_cb = SetColorKey_cb; if ((src_d->dwWidth != dst_d->dwWidth) || (src_d->dwHeight != dst_d->dwHeight)) { /* Should also check for same pixel format, lPitch, ... */ @@ -385,12 +385,12 @@ HRESULT WINAPI IDirect3DTexture2Impl_Load( /* I should put a macro for the calculus of bpp */ int bpp = (src_d->ddpfPixelFormat.dwFlags & DDPF_PALETTEINDEXED8 ? 1 /* 8 bit of palette index */: - src_d->ddpfPixelFormat.u.dwRGBBitCount / 8 /* RGB bits for each colors */ ); + src_d->ddpfPixelFormat.u1.dwRGBBitCount / 8 /* RGB bits for each colors */ ); GLuint current_texture; /* Copy the main memry texture into the surface that corresponds to the OpenGL texture object. */ - memcpy(dst_d->u1.lpSurface, src_d->u1.lpSurface, src_d->dwWidth * src_d->dwHeight * bpp); + memcpy(dst_d->lpSurface, src_d->lpSurface, src_d->dwWidth * src_d->dwHeight * bpp); ENTER_GL(); @@ -407,14 +407,16 @@ HRESULT WINAPI IDirect3DTexture2Impl_Load( /* **************** Paletted Texture **************** */ - IDirectDrawPaletteImpl* pal = This->surface->s.palette; + IDirectDrawPaletteImpl* pal = This->surface->palette; BYTE table[256][4]; int i; +#if 0 if (color_table_queried == FALSE) { ptr_ColorTableEXT = ((Mesa_DeviceCapabilities *) ((x11_dd_private *) This->surface->s.ddraw->d->private)->device_capabilities)->ptr_ColorTableEXT; } +#endif if (pal == NULL) { ERR("Palettized texture Loading with a NULL palette !\n"); @@ -427,9 +429,9 @@ HRESULT WINAPI IDirect3DTexture2Impl_Load( table[i][0] = pal->palents[i].peRed; table[i][1] = pal->palents[i].peGreen; table[i][2] = pal->palents[i].peBlue; - if ((This->surface->s.surface_desc.dwFlags & DDSD_CKSRCBLT) && - (i >= This->surface->s.surface_desc.ddckCKSrcBlt.dwColorSpaceLowValue) && - (i <= This->surface->s.surface_desc.ddckCKSrcBlt.dwColorSpaceHighValue)) + if ((This->surface->surface_desc.dwFlags & DDSD_CKSRCBLT) && + (i >= This->surface->surface_desc.ddckCKSrcBlt.dwColorSpaceLowValue) && + (i <= This->surface->surface_desc.ddckCKSrcBlt.dwColorSpaceHighValue)) table[i][3] = 0x00; else table[i][3] = 0xFF; @@ -454,11 +456,11 @@ HRESULT WINAPI IDirect3DTexture2Impl_Load( 0, /* border */ GL_COLOR_INDEX, /* texture format */ GL_UNSIGNED_BYTE, /* texture type */ - src_d->u1.lpSurface); /* the texture */ + src_d->lpSurface); /* the texture */ } else { DWORD *surface = (DWORD *) HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, src_d->dwWidth * src_d->dwHeight * sizeof(DWORD)); DWORD i; - BYTE *src = (BYTE *) src_d->u1.lpSurface, *dst = (BYTE *) surface; + BYTE *src = (BYTE *) src_d->lpSurface, *dst = (BYTE *) surface; for (i = 0; i < src_d->dwHeight * src_d->dwWidth; i++) { BYTE color = *src++; @@ -483,7 +485,7 @@ HRESULT WINAPI IDirect3DTexture2Impl_Load( /* ************ RGB Textures ************ */ - if (src_d->ddpfPixelFormat.u.dwRGBBitCount == 8) { + if (src_d->ddpfPixelFormat.u1.dwRGBBitCount == 8) { /* ********************** GL_UNSIGNED_BYTE_3_3_2 ********************** */ @@ -494,9 +496,9 @@ HRESULT WINAPI IDirect3DTexture2Impl_Load( 0, GL_RGB, GL_UNSIGNED_BYTE_3_3_2, - src_d->u1.lpSurface); - } else if (src_d->ddpfPixelFormat.u.dwRGBBitCount == 16) { - if (src_d->ddpfPixelFormat.u4.dwRGBAlphaBitMask == 0x00000000) { + src_d->lpSurface); + } else if (src_d->ddpfPixelFormat.u1.dwRGBBitCount == 16) { + if (src_d->ddpfPixelFormat.u5.dwRGBAlphaBitMask == 0x00000000) { /* Texture snooping */ SNOOP_5650(); @@ -508,8 +510,8 @@ HRESULT WINAPI IDirect3DTexture2Impl_Load( 0, GL_RGB, GL_UNSIGNED_SHORT_5_6_5, - src_d->u1.lpSurface); - } else if (src_d->ddpfPixelFormat.u4.dwRGBAlphaBitMask == 0x00000001) { + src_d->lpSurface); + } else if (src_d->ddpfPixelFormat.u5.dwRGBAlphaBitMask == 0x00000001) { /* Texture snooping */ SNOOP_5551(); @@ -520,8 +522,8 @@ HRESULT WINAPI IDirect3DTexture2Impl_Load( 0, GL_RGBA, GL_UNSIGNED_SHORT_5_5_5_1, - src_d->u1.lpSurface); - } else if (src_d->ddpfPixelFormat.u4.dwRGBAlphaBitMask == 0x0000000F) { + src_d->lpSurface); + } else if (src_d->ddpfPixelFormat.u5.dwRGBAlphaBitMask == 0x0000000F) { glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, @@ -529,12 +531,12 @@ HRESULT WINAPI IDirect3DTexture2Impl_Load( 0, GL_RGBA, GL_UNSIGNED_SHORT_4_4_4_4, - src_d->u1.lpSurface); - } else if (src_d->ddpfPixelFormat.u4.dwRGBAlphaBitMask == 0x00008000) { + src_d->lpSurface); + } else if (src_d->ddpfPixelFormat.u5.dwRGBAlphaBitMask == 0x00008000) { /* Converting the 1555 format in 5551 packed */ WORD *surface = (WORD *) HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, src_d->dwWidth * src_d->dwHeight * sizeof(WORD)); DWORD i; - WORD *src = (WORD *) src_d->u1.lpSurface, *dst = surface; + WORD *src = (WORD *) src_d->lpSurface, *dst = surface; for (i = 0; i < src_d->dwHeight * src_d->dwWidth; i++) { *dst++ = (((*src & 0x8000) >> 15) | @@ -555,7 +557,7 @@ HRESULT WINAPI IDirect3DTexture2Impl_Load( } else { ERR("Unhandled texture format (bad Aplha channel for a 16 bit texture)\n"); } - } else if (src_d->ddpfPixelFormat.u.dwRGBBitCount == 24) { + } else if (src_d->ddpfPixelFormat.u1.dwRGBBitCount == 24) { glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, @@ -563,8 +565,8 @@ HRESULT WINAPI IDirect3DTexture2Impl_Load( 0, GL_RGB, GL_UNSIGNED_BYTE, - src_d->u1.lpSurface); - } else if (src_d->ddpfPixelFormat.u.dwRGBBitCount == 32) { + src_d->lpSurface); + } else if (src_d->ddpfPixelFormat.u1.dwRGBBitCount == 32) { glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, @@ -572,7 +574,7 @@ HRESULT WINAPI IDirect3DTexture2Impl_Load( 0, GL_RGBA, GL_UNSIGNED_BYTE, - src_d->u1.lpSurface); + src_d->lpSurface); } else { ERR("Unhandled texture format (bad RGB count)\n"); } diff --git a/dlls/ddraw/dclipper/main.c b/dlls/ddraw/dclipper/main.c index 5bb6f37d33e..0290b0461a7 100644 --- a/dlls/ddraw/dclipper/main.c +++ b/dlls/ddraw/dclipper/main.c @@ -1,43 +1,67 @@ /* DirectDrawClipper implementation * * Copyright 2000 Marcus Meissner + * Copyright 2000 TransGaming Technologies Inc. */ #include "config.h" #include "winerror.h" - -#include -#include -#include -#include -#include -#include - #include "debugtools.h" + +#include + #include "ddraw_private.h" +#include "dclipper/main.h" +#include "ddraw/main.h" DEFAULT_DEBUG_CHANNEL(ddraw); /****************************************************************************** * DirectDrawCreateClipper (DDRAW.7) */ + +static ICOM_VTABLE(IDirectDrawClipper) DDRAW_Clipper_VTable; + HRESULT WINAPI DirectDrawCreateClipper( DWORD dwFlags, LPDIRECTDRAWCLIPPER *lplpDDClipper, LPUNKNOWN pUnkOuter ) { - IDirectDrawClipperImpl** ilplpDDClipper=(IDirectDrawClipperImpl**)lplpDDClipper; - TRACE("(%08lx,%p,%p)\n", dwFlags, ilplpDDClipper, pUnkOuter); + IDirectDrawClipperImpl* This; + TRACE("(%08lx,%p,%p)\n", dwFlags, lplpDDClipper, pUnkOuter); - *ilplpDDClipper = (IDirectDrawClipperImpl*)HeapAlloc(GetProcessHeap(),HEAP_ZERO_MEMORY,sizeof(IDirectDrawClipperImpl)); - ICOM_VTBL(*ilplpDDClipper) = &ddclipvt; - (*ilplpDDClipper)->ref = 1; - (*ilplpDDClipper)->hWnd = 0; + if (pUnkOuter != NULL) return CLASS_E_NOAGGREGATION; + + This = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, + sizeof(IDirectDrawClipperImpl)); + if (This == NULL) return E_OUTOFMEMORY; + + ICOM_INIT_INTERFACE(This, IDirectDrawClipper, DDRAW_Clipper_VTable); + This->ref = 1; + This->hWnd = 0; + This->ddraw_owner = NULL; + + *lplpDDClipper = ICOM_INTERFACE(This, IDirectDrawClipper); return DD_OK; } +/* This is the classfactory implementation. */ +HRESULT DDRAW_CreateDirectDrawClipper(IUnknown* pUnkOuter, REFIID riid, + LPVOID* ppObj) +{ + HRESULT hr; + LPDIRECTDRAWCLIPPER pClip; + + hr = DirectDrawCreateClipper(0, &pClip, pUnkOuter); + if (FAILED(hr)) return hr; + + hr = IDirectDrawClipper_QueryInterface(pClip, riid, ppObj); + IDirectDrawClipper_Release(pClip); + return hr; +} + /****************************************************************************** * IDirectDrawClipper */ -static HRESULT WINAPI IDirectDrawClipperImpl_SetHwnd( +HRESULT WINAPI Main_DirectDrawClipper_SetHwnd( LPDIRECTDRAWCLIPPER iface, DWORD dwFlags, HWND hWnd ) { ICOM_THIS(IDirectDrawClipperImpl,iface); @@ -52,50 +76,77 @@ static HRESULT WINAPI IDirectDrawClipperImpl_SetHwnd( return DD_OK; } -static ULONG WINAPI IDirectDrawClipperImpl_Release(LPDIRECTDRAWCLIPPER iface) { +static void Main_DirectDrawClipper_Destroy(IDirectDrawClipperImpl* This) +{ + if (This->ddraw_owner != NULL) + Main_DirectDraw_RemoveClipper(This->ddraw_owner, This); + + HeapFree(GetProcessHeap(), 0 ,This); +} + +void Main_DirectDrawClipper_ForceDestroy(IDirectDrawClipperImpl* This) +{ + WARN("deleting clipper %p with refcnt %lu\n", This, This->ref); + Main_DirectDrawClipper_Destroy(This); +} + +ULONG WINAPI Main_DirectDrawClipper_Release(LPDIRECTDRAWCLIPPER iface) { ICOM_THIS(IDirectDrawClipperImpl,iface); TRACE("(%p)->() decrementing from %lu.\n", This, This->ref ); - This->ref--; - if (This->ref) - return This->ref; - HeapFree(GetProcessHeap(),0,This); - return S_OK; + if (--This->ref == 0) + { + Main_DirectDrawClipper_Destroy(This); + return 0; + } + else return This->ref; } -static HRESULT WINAPI IDirectDrawClipperImpl_GetClipList( - LPDIRECTDRAWCLIPPER iface,LPRECT rects,LPRGNDATA lprgn,LPDWORD hmm +HRESULT WINAPI Main_DirectDrawClipper_GetClipList( + LPDIRECTDRAWCLIPPER iface,LPRECT prcClip,LPRGNDATA lprgn,LPDWORD pdwSize ) { ICOM_THIS(IDirectDrawClipperImpl,iface); - FIXME("(%p,%p,%p,%p),stub!\n",This,rects,lprgn,hmm); - if (hmm) *hmm=0; + FIXME("(%p,%p,%p,%p),stub!\n",This,prcClip,lprgn,pdwSize); + abort(); + if (pdwSize) *pdwSize=0; return DD_OK; } -static HRESULT WINAPI IDirectDrawClipperImpl_SetClipList( - LPDIRECTDRAWCLIPPER iface,LPRGNDATA lprgn,DWORD hmm +HRESULT WINAPI Main_DirectDrawClipper_SetClipList( + LPDIRECTDRAWCLIPPER iface,LPRGNDATA lprgn,DWORD pdwSize ) { ICOM_THIS(IDirectDrawClipperImpl,iface); - FIXME("(%p,%p,%ld),stub!\n",This,lprgn,hmm); + FIXME("(%p,%p,%ld),stub!\n",This,lprgn,pdwSize); + abort(); return DD_OK; } -static HRESULT WINAPI IDirectDrawClipperImpl_QueryInterface( +HRESULT WINAPI Main_DirectDrawClipper_QueryInterface( LPDIRECTDRAWCLIPPER iface, REFIID riid, LPVOID* ppvObj ) { ICOM_THIS(IDirectDrawClipperImpl,iface); - FIXME("(%p)->(%p,%p),stub!\n",This,riid,ppvObj); - return OLE_E_ENUM_NOMORE; + + if (IsEqualGUID(&IID_IUnknown, riid) + || IsEqualGUID(&IID_IDirectDrawClipper, riid)) + { + *ppvObj = ICOM_INTERFACE(This, IDirectDrawClipper); + ++This->ref; + return S_OK; + } + else + { + return E_NOINTERFACE; + } } -static ULONG WINAPI IDirectDrawClipperImpl_AddRef( LPDIRECTDRAWCLIPPER iface ) +ULONG WINAPI Main_DirectDrawClipper_AddRef( LPDIRECTDRAWCLIPPER iface ) { ICOM_THIS(IDirectDrawClipperImpl,iface); TRACE("(%p)->() incrementing from %lu.\n", This, This->ref ); - return ++(This->ref); + return ++This->ref; } -static HRESULT WINAPI IDirectDrawClipperImpl_GetHWnd( +HRESULT WINAPI Main_DirectDrawClipper_GetHWnd( LPDIRECTDRAWCLIPPER iface, HWND* hWndPtr ) { ICOM_THIS(IDirectDrawClipperImpl,iface); @@ -106,32 +157,44 @@ static HRESULT WINAPI IDirectDrawClipperImpl_GetHWnd( return DD_OK; } -static HRESULT WINAPI IDirectDrawClipperImpl_Initialize( +HRESULT WINAPI Main_DirectDrawClipper_Initialize( LPDIRECTDRAWCLIPPER iface, LPDIRECTDRAW lpDD, DWORD dwFlags ) { + IDirectDrawImpl* pOwner; ICOM_THIS(IDirectDrawClipperImpl,iface); FIXME("(%p)->(%p,0x%08lx),stub!\n",This,lpDD,dwFlags); + + if (This->ddraw_owner != NULL) return DDERR_ALREADYINITIALIZED; + + pOwner = ICOM_OBJECT(IDirectDrawImpl, IDirectDraw, lpDD); + This->ddraw_owner = pOwner; + Main_DirectDraw_AddClipper(pOwner, This); + return DD_OK; } -static HRESULT WINAPI IDirectDrawClipperImpl_IsClipListChanged( +HRESULT WINAPI Main_DirectDrawClipper_IsClipListChanged( LPDIRECTDRAWCLIPPER iface, BOOL* lpbChanged ) { ICOM_THIS(IDirectDrawClipperImpl,iface); FIXME("(%p)->(%p),stub!\n",This,lpbChanged); + + /* XXX What is safest? */ + *lpbChanged = FALSE; + return DD_OK; } -ICOM_VTABLE(IDirectDrawClipper) ddclipvt = +static ICOM_VTABLE(IDirectDrawClipper) DDRAW_Clipper_VTable = { ICOM_MSVTABLE_COMPAT_DummyRTTIVALUE - IDirectDrawClipperImpl_QueryInterface, - IDirectDrawClipperImpl_AddRef, - IDirectDrawClipperImpl_Release, - IDirectDrawClipperImpl_GetClipList, - IDirectDrawClipperImpl_GetHWnd, - IDirectDrawClipperImpl_Initialize, - IDirectDrawClipperImpl_IsClipListChanged, - IDirectDrawClipperImpl_SetClipList, - IDirectDrawClipperImpl_SetHwnd + Main_DirectDrawClipper_QueryInterface, + Main_DirectDrawClipper_AddRef, + Main_DirectDrawClipper_Release, + Main_DirectDrawClipper_GetClipList, + Main_DirectDrawClipper_GetHWnd, + Main_DirectDrawClipper_Initialize, + Main_DirectDrawClipper_IsClipListChanged, + Main_DirectDrawClipper_SetClipList, + Main_DirectDrawClipper_SetHwnd }; diff --git a/dlls/ddraw/dclipper/main.h b/dlls/ddraw/dclipper/main.h new file mode 100644 index 00000000000..74063dd9979 --- /dev/null +++ b/dlls/ddraw/dclipper/main.h @@ -0,0 +1,35 @@ +/* Copyright 2000 TransGaming Technologies Inc. */ + +#ifndef WINE_DDRAW_DCLIPPER_MAIN_H_INCLUDED +#define WINE_DDRAW_DCLIPPER_MAIN_H_INCLUDED + +HRESULT WINAPI DirectDrawCreateClipper(DWORD dwFlags, + LPDIRECTDRAWCLIPPER* ppClipper, + LPUNKNOWN pUnkOuter); +HRESULT DDRAW_CreateClipper(IUnknown* pUnkOuter, REFIID riid, LPVOID* ppObj); +void Main_DirectDrawClipper_ForceDestroy(IDirectDrawClipperImpl* This); + +HRESULT WINAPI +Main_DirectDrawClipper_SetHwnd(LPDIRECTDRAWCLIPPER iface, DWORD dwFlags, + HWND hWnd); +ULONG WINAPI Main_DirectDrawClipper_Release(LPDIRECTDRAWCLIPPER iface); +HRESULT WINAPI +Main_DirectDrawClipper_GetClipList(LPDIRECTDRAWCLIPPER iface,LPRECT prcClip, + LPRGNDATA lprgn,LPDWORD pdwSize); +HRESULT WINAPI +Main_DirectDrawClipper_SetClipList(LPDIRECTDRAWCLIPPER iface,LPRGNDATA lprgn, + DWORD pdwSize); +HRESULT WINAPI +Main_DirectDrawClipper_QueryInterface(LPDIRECTDRAWCLIPPER iface, REFIID riid, + LPVOID* ppvObj); +ULONG WINAPI Main_DirectDrawClipper_AddRef( LPDIRECTDRAWCLIPPER iface ); +HRESULT WINAPI +Main_DirectDrawClipper_GetHWnd(LPDIRECTDRAWCLIPPER iface, HWND* hWndPtr); +HRESULT WINAPI +Main_DirectDrawClipper_Initialize(LPDIRECTDRAWCLIPPER iface, LPDIRECTDRAW lpDD, + DWORD dwFlags); +HRESULT WINAPI +Main_DirectDrawClipper_IsClipListChanged(LPDIRECTDRAWCLIPPER iface, + BOOL* lpbChanged); + +#endif diff --git a/dlls/ddraw/ddcomimpl.h b/dlls/ddraw/ddcomimpl.h new file mode 100644 index 00000000000..da4afd8f4e8 --- /dev/null +++ b/dlls/ddraw/ddcomimpl.h @@ -0,0 +1,39 @@ +/* A few helpful macros for implementing COM objects. + * + * Copyright 2000 TransGaming Technologies Inc. + */ + +#include + +/* Generates the name for a vtable pointer for a given interface. */ +/* The canonical name for a single interface is "lpVtbl". */ +#define ICOM_VFIELD_MULTI_NAME2(iface) ITF_##iface +#define ICOM_VFIELD_MULTI_NAME(iface) ICOM_VFIELD_MULTI_NAME2(iface) + +/* Declares a vtable pointer field in an implementation. */ +#define ICOM_VFIELD_MULTI(iface) \ + iface ICOM_VFIELD_MULTI_NAME(iface) + +/* Returns the offset of a vtable pointer within an implementation object. */ +#define ICOM_VFIELD_OFFSET(impltype, iface) \ + offsetof(impltype, ICOM_VFIELD_MULTI_NAME(iface)) + +/* Given an interface pointer, returns the implementation pointer. */ +#define ICOM_OBJECT(impltype, ifacename, ifaceptr) \ + (impltype*)((ifaceptr) == NULL ? NULL \ + : (char*)(ifaceptr) - ICOM_VFIELD_OFFSET(impltype,ifacename)) + +#define ICOM_THIS_FROM(impltype, ifacename, ifaceptr) \ + impltype* This = ICOM_OBJECT(impltype, ifacename, ifaceptr) + +/* Given an object and interface name, returns a pointer to that interface. */ +#define ICOM_INTERFACE(implobj, iface) \ + (&((implobj)->ICOM_VFIELD_MULTI_NAME(iface))) + +#define ICOM_INIT_INTERFACE(implobj, ifacename, vtblname) \ + do { \ + (implobj)->ICOM_VFIELD_MULTI_NAME(ifacename).lpVtbl = &(vtblname); \ + } while (0) + +#define COM_INTERFACE_CAST(impltype, ifnamefrom, ifnameto, ifaceptr) \ + ICOM_INTERFACE(ICOM_OBJECT(impltype, ifnamefrom, ifaceptr), ifnameto) diff --git a/dlls/ddraw/ddraw.spec b/dlls/ddraw/ddraw.spec index 588822c16d1..1682fa77b59 100644 --- a/dlls/ddraw/ddraw.spec +++ b/dlls/ddraw/ddraw.spec @@ -1,5 +1,6 @@ name ddraw type win32 +init DDRAW_DllMain import user32.dll import x11drv.dll diff --git a/dlls/ddraw/ddraw/dga.c b/dlls/ddraw/ddraw/dga.c deleted file mode 100644 index 1695ea312c9..00000000000 --- a/dlls/ddraw/ddraw/dga.c +++ /dev/null @@ -1,714 +0,0 @@ -/* DirectDraw IDirectDraw XF86DGA interface - * - * Copyright 1997-2000 Marcus Meissner - * Copyright 1998-2000 Lionel Ulmer (most of Direct3D stuff) - */ -/* XF86DGA: - * When DirectVideo mode is enabled you can no longer use 'normal' X - * applications nor can you switch to a virtual console. Also, enabling - * only works, if you have switched to the screen where the application - * is running. - * Some ways to debug this stuff are: - * - A terminal connected to the serial port. Can be bought used for cheap. - * (This is the method I am using.) - * - Another machine connected over some kind of network. - */ - -/* - * This file contains the XF86 DGA specific interface functions. - * We are 'allowed' to call X11 specific IDirectDraw functions. - */ - -#include "config.h" - -#include -#include -#include -#include -#include -#include - -#include "winerror.h" -#include "wine/exception.h" -#include "ddraw.h" -#include "d3d.h" -#include "debugtools.h" -#include "options.h" - -#define RESTORE_SIGNALS - -DEFAULT_DEBUG_CHANNEL(ddraw); - -#include "dga_private.h" - -struct ICOM_VTABLE(IDirectDraw) dga_ddvt; -struct ICOM_VTABLE(IDirectDraw2) dga_dd2vt; -struct ICOM_VTABLE(IDirectDraw4) dga_dd4vt; -struct ICOM_VTABLE(IDirectDraw7) dga_dd7vt; - -#define DDPRIVATE(x) dga_dd_private *ddpriv = ((dga_dd_private*)(x)->d->private) -#define DPPRIVATE(x) dga_dp_private *dppriv = ((dga_dp_private*)(x)->private) - -/******************************************************************************* - * IDirectDraw - */ - -/* This function is used both by DGA and DGA2 drivers, thus the virtual function table - is not set here, but in the calling function */ -HRESULT WINAPI DGA_IDirectDraw2Impl_CreateSurface_with_VT( - LPDIRECTDRAW2 iface,LPDDSURFACEDESC lpddsd,LPDIRECTDRAWSURFACE *lpdsf, - IUnknown *lpunk, void *vtable -) { - ICOM_THIS(IDirectDraw2Impl,iface); - IDirectDrawSurfaceImpl* dsurf; - DDPRIVATE(This); - dga_ds_private *dspriv; - int i, fbheight = ddpriv->fb_height; - - TRACE("(%p)->(%p,%p,%p)\n",This,lpddsd,lpdsf,lpunk); - if (TRACE_ON(ddraw)) _dump_surface_desc(lpddsd); - - *lpdsf = (LPDIRECTDRAWSURFACE)HeapAlloc( - GetProcessHeap(), - HEAP_ZERO_MEMORY, - sizeof(IDirectDrawSurfaceImpl) - ); - dsurf = *(IDirectDrawSurfaceImpl**)lpdsf; - dsurf->private = (dga_ds_private*)HeapAlloc( - GetProcessHeap(), - HEAP_ZERO_MEMORY, - sizeof(dga_ds_private) - ); - ICOM_VTBL(dsurf) = (ICOM_VTABLE(IDirectDrawSurface)*)vtable; - - dspriv = (dga_ds_private*)dsurf->private; - IDirectDraw2_AddRef(iface); - - dsurf->ref = 1; - dsurf->s.ddraw = This; - dsurf->s.palette = NULL; - dspriv->fb_height = -1; /* This is to have non-on screen surfaces freed */ - dsurf->s.lpClipper = NULL; - - /* Copy the surface description */ - dsurf->s.surface_desc = *lpddsd; - - if (!(lpddsd->dwFlags & DDSD_WIDTH)) - dsurf->s.surface_desc.dwWidth = This->d->width; - if (!(lpddsd->dwFlags & DDSD_HEIGHT)) - dsurf->s.surface_desc.dwHeight = This->d->height; - - dsurf->s.surface_desc.dwFlags |= DDSD_WIDTH|DDSD_HEIGHT; - - /* Check if this a 'primary surface' or not */ - if ((lpddsd->dwFlags & DDSD_CAPS) && - (lpddsd->ddsCaps.dwCaps & DDSCAPS_PRIMARYSURFACE)) { - /* This is THE primary surface => there is DGA-specific code */ - - /* Find a viewport */ - for (i=0;i<32;i++) - if (!(ddpriv->vpmask & (1<vpmask|=(1<lPitch = dsurf->s.surface_desc.lPitch = - ddpriv->fb_width*PFGET_BPP(This->d->directdraw_pixelformat); - - dsurf->s.surface_desc.u1.lpSurface = - ddpriv->fb_addr + i*fbheight*lpddsd->lPitch; - - dspriv->fb_height = i*fbheight; - - /* Add flags if there were not present */ - dsurf->s.surface_desc.dwFlags |= DDSD_WIDTH|DDSD_HEIGHT|DDSD_PITCH|DDSD_LPSURFACE|DDSD_PIXELFORMAT; - dsurf->s.surface_desc.dwWidth = This->d->width; - dsurf->s.surface_desc.dwHeight = This->d->height; - TRACE("primary surface: dwWidth=%ld, dwHeight=%ld, lPitch=%ld\n",This->d->width,This->d->height,lpddsd->lPitch); - /* We put our surface always in video memory */ - SDDSCAPS(dsurf) |= DDSCAPS_VISIBLE|DDSCAPS_VIDEOMEMORY; - dsurf->s.surface_desc.ddpfPixelFormat = This->d->directdraw_pixelformat; - dsurf->s.chain = NULL; - - if (lpddsd->dwFlags & DDSD_BACKBUFFERCOUNT) { - IDirectDrawSurface4Impl* back; - dga_ds_private *bspriv; - int bbc; - - for (bbc=lpddsd->dwBackBufferCount;bbc--;) { - int i; - - back = (IDirectDrawSurface4Impl*)HeapAlloc( - GetProcessHeap(), - HEAP_ZERO_MEMORY, - sizeof(IDirectDrawSurface4Impl) - ); - IDirectDraw2_AddRef(iface); - back->ref = 1; - ICOM_VTBL(back) = (ICOM_VTABLE(IDirectDrawSurface4)*)vtable; - back->private = HeapAlloc( - GetProcessHeap(), - HEAP_ZERO_MEMORY, - sizeof(dga_ds_private) - ); - bspriv = (dga_ds_private*)back->private; - - for (i=0;i<32;i++) - if (!(ddpriv->vpmask & (1<vpmask|=(1<fb_height = i*fbheight; - /* Copy the surface description from the front buffer */ - back->s.surface_desc = dsurf->s.surface_desc; - /* Change the parameters that are not the same */ - back->s.surface_desc.u1.lpSurface = - ddpriv->fb_addr + i*fbheight*lpddsd->lPitch; - - back->s.ddraw = This; - /* Add relevant info to front and back buffers */ - /* FIXME: backbuffer/frontbuffer handling broken here, but - * will be fixed up in _Flip(). - */ - SDDSCAPS(dsurf) |= DDSCAPS_FRONTBUFFER; - SDDSCAPS(back) |= DDSCAPS_FLIP|DDSCAPS_BACKBUFFER|DDSCAPS_VIDEOMEMORY; - back->s.surface_desc.dwFlags &= ~DDSD_BACKBUFFERCOUNT; - SDDSCAPS(back) &= ~(DDSCAPS_VISIBLE|DDSCAPS_PRIMARYSURFACE); - IDirectDrawSurface4_AddAttachedSurface((LPDIRECTDRAWSURFACE4)(*lpdsf),(LPDIRECTDRAWSURFACE4)back); - } - } - } else { - /* There is no DGA-specific code here... - * Go to the common surface creation function - */ - return common_off_screen_CreateSurface(This, dsurf); - } - return DD_OK; -} - -static HRESULT WINAPI DGA_IDirectDraw2Impl_CreateSurface( - LPDIRECTDRAW2 iface,LPDDSURFACEDESC lpddsd,LPDIRECTDRAWSURFACE *lpdsf, - IUnknown *lpunk -) { - HRESULT ret; - - ret = DGA_IDirectDraw2Impl_CreateSurface_with_VT(iface, lpddsd, lpdsf, lpunk, &dga_dds4vt); - - return ret; -} - - -static HRESULT WINAPI DGA_IDirectDrawImpl_SetDisplayMode( - LPDIRECTDRAW iface,DWORD width,DWORD height,DWORD depth -) { - ICOM_THIS(IDirectDrawImpl,iface); - DDPRIVATE(This); - - TRACE("(%p)->(%ld,%ld,%ld)\n", This, width, height, depth); - - /* We hope getting the asked for depth */ - if ( _common_depth_to_pixelformat(depth,iface) != -1 ) { - /* I.e. no visual found or emulated */ - ERR("(w=%ld,h=%ld,d=%ld), unsupported depth!\n",width,height,depth); - return DDERR_UNSUPPORTEDMODE; - } - - if (This->d->width < width) { - ERR("SetDisplayMode(w=%ld,h=%ld,d=%ld), width %ld exceeds framebuffer width %ld\n",width,height,depth,width,This->d->width); - return DDERR_UNSUPPORTEDMODE; - } - This->d->width = width; - This->d->height = height; - - /* adjust fb_height, so we don't overlap */ - if (ddpriv->fb_height < height) - ddpriv->fb_height = height; - _common_IDirectDrawImpl_SetDisplayMode(This); - - xf86vmode_setdisplaymode(width,height); - - /* FIXME: this function OVERWRITES several signal handlers. - * can we save them? and restore them later? In a way that - * it works for the library too? - */ - TSXF86DGADirectVideo(display,DefaultScreen(display),XF86DGADirectGraphics); - TSXF86DGASetViewPort(display,DefaultScreen(display),0,0); - -#ifdef RESTORE_SIGNALS - SIGNAL_Init(); -#endif - return DD_OK; -} - -HRESULT WINAPI DGA_IDirectDraw2Impl_GetCaps( - LPDIRECTDRAW2 iface,LPDDCAPS caps1,LPDDCAPS caps2 -) { - ICOM_THIS(IDirectDraw2Impl,iface); - DDPRIVATE(This); - - TRACE("(%p)->GetCaps(%p,%p)\n",This,caps1,caps2); - if (!caps1 && !caps2) - return DDERR_INVALIDPARAMS; - if (caps1) { - caps1->dwVidMemTotal = ddpriv->fb_memsize; - caps1->dwCaps = 0xffffffff&~(DDCAPS_BANKSWITCHED); /* we can do anything */ - caps1->ddsCaps.dwCaps = 0xffffffff; /* we can do anything */ - } - if (caps2) { - caps2->dwVidMemTotal = ddpriv->fb_memsize; - caps2->dwCaps = 0xffffffff&~(DDCAPS_BANKSWITCHED); /* we can do anything */ - caps2->ddsCaps.dwCaps = 0xffffffff; /* we can do anything */ - } - return DD_OK; -} - -#if 0 /* Not used as of now.... */ -static void fill_caps(LPDDCAPS caps) { - /* This function tries to fill the capabilities of Wine's DDraw - * implementation. Needs to be fixed, though.. */ - if (caps == NULL) - return; - - caps->dwSize = sizeof(*caps); - caps->dwCaps = DDCAPS_ALPHA | DDCAPS_BLT | DDCAPS_BLTSTRETCH | DDCAPS_BLTCOLORFILL | DDCAPS_BLTDEPTHFILL | DDCAPS_CANBLTSYSMEM | DDCAPS_COLORKEY | DDCAPS_PALETTE /*| DDCAPS_NOHARDWARE*/; - caps->dwCaps2 = DDCAPS2_CERTIFIED | DDCAPS2_NOPAGELOCKREQUIRED | DDCAPS2_WIDESURFACES; - caps->dwCKeyCaps = 0xFFFFFFFF; /* Should put real caps here one day... */ - caps->dwFXCaps = 0; - caps->dwFXAlphaCaps = 0; - caps->dwPalCaps = DDPCAPS_8BIT | DDPCAPS_ALLOW256; - caps->dwSVCaps = 0; - caps->dwZBufferBitDepths = DDBD_16; - /* I put here 8 Mo so that D3D applications will believe they have enough - * memory to put textures in video memory. - * BTW, is this only frame buffer memory or also texture memory (for Voodoo - * boards for example) ? - */ - caps->dwVidMemTotal = 8192 * 1024; - caps->dwVidMemFree = 8192 * 1024; - /* These are all the supported capabilities of the surfaces */ - caps->ddsCaps.dwCaps = DDSCAPS_ALPHA | DDSCAPS_BACKBUFFER | DDSCAPS_COMPLEX | DDSCAPS_FLIP | - DDSCAPS_FRONTBUFFER | DDSCAPS_LOCALVIDMEM | DDSCAPS_NONLOCALVIDMEM | DDSCAPS_OFFSCREENPLAIN | - /*DDSCAPS_OVERLAY |*/ DDSCAPS_PALETTE | DDSCAPS_PRIMARYSURFACE | DDSCAPS_SYSTEMMEMORY | - DDSCAPS_VIDEOMEMORY | DDSCAPS_VISIBLE; -#ifdef HAVE_OPENGL - caps->dwCaps |= DDCAPS_3D | DDCAPS_ZBLTS; - caps->dwCaps2 |= DDCAPS2_NO2DDURING3DSCENE; - caps->ddsCaps.dwCaps |= DDSCAPS_3DDEVICE | DDSCAPS_MIPMAP | DDSCAPS_TEXTURE | DDSCAPS_ZBUFFER; -#endif -} -#endif - -static HRESULT WINAPI DGA_IDirectDraw2Impl_CreatePalette( - LPDIRECTDRAW2 iface,DWORD dwFlags,LPPALETTEENTRY palent,LPDIRECTDRAWPALETTE *lpddpal,LPUNKNOWN lpunk -) { - ICOM_THIS(IDirectDraw2Impl,iface); - IDirectDrawPaletteImpl* ddpal; - dga_dp_private *dppriv; - HRESULT res; - int xsize = 0,i; - - TRACE("(%p)->(%08lx,%p,%p,%p)\n",This,dwFlags,palent,lpddpal,lpunk); - res = common_IDirectDraw2Impl_CreatePalette(This,dwFlags,palent,(IDirectDrawPaletteImpl**)lpddpal,lpunk,&xsize); - if (res != 0) - return res; - ddpal = *(IDirectDrawPaletteImpl**)lpddpal; - ddpal->private = HeapAlloc( - GetProcessHeap(), - HEAP_ZERO_MEMORY, - sizeof(dga_dp_private) - ); - dppriv = (dga_dp_private*)ddpal->private; - - ICOM_VTBL(ddpal)= &dga_ddpalvt; - if (This->d->directdraw_pixelformat.u.dwRGBBitCount<=8) { - dppriv->cm = TSXCreateColormap(display,DefaultRootWindow(display),DefaultVisualOfScreen(X11DRV_GetXScreen()),AllocAll); - } else { - ERR("why are we doing CreatePalette in hi/truecolor?\n"); - dppriv->cm = 0; - } - if (dppriv->cm && xsize) { - for (i=0;ipalents[i].peRed<<8; - xc.blue = ddpal->palents[i].peBlue<<8; - xc.green = ddpal->palents[i].peGreen<<8; - xc.flags = DoRed|DoBlue|DoGreen; - xc.pixel = i; - TSXStoreColor(display,dppriv->cm,&xc); - } - } - return DD_OK; -} - -static HRESULT WINAPI DGA_IDirectDraw2Impl_RestoreDisplayMode(LPDIRECTDRAW2 iface) { - ICOM_THIS(IDirectDraw2Impl,iface); - TRACE("(%p)->()\n",This); - Sleep(1000); - TSXF86DGADirectVideo(display,DefaultScreen(display),0); -#ifdef RESTORE_SIGNALS - SIGNAL_Init(); -#endif - return DD_OK; -} - -static ULONG WINAPI DGA_IDirectDraw2Impl_Release(LPDIRECTDRAW2 iface) { - ICOM_THIS(IDirectDraw2Impl,iface); - DDPRIVATE(This); - TRACE("(%p)->() decrementing from %lu.\n", This, This->ref ); - - if (!--(This->ref)) { - if (!--(This->d->ref)) { - VirtualFree(ddpriv->fb_addr, 0, MEM_RELEASE); - TSXF86DGADirectVideo(display,DefaultScreen(display),0); - if (This->d->window && GetPropA(This->d->window,ddProp)) - DestroyWindow(This->d->window); - - xf86vmode_restore(); - -#ifdef RESTORE_SIGNALS - SIGNAL_Init(); -#endif - HeapFree(GetProcessHeap(),0,This->d); - } - HeapFree(GetProcessHeap(),0,This); - return S_OK; - } - return This->ref; -} - -HRESULT WINAPI DGA_IDirectDraw2Impl_QueryInterface( - LPDIRECTDRAW2 iface,REFIID refiid,LPVOID *obj -) { - ICOM_THIS(IDirectDraw2Impl,iface); - - TRACE("(%p)->(%s,%p)\n",This,debugstr_guid(refiid),obj); - if ( IsEqualGUID( &IID_IUnknown, refiid ) ) { - *obj = This; - IDirectDraw2_AddRef(iface); - - TRACE(" Creating IUnknown interface (%p)\n", *obj); - - return S_OK; - } - if ( IsEqualGUID( &IID_IDirectDraw, refiid ) ) { - IDirectDrawImpl *dd = HeapAlloc(GetProcessHeap(),0,sizeof(*dd)); - ICOM_VTBL(dd) = &dga_ddvt;dd->ref = 1;dd->d = This->d;This->d++; - *obj = dd; - - IDirectDraw2_AddRef(iface); - TRACE(" Creating IDirectDraw interface (%p)\n", *obj); - - return S_OK; - } - if ( IsEqualGUID( &IID_IDirectDraw2, refiid ) ) { - IDirectDraw2Impl *dd = HeapAlloc(GetProcessHeap(),0,sizeof(*dd)); - ICOM_VTBL(dd) = &dga_dd2vt;dd->ref = 1;dd->d = This->d;This->d++; - *obj = dd; - - IDirectDraw2_AddRef(iface); - TRACE(" Creating IDirectDraw2 interface (%p)\n", *obj); - return S_OK; - } - if ( IsEqualGUID( &IID_IDirectDraw4, refiid ) ) { - IDirectDraw4Impl *dd = HeapAlloc(GetProcessHeap(),0,sizeof(*dd)); - ICOM_VTBL(dd) = &dga_dd4vt;dd->ref = 1;dd->d = This->d;This->d++; - *obj = dd; - - IDirectDraw4_AddRef(iface); - TRACE(" Creating IDirectDraw4 interface (%p)\n", *obj); - return S_OK; - } - if ( IsEqualGUID( &IID_IDirectDraw7, refiid ) ) { - IDirectDraw4Impl *dd = HeapAlloc(GetProcessHeap(),0,sizeof(*dd)); - ICOM_VTBL(dd) = (ICOM_VTABLE(IDirectDraw4)*)&dga_dd7vt;dd->ref = 1;dd->d = This->d;This->d++; - *obj = dd; - - IDirectDraw7_AddRef(iface); - FIXME(" Creating IDirectDraw7 interface (by using DirectDraw4 impl.) (%p)\n", *obj); - return S_OK; - } - FIXME("(%p):interface for IID %s _NOT_ found!\n",This,debugstr_guid(refiid)); - return OLE_E_ENUM_NOMORE; -} - -static HRESULT WINAPI DGA_IDirectDraw2Impl_EnumDisplayModes( - LPDIRECTDRAW2 iface,DWORD dwFlags,LPDDSURFACEDESC lpddsfd,LPVOID context,LPDDENUMMODESCALLBACK modescb -) { - ICOM_THIS(IDirectDraw2Impl,iface); - DDSURFACEDESC ddsfd; - static struct { - int w,h; - } modes[5] = { /* some usual modes */ - {512,384}, - {640,400}, - {640,480}, - {800,600}, - {1024,768}, - }; - static int depths[4] = {8,16,24,32}; - int i,j; - - TRACE("(%p)->(0x%08lx,%p,%p,%p)\n",This,dwFlags,lpddsfd,context,modescb); - ddsfd.dwSize = sizeof(ddsfd); - ddsfd.dwFlags = DDSD_HEIGHT|DDSD_WIDTH|DDSD_BACKBUFFERCOUNT|DDSD_PIXELFORMAT|DDSD_CAPS; - if (dwFlags & DDEDM_REFRESHRATES) { - ddsfd.dwFlags |= DDSD_REFRESHRATE; - ddsfd.u.dwRefreshRate = 60; - } - ddsfd.ddsCaps.dwCaps = 0; - ddsfd.dwBackBufferCount = 1; - - for (i=0;i 8 */ - if (depths[i]==8) { - ddsfd.ddpfPixelFormat.u1.dwRBitMask = 0; - ddsfd.ddpfPixelFormat.u2.dwGBitMask = 0; - ddsfd.ddpfPixelFormat.u3.dwBBitMask = 0; - ddsfd.ddpfPixelFormat.u4.dwRGBAlphaBitMask= 0; - ddsfd.ddsCaps.dwCaps=DDSCAPS_PALETTE; - ddsfd.ddpfPixelFormat.dwFlags|=DDPF_PALETTEINDEXED8; - } else { - ddsfd.ddpfPixelFormat.u4.dwRGBAlphaBitMask= 0; - - /* FIXME: We should query those from X itself */ - switch (depths[i]) { - case 16: - ddsfd.ddpfPixelFormat.u1.dwRBitMask = 0xF800; - ddsfd.ddpfPixelFormat.u2.dwGBitMask = 0x07E0; - ddsfd.ddpfPixelFormat.u3.dwBBitMask= 0x001F; - break; - case 24: - ddsfd.ddpfPixelFormat.u1.dwRBitMask = 0x00FF0000; - ddsfd.ddpfPixelFormat.u2.dwGBitMask = 0x0000FF00; - ddsfd.ddpfPixelFormat.u3.dwBBitMask= 0x000000FF; - break; - case 32: - ddsfd.ddpfPixelFormat.u1.dwRBitMask = 0x00FF0000; - ddsfd.ddpfPixelFormat.u2.dwGBitMask = 0x0000FF00; - ddsfd.ddpfPixelFormat.u3.dwBBitMask= 0x000000FF; - break; - } - } - - ddsfd.dwWidth = GetSystemMetrics(SM_CXSCREEN); - ddsfd.dwHeight = GetSystemMetrics(SM_CYSCREEN); - TRACE(" enumerating (%ldx%ldx%d)\n",ddsfd.dwWidth,ddsfd.dwHeight,depths[i]); - if (!modescb(&ddsfd,context)) return DD_OK; - - for (j=0;j(%p)\n",This,lpddsfd); - lpddsfd->dwFlags = DDSD_HEIGHT|DDSD_WIDTH|DDSD_PITCH|DDSD_BACKBUFFERCOUNT|DDSD_PIXELFORMAT|DDSD_CAPS; - lpddsfd->dwHeight = This->d->height; - lpddsfd->dwWidth = This->d->width; - lpddsfd->lPitch = ddpriv->fb_width*PFGET_BPP(This->d->directdraw_pixelformat); - lpddsfd->dwBackBufferCount = 2; - lpddsfd->u.dwRefreshRate = 60; - lpddsfd->ddsCaps.dwCaps = DDSCAPS_PALETTE; - lpddsfd->ddpfPixelFormat = This->d->directdraw_pixelformat; - if (TRACE_ON(ddraw)) - _dump_surface_desc(lpddsfd); - return DD_OK; -} - -/* Note: Hack so we can reuse the old functions without compiler warnings */ -#if !defined(__STRICT_ANSI__) && defined(__GNUC__) -# define XCAST(fun) (typeof(dga_ddvt.fn##fun)) -#else -# define XCAST(fun) (void *) -#endif - -struct ICOM_VTABLE(IDirectDraw) dga_ddvt = -{ - ICOM_MSVTABLE_COMPAT_DummyRTTIVALUE - XCAST(QueryInterface)DGA_IDirectDraw2Impl_QueryInterface, - XCAST(AddRef)IDirectDraw2Impl_AddRef, - XCAST(Release)DGA_IDirectDraw2Impl_Release, - XCAST(Compact)IDirectDraw2Impl_Compact, - XCAST(CreateClipper)IDirectDraw2Impl_CreateClipper, - XCAST(CreatePalette)DGA_IDirectDraw2Impl_CreatePalette, - XCAST(CreateSurface)DGA_IDirectDraw2Impl_CreateSurface, - XCAST(DuplicateSurface)IDirectDraw2Impl_DuplicateSurface, - XCAST(EnumDisplayModes)DGA_IDirectDraw2Impl_EnumDisplayModes, - XCAST(EnumSurfaces)IDirectDraw2Impl_EnumSurfaces, - XCAST(FlipToGDISurface)IDirectDraw2Impl_FlipToGDISurface, - XCAST(GetCaps)DGA_IDirectDraw2Impl_GetCaps, - XCAST(GetDisplayMode)DGA_IDirectDraw2Impl_GetDisplayMode, - XCAST(GetFourCCCodes)IDirectDraw2Impl_GetFourCCCodes, - XCAST(GetGDISurface)IDirectDraw2Impl_GetGDISurface, - XCAST(GetMonitorFrequency)IDirectDraw2Impl_GetMonitorFrequency, - XCAST(GetScanLine)IDirectDraw2Impl_GetScanLine, - XCAST(GetVerticalBlankStatus)IDirectDraw2Impl_GetVerticalBlankStatus, - XCAST(Initialize)IDirectDraw2Impl_Initialize, - XCAST(RestoreDisplayMode)DGA_IDirectDraw2Impl_RestoreDisplayMode, - XCAST(SetCooperativeLevel)IDirectDraw2Impl_SetCooperativeLevel, - DGA_IDirectDrawImpl_SetDisplayMode, - XCAST(WaitForVerticalBlank)IDirectDraw2Impl_WaitForVerticalBlank, -}; -#undef XCAST - -/***************************************************************************** - * IDirectDraw2 - * - */ - -static HRESULT WINAPI DGA_IDirectDraw2Impl_SetDisplayMode( - LPDIRECTDRAW2 iface,DWORD width,DWORD height,DWORD depth,DWORD dwRefreshRate, DWORD dwFlags -) { - FIXME( "Ignored parameters (0x%08lx,0x%08lx)\n", dwRefreshRate, dwFlags ); - return DGA_IDirectDrawImpl_SetDisplayMode((LPDIRECTDRAW)iface,width,height,depth); -} - -HRESULT WINAPI DGA_IDirectDraw2Impl_GetAvailableVidMem( - LPDIRECTDRAW2 iface,LPDDSCAPS ddscaps,LPDWORD total,LPDWORD free -) { - ICOM_THIS(IDirectDraw2Impl,iface); - DDPRIVATE(This); - - TRACE("(%p)->(%p,%p,%p)\n",This,ddscaps,total,free); - if (total) *total = ddpriv->fb_memsize * 1024; - if (free) *free = ddpriv->fb_memsize * 1024; - return DD_OK; -} - -ICOM_VTABLE(IDirectDraw2) dga_dd2vt = -{ - ICOM_MSVTABLE_COMPAT_DummyRTTIVALUE - DGA_IDirectDraw2Impl_QueryInterface, - IDirectDraw2Impl_AddRef, - DGA_IDirectDraw2Impl_Release, - IDirectDraw2Impl_Compact, - IDirectDraw2Impl_CreateClipper, - DGA_IDirectDraw2Impl_CreatePalette, - DGA_IDirectDraw2Impl_CreateSurface, - IDirectDraw2Impl_DuplicateSurface, - DGA_IDirectDraw2Impl_EnumDisplayModes, - IDirectDraw2Impl_EnumSurfaces, - IDirectDraw2Impl_FlipToGDISurface, - DGA_IDirectDraw2Impl_GetCaps, - DGA_IDirectDraw2Impl_GetDisplayMode, - IDirectDraw2Impl_GetFourCCCodes, - IDirectDraw2Impl_GetGDISurface, - IDirectDraw2Impl_GetMonitorFrequency, - IDirectDraw2Impl_GetScanLine, - IDirectDraw2Impl_GetVerticalBlankStatus, - IDirectDraw2Impl_Initialize, - DGA_IDirectDraw2Impl_RestoreDisplayMode, - IDirectDraw2Impl_SetCooperativeLevel, - DGA_IDirectDraw2Impl_SetDisplayMode, - IDirectDraw2Impl_WaitForVerticalBlank, - DGA_IDirectDraw2Impl_GetAvailableVidMem -}; - -#if !defined(__STRICT_ANSI__) && defined(__GNUC__) -# define XCAST(fun) (typeof(dga_dd4vt.fn##fun)) -#else -# define XCAST(fun) (void*) -#endif - -ICOM_VTABLE(IDirectDraw4) dga_dd4vt = -{ - ICOM_MSVTABLE_COMPAT_DummyRTTIVALUE - XCAST(QueryInterface)DGA_IDirectDraw2Impl_QueryInterface, - XCAST(AddRef)IDirectDraw2Impl_AddRef, - XCAST(Release)DGA_IDirectDraw2Impl_Release, - XCAST(Compact)IDirectDraw2Impl_Compact, - XCAST(CreateClipper)IDirectDraw2Impl_CreateClipper, - XCAST(CreatePalette)DGA_IDirectDraw2Impl_CreatePalette, - XCAST(CreateSurface)DGA_IDirectDraw2Impl_CreateSurface, - XCAST(DuplicateSurface)IDirectDraw2Impl_DuplicateSurface, - XCAST(EnumDisplayModes)DGA_IDirectDraw2Impl_EnumDisplayModes, - XCAST(EnumSurfaces)IDirectDraw2Impl_EnumSurfaces, - XCAST(FlipToGDISurface)IDirectDraw2Impl_FlipToGDISurface, - XCAST(GetCaps)DGA_IDirectDraw2Impl_GetCaps, - XCAST(GetDisplayMode)DGA_IDirectDraw2Impl_GetDisplayMode, - XCAST(GetFourCCCodes)IDirectDraw2Impl_GetFourCCCodes, - XCAST(GetGDISurface)IDirectDraw2Impl_GetGDISurface, - XCAST(GetMonitorFrequency)IDirectDraw2Impl_GetMonitorFrequency, - XCAST(GetScanLine)IDirectDraw2Impl_GetScanLine, - XCAST(GetVerticalBlankStatus)IDirectDraw2Impl_GetVerticalBlankStatus, - XCAST(Initialize)IDirectDraw2Impl_Initialize, - XCAST(RestoreDisplayMode)DGA_IDirectDraw2Impl_RestoreDisplayMode, - XCAST(SetCooperativeLevel)IDirectDraw2Impl_SetCooperativeLevel, - XCAST(SetDisplayMode)DGA_IDirectDrawImpl_SetDisplayMode, - XCAST(WaitForVerticalBlank)IDirectDraw2Impl_WaitForVerticalBlank, - XCAST(GetAvailableVidMem)DGA_IDirectDraw2Impl_GetAvailableVidMem, - IDirectDraw4Impl_GetSurfaceFromDC, - IDirectDraw4Impl_RestoreAllSurfaces, - IDirectDraw4Impl_TestCooperativeLevel, - IDirectDraw4Impl_GetDeviceIdentifier -}; -#undef XCAST - -#if !defined(__STRICT_ANSI__) && defined(__GNUC__) -# define XCAST(fun) (typeof(dga_dd7vt.fn##fun)) -#else -# define XCAST(fun) (void*) -#endif - -ICOM_VTABLE(IDirectDraw7) dga_dd7vt = -{ - ICOM_MSVTABLE_COMPAT_DummyRTTIVALUE - XCAST(QueryInterface)DGA_IDirectDraw2Impl_QueryInterface, - XCAST(AddRef)IDirectDraw2Impl_AddRef, - XCAST(Release)DGA_IDirectDraw2Impl_Release, - XCAST(Compact)IDirectDraw2Impl_Compact, - XCAST(CreateClipper)IDirectDraw2Impl_CreateClipper, - XCAST(CreatePalette)DGA_IDirectDraw2Impl_CreatePalette, - XCAST(CreateSurface)DGA_IDirectDraw2Impl_CreateSurface, - XCAST(DuplicateSurface)IDirectDraw2Impl_DuplicateSurface, - XCAST(EnumDisplayModes)DGA_IDirectDraw2Impl_EnumDisplayModes, - XCAST(EnumSurfaces)IDirectDraw2Impl_EnumSurfaces, - XCAST(FlipToGDISurface)IDirectDraw2Impl_FlipToGDISurface, - XCAST(GetCaps)DGA_IDirectDraw2Impl_GetCaps, - XCAST(GetDisplayMode)DGA_IDirectDraw2Impl_GetDisplayMode, - XCAST(GetFourCCCodes)IDirectDraw2Impl_GetFourCCCodes, - XCAST(GetGDISurface)IDirectDraw2Impl_GetGDISurface, - XCAST(GetMonitorFrequency)IDirectDraw2Impl_GetMonitorFrequency, - XCAST(GetScanLine)IDirectDraw2Impl_GetScanLine, - XCAST(GetVerticalBlankStatus)IDirectDraw2Impl_GetVerticalBlankStatus, - XCAST(Initialize)IDirectDraw2Impl_Initialize, - XCAST(RestoreDisplayMode)DGA_IDirectDraw2Impl_RestoreDisplayMode, - XCAST(SetCooperativeLevel)IDirectDraw2Impl_SetCooperativeLevel, - XCAST(SetDisplayMode)DGA_IDirectDrawImpl_SetDisplayMode, - XCAST(WaitForVerticalBlank)IDirectDraw2Impl_WaitForVerticalBlank, - XCAST(GetAvailableVidMem)DGA_IDirectDraw2Impl_GetAvailableVidMem, - XCAST(GetSurfaceFromDC)IDirectDraw4Impl_GetSurfaceFromDC, - XCAST(RestoreAllSurfaces)IDirectDraw4Impl_RestoreAllSurfaces, - XCAST(TestCooperativeLevel)IDirectDraw4Impl_TestCooperativeLevel, - XCAST(GetDeviceIdentifier)IDirectDraw4Impl_GetDeviceIdentifier, - IDirectDraw7Impl_StartModeTest, - IDirectDraw7Impl_EvaluateMode -}; -#undef XCAST diff --git a/dlls/ddraw/ddraw/dga2.c b/dlls/ddraw/ddraw/dga2.c index 88f26653bef..fabc2af53ef 100644 --- a/dlls/ddraw/ddraw/dga2.c +++ b/dlls/ddraw/ddraw/dga2.c @@ -1,431 +1,407 @@ -/* DirectDraw IDirectDraw XF86DGA interface +/* DirectDraw driver for XF86DGA2 primary surface * - * DGA2's specific IDirectDraw functions... + * Copyright 2000 TransGaming Technologies Inc. */ #include "config.h" -#include -#include +#ifdef HAVE_LIBXXF86DGA2 + +#include "debugtools.h" +#include "ts_xlib.h" +#include "ts_xf86dga2.h" +#include "x11drv.h" +#include + #include -#include -#include #include -#include "winerror.h" -#include "wine/exception.h" -#include "ddraw.h" -#include "d3d.h" -#include "debugtools.h" -#include "message.h" +#include "ddraw_private.h" +#include "ddraw/main.h" +#include "ddraw/user.h" +#include "ddraw/dga2.h" +#include "dclipper/main.h" +#include "dpalette/main.h" +#include "dsurface/main.h" +#include "dsurface/dib.h" +#include "dsurface/user.h" +#include "dsurface/dga2.h" + #include "options.h" DEFAULT_DEBUG_CHANNEL(ddraw); -#include "dga2_private.h" +static ICOM_VTABLE(IDirectDraw7) XF86DGA2_DirectDraw_VTable; -struct ICOM_VTABLE(IDirectDraw) dga2_ddvt; -struct ICOM_VTABLE(IDirectDraw2) dga2_dd2vt; -struct ICOM_VTABLE(IDirectDraw4) dga2_dd4vt; +static const DDDEVICEIDENTIFIER2 xf86dga2_device = +{ + "XF86DGA2 Driver", + "WINE DirectDraw on XF86DGA2", + { { 0x00010001, 0x00010001 } }, + 0, 0, 0, 0, + /* e2dcb020-dc60-11d1-8407-9714f5d50803 */ + {0xe2dcb020,0xdc60,0x11d1,{0x84,0x07,0x97,0x14,0xf5,0xd5,0x08,0x03}}, + 0 +}; -#define DDPRIVATE(x) dga2_dd_private *ddpriv = ((dga2_dd_private*)(x)->d->private) -#define DPPRIVATE(x) dga2_dp_private *dppriv = ((dga2_dp_private*)(x)->private) +HRESULT XF86DGA2_DirectDraw_Create(const GUID* pGUID, LPDIRECTDRAW7* pIface, + IUnknown* pUnkOuter, BOOL ex); +HRESULT XF86DGA2_DirectDraw_Initialize(IDirectDrawImpl*, const GUID*); -/******************************************************************************* - * IDirectDraw - */ -static HRESULT WINAPI DGA2_IDirectDraw2Impl_CreateSurface( - LPDIRECTDRAW2 iface,LPDDSURFACEDESC lpddsd,LPDIRECTDRAWSURFACE *lpdsf, - IUnknown *lpunk -) { - HRESULT ret; +static const ddraw_driver xf86dga2_driver = +{ + &xf86dga2_device, + 20, /* XVidMode is 11 */ + XF86DGA2_DirectDraw_Create, + XF86DGA2_DirectDraw_Initialize +}; - ret = DGA_IDirectDraw2Impl_CreateSurface_with_VT(iface, lpddsd, lpdsf, lpunk, &dga2_dds4vt); +static XDGAMode* modes; +static DWORD num_modes; +static int dga_event, dga_error; - return ret; -} +/* Called from DllInit, which is synchronised so there are no threading + * concerns. */ +static BOOL initialize(void) +{ + int nmodes; + int major, minor; -static HRESULT WINAPI DGA2_IDirectDraw2Impl_SetCooperativeLevel( - LPDIRECTDRAW2 iface,HWND hwnd,DWORD cooplevel -) { - /* ICOM_THIS(IDirectDraw2Impl,iface); */ - HRESULT ret; - int evbase, erbase; + if (X11DRV_GetXRootWindow() != DefaultRootWindow(display)) return FALSE; - ret = IDirectDraw2Impl_SetCooperativeLevel(iface, hwnd, cooplevel); + /* FIXME: don't use PROFILE calls */ + if (!PROFILE_GetWineIniBool("x11drv", "UseDGA", 1)) return FALSE; - if (ret != DD_OK) - return ret; + if (!TSXDGAQueryExtension(display, &dga_event, &dga_error)) return FALSE; - TSXDGAQueryExtension(display, &evbase, &erbase); + if (!TSXDGAQueryVersion(display, &major, &minor)) return FALSE; + + if (major < 2) return FALSE; /* only bother with DGA2 */ + + /* test that it works */ + if (!TSXDGAOpenFramebuffer(display, DefaultScreen(display))) { + TRACE("disabling XF86DGA2 (insufficient permissions?)\n"); + return FALSE; + } + TSXDGACloseFramebuffer(display, DefaultScreen(display)); - /* Now, start handling of DGA events giving the handle to the DDraw window - as the window for which the event will be reported */ - TSXDGASelectInput(display, DefaultScreen(display), - KeyPressMask|KeyReleaseMask|ButtonPressMask|ButtonReleaseMask|PointerMotionMask ); - X11DRV_EVENT_SetDGAStatus(hwnd, evbase); - return DD_OK; + TRACE("getting XF86DGA2 mode list\n"); + modes = TSXDGAQueryModes(display, DefaultScreen(display), &nmodes); + if (!modes) return FALSE; + num_modes = nmodes; + + TRACE("enabling XF86DGA2\n"); + + return TRUE; } -void _DGA2_Initialize_FrameBuffer(IDirectDrawImpl *This, int mode) { - DDPIXELFORMAT *pf = &(This->d->directdraw_pixelformat); - DDPRIVATE(This); - - /* Now, get the device / mode description */ - ddpriv->dev = TSXDGASetMode(display, DefaultScreen(display), mode); - - ddpriv->DGA.fb_width = ddpriv->dev->mode.imageWidth; - TSXDGASetViewport(display,DefaultScreen(display),0,0, XDGAFlipImmediate); - ddpriv->DGA.fb_height = ddpriv->dev->mode.viewportHeight; - TRACE("video framebuffer: begin %p, width %d, memsize %d\n", - ddpriv->dev->data, - ddpriv->dev->mode.imageWidth, - (ddpriv->dev->mode.imageWidth * - ddpriv->dev->mode.imageHeight * - (ddpriv->dev->mode.bitsPerPixel / 8)) - ); - TRACE("viewport height: %d\n", ddpriv->dev->mode.viewportHeight); - /* Get the screen dimensions as seen by Wine. - * In that case, it may be better to ignore the -desktop mode and return the - * real screen size => print a warning */ - This->d->height = GetSystemMetrics(SM_CYSCREEN); - This->d->width = GetSystemMetrics(SM_CXSCREEN); - ddpriv->DGA.fb_addr = ddpriv->dev->data; - ddpriv->DGA.fb_memsize = (ddpriv->dev->mode.imageWidth * - ddpriv->dev->mode.imageHeight * - (ddpriv->dev->mode.bitsPerPixel / 8)); - ddpriv->DGA.vpmask = 0; - - /* Fill the screen pixelformat */ - pf->dwSize = sizeof(DDPIXELFORMAT); - pf->dwFourCC = 0; - pf->u.dwRGBBitCount = ddpriv->dev->mode.bitsPerPixel; - if (ddpriv->dev->mode.depth == 8) { - pf->dwFlags = DDPF_PALETTEINDEXED8|DDPF_RGB; - pf->u1.dwRBitMask = 0; - pf->u2.dwGBitMask = 0; - pf->u3.dwBBitMask = 0; - } else { - pf->dwFlags = DDPF_RGB; - pf->u1.dwRBitMask = ddpriv->dev->mode.redMask; - pf->u2.dwGBitMask = ddpriv->dev->mode.greenMask; - pf->u3.dwBBitMask = ddpriv->dev->mode.blueMask; - } - pf->u4.dwRGBAlphaBitMask= 0; - This->d->screen_pixelformat = *pf; +static void cleanup(void) +{ + TSXFree(modes); } -static HRESULT WINAPI DGA2_IDirectDrawImpl_SetDisplayMode( - LPDIRECTDRAW iface,DWORD width,DWORD height,DWORD depth -) { - ICOM_THIS(IDirectDrawImpl,iface); - DDPRIVATE(This); - int i; - XDGAMode *modes = ddpriv->modes; - int mode_to_use = -1; +static XDGAMode* choose_mode(DWORD dwWidth, DWORD dwHeight, + DWORD dwRefreshRate, DWORD dwFlags) +{ + XDGAMode* best = NULL; + int i; - TRACE("(%p)->(%ld,%ld,%ld)\n", This, width, height, depth); - - /* Search in the list a display mode that corresponds to what is requested */ - for (i = 0; i < ddpriv->num_modes; i++) { - if ((height == modes[i].viewportHeight) && - (width == modes[i].viewportWidth) && - (depth == modes[i].depth) - ) - mode_to_use = modes[i].num; - } - - if (mode_to_use < 0) { - ERR("Could not find matching mode !!!\n"); - return DDERR_UNSUPPORTEDMODE; - } else { - TRACE("Using mode number %d\n", mode_to_use); - - VirtualFree(ddpriv->DGA.fb_addr, 0, MEM_RELEASE); - TSXDGACloseFramebuffer(display, DefaultScreen(display)); - - if (!TSXDGAOpenFramebuffer(display, DefaultScreen(display))) { - ERR("Error opening the frame buffer !!!\n"); - return DDERR_GENERIC; - } - - /* Initialize the frame buffer */ - _DGA2_Initialize_FrameBuffer(This, mode_to_use); - VirtualAlloc(ddpriv->DGA.fb_addr, ddpriv->DGA.fb_memsize, MEM_RESERVE|MEM_SYSTEM, PAGE_READWRITE); - - /* Re-get (if necessary) the DGA events */ - TSXDGASelectInput(display, DefaultScreen(display), - KeyPressMask|KeyReleaseMask|ButtonPressMask|ButtonReleaseMask|PointerMotionMask ); - - /* And change the DDraw parameters */ - This->d->width = width; - This->d->height = height; - } - - return DD_OK; -} - -static HRESULT WINAPI DGA2_IDirectDraw2Impl_CreatePalette( - LPDIRECTDRAW2 iface,DWORD dwFlags,LPPALETTEENTRY palent,LPDIRECTDRAWPALETTE *lpddpal,LPUNKNOWN lpunk -) { - ICOM_THIS(IDirectDraw2Impl,iface); - IDirectDrawPaletteImpl* ddpal; - dga_dp_private *dppriv; - HRESULT res; - int xsize = 0,i; - DDPRIVATE(This); - - TRACE("(%p)->(%08lx,%p,%p,%p)\n",This,dwFlags,palent,lpddpal,lpunk); - res = common_IDirectDraw2Impl_CreatePalette(This,dwFlags,palent,(IDirectDrawPaletteImpl**)lpddpal,lpunk,&xsize); - if (res != 0) - return res; - ddpal = *(IDirectDrawPaletteImpl**)lpddpal; - ddpal->private = HeapAlloc( - GetProcessHeap(), - HEAP_ZERO_MEMORY, - sizeof(dga_dp_private) - ); - dppriv = (dga_dp_private*)ddpal->private; - - ICOM_VTBL(ddpal)= &dga_ddpalvt; - if (This->d->directdraw_pixelformat.u.dwRGBBitCount<=8) { - dppriv->cm = TSXDGACreateColormap(display,DefaultScreen(display), ddpriv->dev, AllocAll); - } else { - ERR("why are we doing CreatePalette in hi/truecolor?\n"); - dppriv->cm = 0; - } - if (dppriv->cm && xsize) { - for (i=0;ipalents[i].peRed<<8; - xc.blue = ddpal->palents[i].peBlue<<8; - xc.green = ddpal->palents[i].peGreen<<8; - xc.flags = DoRed|DoBlue|DoGreen; - xc.pixel = i; - TSXStoreColor(display,dppriv->cm,&xc); + /* Choose the smallest mode that is large enough. */ + for (i=0; i < num_modes; i++) + { + if (modes[i].viewportWidth >= dwWidth && modes[i].viewportHeight >= dwHeight) + { + if (best == NULL) best = &modes[i]; + else + { + if (modes[i].viewportWidth < best->viewportWidth + || modes[i].viewportHeight < best->viewportHeight) + best = &modes[i]; + } } } - return DD_OK; + + /* all modes were too small, use the largest */ + if (!best) + { + TRACE("all modes too small\n"); + + for (i=1; i < num_modes; i++) + { + if (best == NULL) best = &modes[i]; + else + { + if (modes[i].viewportWidth > best->viewportWidth + || modes[i].viewportHeight > best->viewportHeight) + best = &modes[i]; + } + } + } + + TRACE("using %d %d for %lu %lu\n", best->viewportWidth, best->viewportHeight, + dwWidth, dwHeight); + + return best; } -static HRESULT WINAPI DGA2_IDirectDraw2Impl_RestoreDisplayMode(LPDIRECTDRAW2 iface) { - ICOM_THIS(IDirectDraw2Impl,iface); - TRACE("(%p)->()\n",This); - Sleep(1000); - - XDGACloseFramebuffer(display,DefaultScreen(display)); - XDGASetMode(display,DefaultScreen(display), 0); +BOOL DDRAW_XF86DGA2_Init(HINSTANCE hInstDLL, DWORD fdwReason, LPVOID lpv) +{ + if (fdwReason == DLL_PROCESS_ATTACH) + { + if (initialize()) + DDRAW_register_driver(&xf86dga2_driver); + } + else if (fdwReason == DLL_PROCESS_DETACH) + { + cleanup(); + } + + return TRUE; +} + +/* Not called from the vtable. */ +HRESULT XF86DGA2_DirectDraw_Construct(IDirectDrawImpl *This, BOOL ex) +{ + HRESULT hr; + + TRACE("\n"); + + hr = User_DirectDraw_Construct(This, ex); + if (FAILED(hr)) return hr; + + This->final_release = XF86DGA2_DirectDraw_final_release; + + This->create_primary = XF86DGA2_DirectDraw_create_primary; + This->create_backbuffer = XF86DGA2_DirectDraw_create_backbuffer; + + ICOM_INIT_INTERFACE(This, IDirectDraw7, XF86DGA2_DirectDraw_VTable); + + return S_OK; +} + +/* This function is called from DirectDrawCreate(Ex) on the most-derived + * class to start construction. + * Not called from the vtable. */ +HRESULT XF86DGA2_DirectDraw_Create(const GUID* pGUID, LPDIRECTDRAW7* pIface, + IUnknown* pUnkOuter, BOOL ex) +{ + HRESULT hr; + IDirectDrawImpl* This; + + TRACE("\n"); + + assert(pUnkOuter == NULL); + + This = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, + sizeof(IDirectDrawImpl) + + sizeof(XF86DGA2_DirectDrawImpl)); + if (This == NULL) return E_OUTOFMEMORY; + + /* Note that this relation does *not* hold true if the DD object was + * CoCreateInstanced then Initialized. */ + This->private = (XF86DGA2_DirectDrawImpl *)(This+1); + + hr = XF86DGA2_DirectDraw_Construct(This, ex); + if (FAILED(hr)) + HeapFree(GetProcessHeap(), 0, This); + else + *pIface = ICOM_INTERFACE(This, IDirectDraw7); + + return hr; +} + +/* This function is called from Uninit_DirectDraw_Initialize on the + * most-derived-class to start initialization. + * Not called from the vtable. */ +HRESULT XF86DGA2_DirectDraw_Initialize(IDirectDrawImpl *This, const GUID* guid) +{ + HRESULT hr; + + TRACE("\n"); + + This->private = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, + sizeof(XF86DGA2_DirectDrawImpl)); + if (This->private == NULL) return E_OUTOFMEMORY; + + hr = XF86DGA2_DirectDraw_Construct(This, TRUE); /* XXX ex? */ + if (FAILED(hr)) + { + HeapFree(GetProcessHeap(), 0, This->private); + return hr; + } return DD_OK; } -static ULONG WINAPI DGA2_IDirectDraw2Impl_Release(LPDIRECTDRAW2 iface) { - ICOM_THIS(IDirectDraw2Impl,iface); - DDPRIVATE(This); - TRACE("(%p)->() decrementing from %lu.\n", This, This->ref ); +/* Called from an internal function pointer. */ +void XF86DGA2_DirectDraw_final_release(IDirectDrawImpl *This) +{ + XF86DGA2_DDRAW_PRIV_VAR(priv, This); - if (!--(This->ref)) { - if (!--(This->d->ref)) { - TRACE("Closing access to the FrameBuffer\n"); - VirtualFree(ddpriv->DGA.fb_addr, 0, MEM_RELEASE); - TSXDGACloseFramebuffer(display, DefaultScreen(display)); - TRACE("Going back to normal X mode of operation\n"); - TSXDGASetMode(display, DefaultScreen(display), 0); - - /* Set the input handling back to absolute */ - X11DRV_EVENT_SetInputMethod(X11DRV_INPUT_ABSOLUTE); - - /* Remove the handling of DGA2 events */ - X11DRV_EVENT_SetDGAStatus(0, -1); - - /* Free the modes list */ - TSXFree(ddpriv->modes); - HeapFree(GetProcessHeap(),0,This->d); - } - HeapFree(GetProcessHeap(),0,This); - return 0; + if (priv->xf86dga2.current_mode) { + TSXDGASetMode(display, DefaultScreen(display), 0); + VirtualFree(priv->xf86dga2.current_mode->data, 0, MEM_RELEASE); + X11DRV_EVENT_SetInputMethod(X11DRV_INPUT_ABSOLUTE); + X11DRV_EVENT_SetDGAStatus(0, -1); + TSXFree(priv->xf86dga2.current_mode); + TSXDGACloseFramebuffer(display, DefaultScreen(display)); + priv->xf86dga2.current_mode = NULL; } - return This->ref; + + User_DirectDraw_final_release(This); } -static HRESULT WINAPI DGA2_IDirectDraw2Impl_EnumDisplayModes( - LPDIRECTDRAW2 iface,DWORD dwFlags,LPDDSURFACEDESC lpddsfd,LPVOID context,LPDDENUMMODESCALLBACK modescb -) { - ICOM_THIS(IDirectDraw2Impl,iface); - DDSURFACEDESC ddsfd; - DDPRIVATE(This); - int i; - XDGAMode *modes = ddpriv->modes; +HRESULT XF86DGA2_DirectDraw_create_primary(IDirectDrawImpl* This, + const DDSURFACEDESC2* pDDSD, + LPDIRECTDRAWSURFACE7* ppSurf, + IUnknown* pUnkOuter) +{ + if (This->cooperative_level & DDSCL_EXCLUSIVE) + return XF86DGA2_DirectDrawSurface_Create(This, pDDSD, ppSurf, pUnkOuter); + else + return User_DirectDrawSurface_Create(This, pDDSD, ppSurf, pUnkOuter); +} - TRACE("(%p)->(0x%08lx,%p,%p,%p)\n",This,dwFlags,lpddsfd,context,modescb); - ddsfd.dwSize = sizeof(ddsfd); - ddsfd.dwFlags = DDSD_HEIGHT|DDSD_WIDTH|DDSD_BACKBUFFERCOUNT|DDSD_PIXELFORMAT|DDSD_CAPS; - if (dwFlags & DDEDM_REFRESHRATES) { - ddsfd.dwFlags |= DDSD_REFRESHRATE; - ddsfd.u.dwRefreshRate = 60; - } - ddsfd.ddsCaps.dwCaps = 0; - ddsfd.dwBackBufferCount = 1; +HRESULT XF86DGA2_DirectDraw_create_backbuffer(IDirectDrawImpl* This, + const DDSURFACEDESC2* pDDSD, + LPDIRECTDRAWSURFACE7* ppSurf, + IUnknown* pUnkOuter, + IDirectDrawSurfaceImpl* primary) +{ + if (This->cooperative_level & DDSCL_EXCLUSIVE) + return XF86DGA2_DirectDrawSurface_Create(This, pDDSD, ppSurf, pUnkOuter); + else + return User_DirectDrawSurface_Create(This, pDDSD, ppSurf, pUnkOuter); +} - - ddsfd.dwFlags |= DDSD_PITCH; - for (i = 0; i < ddpriv->num_modes; i++) { - if (TRACE_ON(ddraw)) { - DPRINTF(" Enumerating mode %d : %s (FB: %dx%d / VP: %dx%d) - depth %d -", - modes[i].num, - modes[i].name, modes[i].imageWidth, modes[i].imageHeight, - modes[i].viewportWidth, modes[i].viewportHeight, - modes[i].depth); - if (modes[i].flags & XDGAConcurrentAccess) DPRINTF(" XDGAConcurrentAccess "); - if (modes[i].flags & XDGASolidFillRect) DPRINTF(" XDGASolidFillRect "); - if (modes[i].flags & XDGABlitRect) DPRINTF(" XDGABlitRect "); - if (modes[i].flags & XDGABlitTransRect) DPRINTF(" XDGABlitTransRect "); - if (modes[i].flags & XDGAPixmap) DPRINTF(" XDGAPixmap "); - DPRINTF("\n"); - } - /* Fill the pixel format */ - ddsfd.ddpfPixelFormat.dwSize = sizeof(DDPIXELFORMAT); - ddsfd.ddpfPixelFormat.dwFourCC = 0; - ddsfd.ddpfPixelFormat.u4.dwRGBAlphaBitMask= 0; - ddsfd.ddpfPixelFormat.u.dwRGBBitCount = modes[i].bitsPerPixel; - if (modes[i].depth == 8) { - ddsfd.ddpfPixelFormat.dwFlags = DDPF_RGB|DDPF_PALETTEINDEXED8; - ddsfd.ddpfPixelFormat.u1.dwRBitMask = 0; - ddsfd.ddpfPixelFormat.u2.dwGBitMask = 0; - ddsfd.ddpfPixelFormat.u3.dwBBitMask = 0; - ddsfd.ddsCaps.dwCaps = DDSCAPS_PALETTE; - } else { - ddsfd.ddpfPixelFormat.dwFlags = DDPF_RGB; - ddsfd.ddpfPixelFormat.u1.dwRBitMask = modes[i].redMask; - ddsfd.ddpfPixelFormat.u2.dwGBitMask = modes[i].greenMask; - ddsfd.ddpfPixelFormat.u3.dwBBitMask = modes[i].blueMask; - } - - ddsfd.dwWidth = modes[i].viewportWidth; - ddsfd.dwHeight = modes[i].viewportHeight; - ddsfd.lPitch = modes[i].imageWidth; - - /* Send mode to the application */ - if (!modescb(&ddsfd,context)) return DD_OK; - } - +HRESULT WINAPI +XF86DGA2_DirectDraw_GetDeviceIdentifier(LPDIRECTDRAW7 iface, + LPDDDEVICEIDENTIFIER2 pDDDI, + DWORD dwFlags) +{ + *pDDDI = xf86dga2_device; return DD_OK; } -/* Note: Hack so we can reuse the old functions without compiler warnings */ -#if !defined(__STRICT_ANSI__) && defined(__GNUC__) -# define XCAST(fun) (typeof(dga2_ddvt.fn##fun)) -#else -# define XCAST(fun) (void *) -#endif - -struct ICOM_VTABLE(IDirectDraw) dga2_ddvt = +HRESULT WINAPI +XF86DGA2_DirectDraw_RestoreDisplayMode(LPDIRECTDRAW7 iface) { - ICOM_MSVTABLE_COMPAT_DummyRTTIVALUE - XCAST(QueryInterface)DGA_IDirectDraw2Impl_QueryInterface, - XCAST(AddRef)IDirectDraw2Impl_AddRef, - XCAST(Release)DGA2_IDirectDraw2Impl_Release, - XCAST(Compact)IDirectDraw2Impl_Compact, - XCAST(CreateClipper)IDirectDraw2Impl_CreateClipper, - XCAST(CreatePalette)DGA2_IDirectDraw2Impl_CreatePalette, - XCAST(CreateSurface)DGA2_IDirectDraw2Impl_CreateSurface, - XCAST(DuplicateSurface)IDirectDraw2Impl_DuplicateSurface, - XCAST(EnumDisplayModes)DGA2_IDirectDraw2Impl_EnumDisplayModes, - XCAST(EnumSurfaces)IDirectDraw2Impl_EnumSurfaces, - XCAST(FlipToGDISurface)IDirectDraw2Impl_FlipToGDISurface, - XCAST(GetCaps)DGA_IDirectDraw2Impl_GetCaps, - XCAST(GetDisplayMode)DGA_IDirectDraw2Impl_GetDisplayMode, - XCAST(GetFourCCCodes)IDirectDraw2Impl_GetFourCCCodes, - XCAST(GetGDISurface)IDirectDraw2Impl_GetGDISurface, - XCAST(GetMonitorFrequency)IDirectDraw2Impl_GetMonitorFrequency, - XCAST(GetScanLine)IDirectDraw2Impl_GetScanLine, - XCAST(GetVerticalBlankStatus)IDirectDraw2Impl_GetVerticalBlankStatus, - XCAST(Initialize)IDirectDraw2Impl_Initialize, - XCAST(RestoreDisplayMode)DGA2_IDirectDraw2Impl_RestoreDisplayMode, - XCAST(SetCooperativeLevel)DGA2_IDirectDraw2Impl_SetCooperativeLevel, - DGA2_IDirectDrawImpl_SetDisplayMode, - XCAST(WaitForVerticalBlank)IDirectDraw2Impl_WaitForVerticalBlank, -}; -#undef XCAST + ICOM_THIS(IDirectDrawImpl, iface); + HRESULT hr; -/***************************************************************************** - * IDirectDraw2 - * - */ + TRACE("\n"); -static HRESULT WINAPI DGA2_IDirectDraw2Impl_SetDisplayMode( - LPDIRECTDRAW2 iface,DWORD width,DWORD height,DWORD depth,DWORD dwRefreshRate, DWORD dwFlags -) { - FIXME( "Ignored parameters (0x%08lx,0x%08lx)\n", dwRefreshRate, dwFlags ); - return DGA2_IDirectDrawImpl_SetDisplayMode((LPDIRECTDRAW)iface,width,height,depth); + hr = Main_DirectDraw_RestoreDisplayMode(iface); + if (SUCCEEDED(hr)) + { + XF86DGA2_DDRAW_PRIV_VAR(priv, This); + + if (priv->xf86dga2.current_mode) + { + TSXDGASetMode(display, DefaultScreen(display), 0); + VirtualFree(priv->xf86dga2.current_mode->data, 0, MEM_RELEASE); + X11DRV_EVENT_SetInputMethod(X11DRV_INPUT_ABSOLUTE); + X11DRV_EVENT_SetDGAStatus(0, -1); + TSXFree(priv->xf86dga2.current_mode); + TSXDGACloseFramebuffer(display, DefaultScreen(display)); + priv->xf86dga2.current_mode = NULL; + } + } + + return hr; } -ICOM_VTABLE(IDirectDraw2) dga2_dd2vt = +HRESULT WINAPI +XF86DGA2_DirectDraw_SetDisplayMode(LPDIRECTDRAW7 iface, DWORD dwWidth, + DWORD dwHeight, DWORD dwBPP, + DWORD dwRefreshRate, DWORD dwFlags) { - ICOM_MSVTABLE_COMPAT_DummyRTTIVALUE - DGA_IDirectDraw2Impl_QueryInterface, - IDirectDraw2Impl_AddRef, - DGA2_IDirectDraw2Impl_Release, - IDirectDraw2Impl_Compact, - IDirectDraw2Impl_CreateClipper, - DGA2_IDirectDraw2Impl_CreatePalette, - DGA2_IDirectDraw2Impl_CreateSurface, - IDirectDraw2Impl_DuplicateSurface, - DGA2_IDirectDraw2Impl_EnumDisplayModes, - IDirectDraw2Impl_EnumSurfaces, - IDirectDraw2Impl_FlipToGDISurface, - DGA_IDirectDraw2Impl_GetCaps, - DGA_IDirectDraw2Impl_GetDisplayMode, - IDirectDraw2Impl_GetFourCCCodes, - IDirectDraw2Impl_GetGDISurface, - IDirectDraw2Impl_GetMonitorFrequency, - IDirectDraw2Impl_GetScanLine, - IDirectDraw2Impl_GetVerticalBlankStatus, - IDirectDraw2Impl_Initialize, - DGA2_IDirectDraw2Impl_RestoreDisplayMode, - DGA2_IDirectDraw2Impl_SetCooperativeLevel, - DGA2_IDirectDraw2Impl_SetDisplayMode, - IDirectDraw2Impl_WaitForVerticalBlank, - DGA_IDirectDraw2Impl_GetAvailableVidMem + ICOM_THIS(IDirectDrawImpl, iface); + + HRESULT hr; + + TRACE("(%p)->(%ldx%ldx%ld,%ld Hz,%08lx)\n",This,dwWidth,dwHeight,dwBPP,dwRefreshRate,dwFlags); + hr = User_DirectDraw_SetDisplayMode(iface, dwWidth, dwHeight, dwBPP, + dwRefreshRate, dwFlags); + + if (SUCCEEDED(hr)) + { + XF86DGA2_DDRAW_PRIV_VAR(priv, This); + XDGADevice* old_mode = priv->xf86dga2.current_mode; + XDGAMode* new_mode; + int old_mode_num = old_mode ? old_mode->mode.num : 0; + + new_mode = choose_mode(dwWidth, dwHeight, dwRefreshRate, dwFlags); + + if (new_mode && new_mode->num != old_mode_num) + { + XDGADevice * nm = NULL; + if (old_mode || TSXDGAOpenFramebuffer(display, DefaultScreen(display))) + nm = TSXDGASetMode(display, DefaultScreen(display), new_mode->num); + if (nm) { + TSXDGASetViewport(display, DefaultScreen(display), 0, 0, XDGAFlipImmediate); + if (old_mode) { + VirtualFree(old_mode->data, 0, MEM_RELEASE); + TSXFree(old_mode); + } else { + TSXDGASelectInput(display, DefaultScreen(display), + KeyPressMask|KeyReleaseMask| + ButtonPressMask|ButtonReleaseMask| + PointerMotionMask); + X11DRV_EVENT_SetDGAStatus(This->window, dga_event); + X11DRV_EVENT_SetInputMethod(X11DRV_INPUT_RELATIVE); + } + priv->xf86dga2.current_mode = nm; + priv->xf86dga2.next_vofs = 0; + TRACE("frame buffer at %p, pitch=%d, width=%d, height=%d\n", nm->data, + nm->mode.bytesPerScanline, nm->mode.imageWidth, nm->mode.imageHeight); + VirtualAlloc(nm->data, nm->mode.bytesPerScanline * nm->mode.imageHeight, + MEM_RESERVE|MEM_SYSTEM, PAGE_READWRITE); + } else { + /* argh */ + ERR("failed\n"); + /* XXX revert size data to previous mode */ + if (!old_mode) + TSXDGACloseFramebuffer(display, DefaultScreen(display)); + } + } + } + + return hr; +} + +static ICOM_VTABLE(IDirectDraw7) XF86DGA2_DirectDraw_VTable = +{ + Main_DirectDraw_QueryInterface, + Main_DirectDraw_AddRef, + Main_DirectDraw_Release, + Main_DirectDraw_Compact, + Main_DirectDraw_CreateClipper, + Main_DirectDraw_CreatePalette, + Main_DirectDraw_CreateSurface, + Main_DirectDraw_DuplicateSurface, + User_DirectDraw_EnumDisplayModes, + Main_DirectDraw_EnumSurfaces, + Main_DirectDraw_FlipToGDISurface, + User_DirectDraw_GetCaps, + Main_DirectDraw_GetDisplayMode, + Main_DirectDraw_GetFourCCCodes, + Main_DirectDraw_GetGDISurface, + Main_DirectDraw_GetMonitorFrequency, + Main_DirectDraw_GetScanLine, + Main_DirectDraw_GetVerticalBlankStatus, + Main_DirectDraw_Initialize, + XF86DGA2_DirectDraw_RestoreDisplayMode, + Main_DirectDraw_SetCooperativeLevel, + XF86DGA2_DirectDraw_SetDisplayMode, + Main_DirectDraw_WaitForVerticalBlank, + Main_DirectDraw_GetAvailableVidMem, + Main_DirectDraw_GetSurfaceFromDC, + Main_DirectDraw_RestoreAllSurfaces, + Main_DirectDraw_TestCooperativeLevel, + XF86DGA2_DirectDraw_GetDeviceIdentifier, + Main_DirectDraw_StartModeTest, + Main_DirectDraw_EvaluateMode }; -#if !defined(__STRICT_ANSI__) && defined(__GNUC__) -# define XCAST(fun) (typeof(dga2_dd4vt.fn##fun)) -#else -# define XCAST(fun) (void*) -#endif - -ICOM_VTABLE(IDirectDraw4) dga2_dd4vt = -{ - ICOM_MSVTABLE_COMPAT_DummyRTTIVALUE - XCAST(QueryInterface)DGA_IDirectDraw2Impl_QueryInterface, - XCAST(AddRef)IDirectDraw2Impl_AddRef, - XCAST(Release)DGA2_IDirectDraw2Impl_Release, - XCAST(Compact)IDirectDraw2Impl_Compact, - XCAST(CreateClipper)IDirectDraw2Impl_CreateClipper, - XCAST(CreatePalette)DGA2_IDirectDraw2Impl_CreatePalette, - XCAST(CreateSurface)DGA2_IDirectDraw2Impl_CreateSurface, - XCAST(DuplicateSurface)IDirectDraw2Impl_DuplicateSurface, - XCAST(EnumDisplayModes)DGA2_IDirectDraw2Impl_EnumDisplayModes, - XCAST(EnumSurfaces)IDirectDraw2Impl_EnumSurfaces, - XCAST(FlipToGDISurface)IDirectDraw2Impl_FlipToGDISurface, - XCAST(GetCaps)DGA_IDirectDraw2Impl_GetCaps, - XCAST(GetDisplayMode)DGA_IDirectDraw2Impl_GetDisplayMode, - XCAST(GetFourCCCodes)IDirectDraw2Impl_GetFourCCCodes, - XCAST(GetGDISurface)IDirectDraw2Impl_GetGDISurface, - XCAST(GetMonitorFrequency)IDirectDraw2Impl_GetMonitorFrequency, - XCAST(GetScanLine)IDirectDraw2Impl_GetScanLine, - XCAST(GetVerticalBlankStatus)IDirectDraw2Impl_GetVerticalBlankStatus, - XCAST(Initialize)IDirectDraw2Impl_Initialize, - XCAST(RestoreDisplayMode)DGA2_IDirectDraw2Impl_RestoreDisplayMode, - XCAST(SetCooperativeLevel)DGA2_IDirectDraw2Impl_SetCooperativeLevel, - XCAST(SetDisplayMode)DGA2_IDirectDrawImpl_SetDisplayMode, - XCAST(WaitForVerticalBlank)IDirectDraw2Impl_WaitForVerticalBlank, - XCAST(GetAvailableVidMem)DGA_IDirectDraw2Impl_GetAvailableVidMem, - IDirectDraw4Impl_GetSurfaceFromDC, - IDirectDraw4Impl_RestoreAllSurfaces, - IDirectDraw4Impl_TestCooperativeLevel, - IDirectDraw4Impl_GetDeviceIdentifier -}; -#undef XCAST +#endif /* HAVE_LIBXXF86DGA2 */ diff --git a/dlls/ddraw/ddraw/dga2.h b/dlls/ddraw/ddraw/dga2.h new file mode 100644 index 00000000000..3dd6b838da7 --- /dev/null +++ b/dlls/ddraw/ddraw/dga2.h @@ -0,0 +1,48 @@ +/* Copyright 2000 TransGaming Technologies, Inc. */ +#ifndef WINE_DDRAW_DDRAW_DGA2_H_INCLUDED +#define WINE_DDRAW_DDRAW_DGA2_H_INCLUDED + +#include + +#define XF86DGA2_DDRAW_PRIV(ddraw) \ + ((XF86DGA2_DirectDrawImpl*)((ddraw)->private)) +#define XF86DGA2_DDRAW_PRIV_VAR(name,ddraw) \ + XF86DGA2_DirectDrawImpl* name = XF86DGA2_DDRAW_PRIV(ddraw) + +typedef struct +{ + XDGADevice* current_mode; + DWORD next_vofs; +} XF86DGA2_DirectDrawImpl_Part; + +typedef struct +{ + User_DirectDrawImpl_Part user; + XF86DGA2_DirectDrawImpl_Part xf86dga2; +} XF86DGA2_DirectDrawImpl; + +void XF86DGA2_DirectDraw_final_release(IDirectDrawImpl* This); +HRESULT XF86DGA2_DirectDraw_create_primary(IDirectDrawImpl* This, + const DDSURFACEDESC2* pDDSD, + LPDIRECTDRAWSURFACE7* ppSurf, + LPUNKNOWN pOuter); +HRESULT XF86DGA2_DirectDraw_create_backbuffer(IDirectDrawImpl* This, + const DDSURFACEDESC2* pDDSD, + LPDIRECTDRAWSURFACE7* ppSurf, + LPUNKNOWN pOuter, + IDirectDrawSurfaceImpl* primary); +HRESULT XF86DGA2_DirectDraw_Construct(IDirectDrawImpl *This, BOOL ex); +HRESULT XF86DGA2_DirectDraw_Create(const GUID* pGUID, LPDIRECTDRAW7* pIface, + IUnknown* pUnkOuter, BOOL ex); +HRESULT WINAPI +XF86DGA2_DirectDraw_GetDeviceIdentifier(LPDIRECTDRAW7 iface, + LPDDDEVICEIDENTIFIER2 pDDDI, + DWORD dwFlags); +HRESULT WINAPI +XF86DGA2_DirectDraw_SetDisplayMode(LPDIRECTDRAW7 iface, DWORD dwWidth, + DWORD dwHeight, DWORD dwBPP, + DWORD dwRefreshRate, DWORD dwFlags); +HRESULT WINAPI +XF86DGA2_DirectDraw_RestoreDisplayMode(LPDIRECTDRAW7 iface); + +#endif diff --git a/dlls/ddraw/ddraw/main.c b/dlls/ddraw/ddraw/main.c index 8becc21d40f..6ef31b91196 100644 --- a/dlls/ddraw/ddraw/main.c +++ b/dlls/ddraw/ddraw/main.c @@ -2,476 +2,989 @@ * * Copyright 1997-2000 Marcus Meissner * Copyright 1998-2000 Lionel Ulmer (most of Direct3D stuff) + * Copyright 2000 TransGaming Technologies Inc. */ /* * This file contains all the interface functions that are shared between - * all interfaces. Or better, it is a "common stub" library for the IDirectDraw* - * objects + * all interfaces. Or better, it is a "common stub" library for the + * IDirectDraw* objects */ #include "config.h" #include -#include -#include #include -#include #include "winerror.h" #include "ddraw.h" #include "d3d.h" #include "debugtools.h" #include "options.h" +#include "bitmap.h" + +#include "ddraw_private.h" +#include "ddraw/main.h" +#include "dclipper/main.h" +#include "dpalette/main.h" +#include "dsurface/main.h" +#include "dsurface/dib.h" +#include "dsurface/fakezbuffer.h" +#include "dsurface/dibtexture.h" DEFAULT_DEBUG_CHANNEL(ddraw); -#include "ddraw_private.h" +extern ICOM_VTABLE(IDirectDraw) DDRAW_IDirectDraw_VTable; +extern ICOM_VTABLE(IDirectDraw2) DDRAW_IDirectDraw2_VTable; +extern ICOM_VTABLE(IDirectDraw4) DDRAW_IDirectDraw4_VTable; + +static void DDRAW_UnsubclassWindow(IDirectDrawImpl* This); + +static void Main_DirectDraw_DeleteSurfaces(IDirectDrawImpl* This); +static void Main_DirectDraw_DeleteClippers(IDirectDrawImpl* This); +static void Main_DirectDraw_DeletePalettes(IDirectDrawImpl* This); +static void LosePrimarySurface(IDirectDrawImpl* This); + +static const char ddProp[] = "WINE_DDRAW_Property"; + +/* Not called from the vtable. */ +HRESULT Main_DirectDraw_Construct(IDirectDrawImpl *This, BOOL ex) +{ + /* NOTE: The creator must use HEAP_ZERO_MEMORY or equivalent. */ + This->ref = 1; + This->ex = ex; + + This->final_release = Main_DirectDraw_final_release; + + This->create_palette = Main_DirectDrawPalette_Create; + + This->create_offscreen = Main_create_offscreen; + This->create_texture = Main_create_texture; + This->create_zbuffer = Main_create_zbuffer; + /* There are no generic versions of create_{primary,backbuffer}. */ + + ICOM_INIT_INTERFACE(This, IDirectDraw, DDRAW_IDirectDraw_VTable); + ICOM_INIT_INTERFACE(This, IDirectDraw2, DDRAW_IDirectDraw2_VTable); + ICOM_INIT_INTERFACE(This, IDirectDraw4, DDRAW_IDirectDraw4_VTable); + /* There is no generic implementation of IDD7 */ -HRESULT WINAPI IDirectDraw2Impl_DuplicateSurface( - LPDIRECTDRAW2 iface,LPDIRECTDRAWSURFACE src,LPDIRECTDRAWSURFACE *dst -) { - ICOM_THIS(IDirectDraw2Impl,iface); - FIXME("(%p)->(%p,%p) simply copies\n",This,src,dst); - *dst = src; /* FIXME */ return DD_OK; } -HRESULT WINAPI IDirectDraw2Impl_SetCooperativeLevel( - LPDIRECTDRAW2 iface,HWND hwnd,DWORD cooplevel -) { - ICOM_THIS(IDirectDraw2Impl,iface); - - FIXME("(%p)->(%08lx,%08lx)\n",This,(DWORD)hwnd,cooplevel); - _dump_cooperativelevel(cooplevel); - This->d->mainWindow = hwnd; - return DD_OK; -} - -/* - * Small helper to either use the cooperative window or create a new - * one (for mouse and keyboard input) and drawing in the Xlib implementation. - * - * Note this just uses USER calls, so it is safe in here. - */ -void _common_IDirectDrawImpl_SetDisplayMode(IDirectDrawImpl* This) { - RECT rect; - - /* Do destroy only our window */ - if (This->d->window && GetPropA(This->d->window,ddProp)) { - DestroyWindow(This->d->window); - This->d->window = 0; +void Main_DirectDraw_final_release(IDirectDrawImpl* This) +{ + if (IsWindow(This->window)) + { + if (GetPropA(This->window, ddProp)) + DDRAW_UnsubclassWindow(This); + else + FIXME("this shouldn't happen, right?\n"); } - /* Sanity check cooperative window before assigning it to drawing. */ - if (IsWindow(This->d->mainWindow) && - IsWindowVisible(This->d->mainWindow) - ) { - GetWindowRect(This->d->mainWindow,&rect); - if ((((rect.right-rect.left) >= This->d->width) && - ((rect.bottom-rect.top) >= This->d->height)) - ) { - This->d->window = This->d->mainWindow; - /* FIXME: resizing is not windows compatible behaviour, need test */ - /* SetWindowPos(This->d->mainWindow,HWND_TOPMOST,0,0,This->d->width,This->d->height,SWP_NOMOVE|SWP_NOACTIVATE|SWP_NOOWNERZORDER); */ - This->d->paintable = 1; /* don't wait for WM_PAINT */ - } - } - /* ... failed, create new one. */ - if (!This->d->window) { - This->d->window = CreateWindowExA( - 0, - "WINE_DirectDraw", - "WINE_DirectDraw", - WS_POPUP, - 0,0, - This->d->width, - This->d->height, - 0, - 0, - 0, - NULL - ); - /*Store THIS with the window. We'll use it in the window procedure*/ - SetPropA(This->d->window,ddProp,(LONG)This); - ShowWindow(This->d->window,TRUE); - UpdateWindow(This->d->window); - } - SetFocus(This->d->window); + + Main_DirectDraw_DeleteSurfaces(This); + Main_DirectDraw_DeleteClippers(This); + Main_DirectDraw_DeletePalettes(This); } -HRESULT WINAPI IDirectDrawImpl_SetDisplayMode( - LPDIRECTDRAW iface,DWORD width,DWORD height,DWORD depth -) { - ICOM_THIS(IDirectDrawImpl,iface); +/* There is no Main_DirectDraw_Create. */ - FIXME("(%p)->SetDisplayMode(%ld,%ld,%ld), needs to be implemented for your display adapter!\n",This,width,height,depth); - This->d->width = width; - This->d->height = height; - _common_IDirectDrawImpl_SetDisplayMode(This); - return DD_OK; -} - -static void fill_caps(LPDDCAPS caps) { - /* This function tries to fill the capabilities of Wines DDraw - * implementation. Needs to be fixed, though.. */ - if (caps == NULL) - return; - - caps->dwSize = sizeof(*caps); - caps->dwCaps = DDCAPS_ALPHA | DDCAPS_BLT | DDCAPS_BLTSTRETCH | DDCAPS_BLTCOLORFILL | DDCAPS_BLTDEPTHFILL | DDCAPS_CANBLTSYSMEM | DDCAPS_COLORKEY | DDCAPS_PALETTE /*| DDCAPS_NOHARDWARE*/; - caps->dwCaps2 = DDCAPS2_CERTIFIED | DDCAPS2_NOPAGELOCKREQUIRED | DDCAPS2_WIDESURFACES; - caps->dwCKeyCaps = 0xFFFFFFFF; /* Should put real caps here one day... */ - caps->dwFXCaps = 0; - caps->dwFXAlphaCaps = 0; - caps->dwPalCaps = DDPCAPS_8BIT | DDPCAPS_ALLOW256; - caps->dwSVCaps = 0; - caps->dwZBufferBitDepths = DDBD_16; - /* I put here 8 Mo so that D3D applications will believe they have enough - * memory to put textures in video memory. BTW, is this only frame buffer - * memory or also texture memory (for Voodoo boards for example) ? - */ - caps->dwVidMemTotal = 8192 * 1024; - caps->dwVidMemFree = 8192 * 1024; - /* These are all the supported capabilities of the surfaces */ - caps->ddsCaps.dwCaps = DDSCAPS_ALPHA | DDSCAPS_BACKBUFFER | DDSCAPS_COMPLEX | DDSCAPS_FLIP | - DDSCAPS_FRONTBUFFER | DDSCAPS_LOCALVIDMEM | DDSCAPS_NONLOCALVIDMEM | DDSCAPS_OFFSCREENPLAIN | - /*DDSCAPS_OVERLAY |*/ DDSCAPS_PALETTE | DDSCAPS_PRIMARYSURFACE | DDSCAPS_SYSTEMMEMORY | - DDSCAPS_VIDEOMEMORY | DDSCAPS_VISIBLE; -} - -HRESULT WINAPI IDirectDraw2Impl_GetCaps( - LPDIRECTDRAW2 iface,LPDDCAPS caps1,LPDDCAPS caps2 -) { - ICOM_THIS(IDirectDraw2Impl,iface); - TRACE("(%p)->GetCaps(%p,%p)\n",This,caps1,caps2); - - /* Put the same caps for the two capabilities */ - fill_caps(caps1); - fill_caps(caps2); - - return DD_OK; -} - -HRESULT WINAPI IDirectDraw2Impl_CreateClipper( - LPDIRECTDRAW2 iface,DWORD x,LPDIRECTDRAWCLIPPER *lpddclip,LPUNKNOWN lpunk -) { - ICOM_THIS(IDirectDraw2Impl,iface); - IDirectDrawClipperImpl** ilpddclip=(IDirectDrawClipperImpl**)lpddclip; - FIXME("(%p)->(%08lx,%p,%p),stub!\n", This,x,ilpddclip,lpunk); - *ilpddclip = (IDirectDrawClipperImpl*)HeapAlloc(GetProcessHeap(),HEAP_ZERO_MEMORY,sizeof(IDirectDrawClipperImpl)); - (*ilpddclip)->ref = 1; - ICOM_VTBL(*ilpddclip) = &ddclipvt; - return DD_OK; -} - -HRESULT WINAPI common_IDirectDraw2Impl_CreatePalette( - IDirectDraw2Impl* This,DWORD dwFlags,LPPALETTEENTRY palent, - IDirectDrawPaletteImpl **lpddpal,LPUNKNOWN lpunk,int *psize -) { - int size = 0; - - if (TRACE_ON(ddraw)) - _dump_paletteformat(dwFlags); - - *lpddpal = (IDirectDrawPaletteImpl*)HeapAlloc(GetProcessHeap(),HEAP_ZERO_MEMORY,sizeof(IDirectDrawPaletteImpl)); - if (*lpddpal == NULL) return E_OUTOFMEMORY; - (*lpddpal)->ref = 1; - (*lpddpal)->ddraw = (IDirectDrawImpl*)This; - - if (dwFlags & DDPCAPS_1BIT) - size = 2; - else if (dwFlags & DDPCAPS_2BIT) - size = 4; - else if (dwFlags & DDPCAPS_4BIT) - size = 16; - else if (dwFlags & DDPCAPS_8BIT) - size = 256; - else - ERR("unhandled palette format\n"); - - *psize = size; - if (This->d->palette_convert == NULL) { - /* No depth conversion - create 8<->8 identity map */ - int ent; - for (ent=0; ent<256; ent++) - (*lpddpal)->screen_palents[ent] = ent; - } - if (palent) { - /* Now, if we are in depth conversion mode, create the screen palette */ - if (This->d->palette_convert != NULL) - This->d->palette_convert(palent,(*lpddpal)->screen_palents,0,size); - - memcpy((*lpddpal)->palents, palent, size * sizeof(PALETTEENTRY)); - } else if (This->d->palette_convert != NULL) { - /* In that case, put all 0xFF */ - memset((*lpddpal)->screen_palents, 0xFF, 256 * sizeof(int)); - } - return DD_OK; -} - -HRESULT WINAPI IDirectDraw2Impl_CreatePalette( - LPDIRECTDRAW2 iface,DWORD dwFlags,LPPALETTEENTRY palent,LPDIRECTDRAWPALETTE *lpddpal,LPUNKNOWN lpunk -) { - ICOM_THIS(IDirectDraw2Impl,iface); - IDirectDrawPaletteImpl** ilpddpal=(IDirectDrawPaletteImpl**)lpddpal; - int xsize; - HRESULT res; - - TRACE("(%p)->(%08lx,%p,%p,%p)\n",This,dwFlags,palent,ilpddpal,lpunk); - res = common_IDirectDraw2Impl_CreatePalette(This,dwFlags,palent,ilpddpal,lpunk,&xsize); - if (res != 0) return res; - ICOM_VTBL(*ilpddpal) = &ddraw_ddpalvt; - return DD_OK; -} - -HRESULT WINAPI IDirectDraw2Impl_RestoreDisplayMode(LPDIRECTDRAW2 iface) { - ICOM_THIS(IDirectDraw2Impl,iface); - TRACE("(%p)->RestoreDisplayMode()\n", This); - Sleep(1000); - return DD_OK; -} - -HRESULT WINAPI IDirectDraw2Impl_WaitForVerticalBlank( - LPDIRECTDRAW2 iface,DWORD x,HANDLE h -) { - ICOM_THIS(IDirectDraw2Impl,iface); - FIXME("(%p)->(flags=0x%08lx,handle=0x%08x)\n",This,x,h); - return DD_OK; -} - -ULONG WINAPI IDirectDraw2Impl_AddRef(LPDIRECTDRAW2 iface) { - ICOM_THIS(IDirectDraw2Impl,iface); +ULONG WINAPI Main_DirectDraw_AddRef(LPDIRECTDRAW7 iface) { + ICOM_THIS(IDirectDrawImpl,iface); TRACE("(%p)->() incrementing from %lu.\n", This, This->ref ); - return ++(This->ref); + return ++This->ref; } -ULONG WINAPI IDirectDraw2Impl_Release(LPDIRECTDRAW2 iface) { - ICOM_THIS(IDirectDraw2Impl,iface); +ULONG WINAPI Main_DirectDraw_Release(LPDIRECTDRAW7 iface) { + ULONG ref; + ICOM_THIS(IDirectDrawImpl,iface); TRACE("(%p)->() decrementing from %lu.\n", This, This->ref ); - if (!--(This->ref)) { - if (!--(This->d->ref)) { - if (This->d->window && GetPropA(This->d->window,ddProp)) - DestroyWindow(This->d->window); - HeapFree(GetProcessHeap(),0,This->d); - } - HeapFree(GetProcessHeap(),0,This); - return S_OK; + ref = --This->ref; + + if (ref == 0) + { + if (This->final_release != NULL) + This->final_release(This); + + /* We free the private. This is an artifact of the fact that I don't + * have the destructors set up correctly. */ + if (This->private != (This+1)) + HeapFree(GetProcessHeap(), 0, This->private); + + HeapFree(GetProcessHeap(), 0, This); } - return This->ref; + + return ref; } -HRESULT WINAPI IDirectDraw2Impl_QueryInterface( - LPDIRECTDRAW2 iface,REFIID refiid,LPVOID *obj +/* TODO: need to support IDirect3D. */ +HRESULT WINAPI Main_DirectDraw_QueryInterface( + LPDIRECTDRAW7 iface,REFIID refiid,LPVOID *obj ) { - ICOM_THIS(IDirectDraw2Impl,iface); + ICOM_THIS(IDirectDrawImpl,iface); + TRACE("(%p)->(%s,%p)\n", This, debugstr_guid(refiid), obj); - if ( IsEqualGUID( &IID_IUnknown, refiid ) ) { - *obj = This; - IDirectDraw2_AddRef(iface); - TRACE(" Creating IUnknown interface (%p)\n", *obj); - return S_OK; + if ( IsEqualGUID( &IID_IUnknown, refiid ) + || IsEqualGUID( &IID_IDirectDraw7, refiid ) ) + { + *obj = ICOM_INTERFACE(This, IDirectDraw7); } - ERR("(%p)->(%s,%p), must be implemented by display interface!\n",This,debugstr_guid(refiid),obj); - return OLE_E_ENUM_NOMORE; + else if ( IsEqualGUID( &IID_IDirectDraw, refiid ) ) + { + *obj = ICOM_INTERFACE(This, IDirectDraw); + } + else if ( IsEqualGUID( &IID_IDirectDraw2, refiid ) ) + { + *obj = ICOM_INTERFACE(This, IDirectDraw2); + } + else if ( IsEqualGUID( &IID_IDirectDraw4, refiid ) ) + { + *obj = ICOM_INTERFACE(This, IDirectDraw4); + } +#ifdef HAVE_OPENGL + else if ( IsEqualGUID( &IID_IDirect3D3, refiid ) ) + { + return create_direct3d3(obj, This); + } + else if ( IsEqualGUID( &IID_IDirect3D2, refiid ) ) + { + return create_direct3d2(obj, This); + } + else if ( IsEqualGUID( &IID_IDirect3D, refiid ) ) + { + return create_direct3d(obj, This); + } +#endif + else + { + FIXME("(%p)->(%s,%p): no interface\n",This,debugstr_guid(refiid),obj); + return E_NOINTERFACE; + } + + IDirectDraw7_AddRef(iface); + return S_OK; } -HRESULT WINAPI IDirectDraw2Impl_GetVerticalBlankStatus( - LPDIRECTDRAW2 iface,BOOL *status -) { - ICOM_THIS(IDirectDraw2Impl,iface); - TRACE("(%p)->(%p)\n",This,status); - *status = TRUE; +/* MSDN: "not currently implemented". */ +HRESULT WINAPI Main_DirectDraw_Compact(LPDIRECTDRAW7 iface) +{ + TRACE("(%p)\n", iface); + return DD_OK; } -HRESULT WINAPI IDirectDraw2Impl_EnumDisplayModes( - LPDIRECTDRAW2 iface,DWORD dwFlags,LPDDSURFACEDESC lpddsfd,LPVOID context, - LPDDENUMMODESCALLBACK modescb -) { - ICOM_THIS(IDirectDraw2Impl,iface); - DDSURFACEDESC ddsfd; - static struct { - int w,h; - } modes[5] = { /* some of the usual modes */ - {512,384}, - {640,400}, - {640,480}, - {800,600}, - {1024,768}, +HRESULT WINAPI Main_DirectDraw_CreateClipper(LPDIRECTDRAW7 iface, + DWORD dwFlags, + LPDIRECTDRAWCLIPPER *ppClipper, + IUnknown *pUnkOuter) +{ + ICOM_THIS(IDirectDrawImpl, iface); + HRESULT hr; + + TRACE("(%p)->(0x%lx, %p, %p)\n", iface, dwFlags, ppClipper, pUnkOuter); + + hr = DirectDrawCreateClipper(dwFlags, ppClipper, pUnkOuter); + if (FAILED(hr)) return hr; + + /* dwFlags is passed twice, apparently an API wart. */ + hr = IDirectDrawClipper_Initialize(*ppClipper, + ICOM_INTERFACE(This, IDirectDraw), + dwFlags); + if (FAILED(hr)) + { + IDirectDrawClipper_Release(*ppClipper); + return hr; + } + + return DD_OK; +} + +HRESULT WINAPI +Main_DirectDraw_CreatePalette(LPDIRECTDRAW7 iface, DWORD dwFlags, + LPPALETTEENTRY palent, + LPDIRECTDRAWPALETTE* ppPalette, + LPUNKNOWN pUnknown) +{ + ICOM_THIS(IDirectDrawImpl,iface); + LPDIRECTDRAWPALETTE pPalette; + HRESULT hr; + + TRACE("(%p)->(%08lx,%p,%p,%p)\n",This,dwFlags,palent,ppPalette,pUnknown); + + if (ppPalette == NULL) return E_POINTER; /* unchecked */ + if (pUnknown != NULL) return CLASS_E_NOAGGREGATION; /* unchecked */ + + hr = This->create_palette(This, dwFlags, &pPalette, pUnknown); + if (FAILED(hr)) return hr; + + hr = IDirectDrawPalette_SetEntries(pPalette, 0, 0, + Main_DirectDrawPalette_Size(dwFlags), + palent); + if (FAILED(hr)) + { + IDirectDrawPalette_Release(pPalette); + return hr; + } + else + { + *ppPalette = pPalette; + return DD_OK; + } +} + +HRESULT +Main_create_offscreen(IDirectDrawImpl* This, const DDSURFACEDESC2* pDDSD, + LPDIRECTDRAWSURFACE7* ppSurf, LPUNKNOWN pOuter) +{ + assert(pOuter == NULL); + + return DIB_DirectDrawSurface_Create(This, pDDSD, ppSurf, pOuter); +} + +HRESULT +Main_create_texture(IDirectDrawImpl* This, const DDSURFACEDESC2* pDDSD, + LPDIRECTDRAWSURFACE7* ppSurf, LPUNKNOWN pOuter, + DWORD dwMipMapLevel) +{ + assert(pOuter == NULL); + + return DIBTexture_DirectDrawSurface_Create(This, pDDSD, ppSurf, pOuter); +} + +HRESULT +Main_create_zbuffer(IDirectDrawImpl* This, const DDSURFACEDESC2* pDDSD, + LPDIRECTDRAWSURFACE7* ppSurf, LPUNKNOWN pOuter) +{ + assert(pOuter == NULL); + + return FakeZBuffer_DirectDrawSurface_Create(This, pDDSD, ppSurf, pOuter); +} + +/* Does the texture surface described in pDDSD have any smaller mipmaps? */ +static BOOL more_mipmaps(const DDSURFACEDESC2 *pDDSD) +{ + return ((pDDSD->dwFlags & DDSD_MIPMAPCOUNT) && pDDSD->u2.dwMipMapCount > 1 + && (pDDSD->dwWidth > 1 || pDDSD->dwHeight > 1)); +} + +/* Create a texture surface along with any of its mipmaps. */ +static HRESULT +create_texture(IDirectDrawImpl* This, const DDSURFACEDESC2 *pDDSD, + LPDIRECTDRAWSURFACE7* ppSurf, LPUNKNOWN pUnkOuter) +{ + DDSURFACEDESC2 ddsd; + DWORD mipmap_level = 0; + HRESULT hr; + + assert(pUnkOuter == NULL); + + /* is this check right? (pixelformat can be copied from primary) */ + if ((pDDSD->dwFlags&(DDSD_HEIGHT|DDSD_WIDTH)) != (DDSD_HEIGHT|DDSD_WIDTH)) + return DDERR_INVALIDPARAMS; + + ddsd = *pDDSD; + + if (!(ddsd.dwFlags & DDSD_PIXELFORMAT)) + { + ddsd.u4.ddpfPixelFormat = This->pixelformat; + } + + if (!(ddsd.dwFlags & DDSD_PITCH)) + { + ddsd.u1.lPitch = DDRAW_width_bpp_to_pitch(ddsd.dwWidth, + GET_BPP(ddsd)*8); + } + + ddsd.dwFlags |= DDSD_PITCH | DDSD_PIXELFORMAT; + + hr = This->create_texture(This, &ddsd, ppSurf, pUnkOuter, mipmap_level); + if (FAILED(hr)) return hr; + + /* Create attached mipmaps if required. */ + if (more_mipmaps(&ddsd)) + { + LPDIRECTDRAWSURFACE7 mipmap; + LPDIRECTDRAWSURFACE7 prev_mipmap; + DDSURFACEDESC2 mipmap_surface_desc; + + prev_mipmap = *ppSurf; + IDirectDrawSurface7_AddRef(prev_mipmap); + mipmap_surface_desc = ddsd; + + while (more_mipmaps(&mipmap_surface_desc)) + { + mipmap_level++; + + mipmap_surface_desc.u2.dwMipMapCount--; + + if (mipmap_surface_desc.dwWidth > 1) + mipmap_surface_desc.dwWidth /= 2; + + if (mipmap_surface_desc.dwHeight > 1) + mipmap_surface_desc.dwHeight /= 2; + + mipmap_surface_desc.u1.lPitch + = DDRAW_width_bpp_to_pitch(mipmap_surface_desc.dwWidth, + GET_BPP(ddsd)*8); + + hr = This->create_texture(This, &mipmap_surface_desc, &mipmap, + pUnkOuter, mipmap_level); + if (FAILED(hr)) + { + IDirectDrawSurface7_Release(prev_mipmap); + IDirectDrawSurface7_Release(*ppSurf); + return hr; + } + + IDirectDrawSurface7_AddAttachedSurface(prev_mipmap, mipmap); + IDirectDrawSurface7_Release(prev_mipmap); + prev_mipmap = mipmap; + } + + IDirectDrawSurface7_Release(prev_mipmap); + } + + return DD_OK; +} + +/* Creates a primary surface and any indicated backbuffers. */ +static HRESULT +create_primary(IDirectDrawImpl* This, LPDDSURFACEDESC2 pDDSD, + LPDIRECTDRAWSURFACE7* ppSurf, LPUNKNOWN pUnkOuter) +{ + DDSURFACEDESC2 ddsd; + HRESULT hr; + + assert(pUnkOuter == NULL); + + if (This->primary_surface != NULL) + return DDERR_PRIMARYSURFACEALREADYEXISTS; + + /* as documented (what about pitch?) */ + if (pDDSD->dwFlags & (DDSD_HEIGHT|DDSD_WIDTH|DDSD_PIXELFORMAT)) + return DDERR_INVALIDPARAMS; + + ddsd = *pDDSD; + ddsd.dwFlags |= DDSD_HEIGHT | DDSD_WIDTH | DDSD_PITCH | DDSD_PIXELFORMAT; + ddsd.dwHeight = This->height; + ddsd.dwWidth = This->width; + ddsd.u1.lPitch = This->pitch; + ddsd.u4.ddpfPixelFormat = This->pixelformat; + ddsd.ddsCaps.dwCaps |= DDSCAPS_LOCALVIDMEM | DDSCAPS_VIDEOMEMORY + | DDSCAPS_VISIBLE | DDSCAPS_FRONTBUFFER; + + if ((ddsd.dwFlags & DDSD_BACKBUFFERCOUNT) && ddsd.dwBackBufferCount > 0) + ddsd.ddsCaps.dwCaps |= DDSCAPS_FLIP; + + hr = This->create_primary(This, &ddsd, ppSurf, pUnkOuter); + if (FAILED(hr)) return hr; + + if (ddsd.dwFlags & DDSD_BACKBUFFERCOUNT) + { + IDirectDrawSurfaceImpl* primary; + LPDIRECTDRAWSURFACE7 pPrev; + DWORD i; + + ddsd.dwFlags &= ~DDSD_BACKBUFFERCOUNT; + ddsd.ddsCaps.dwCaps &= ~(DDSCAPS_VISIBLE | DDSCAPS_PRIMARYSURFACE + | DDSCAPS_BACKBUFFER); + + primary = ICOM_OBJECT(IDirectDrawSurfaceImpl,IDirectDrawSurface7, + *ppSurf); + pPrev = *ppSurf; + IDirectDrawSurface7_AddRef(pPrev); + + for (i=0; i < ddsd.dwBackBufferCount; i++) + { + LPDIRECTDRAWSURFACE7 pBack; + + if (i == 0) + ddsd.ddsCaps.dwCaps |= DDSCAPS_BACKBUFFER; + else + ddsd.ddsCaps.dwCaps &= ~DDSCAPS_BACKBUFFER; + + hr = This->create_backbuffer(This, &ddsd, &pBack, pUnkOuter, + primary); + + if (FAILED(hr)) + { + IDirectDraw7_Release(pPrev); + IDirectDraw7_Release(*ppSurf); + return hr; + } + + IDirectDrawSurface7_AddAttachedSurface(pPrev, pBack); + IDirectDrawSurface7_Release(pPrev); + pPrev = pBack; + } + + IDirectDrawSurface7_Release(pPrev); + } + + This->primary_surface = *ppSurf; + + return DD_OK; +} + +static HRESULT +create_offscreen(IDirectDrawImpl* This, LPDDSURFACEDESC2 pDDSD, + LPDIRECTDRAWSURFACE7* ppSurf, LPUNKNOWN pUnkOuter) +{ + DDSURFACEDESC2 ddsd; + HRESULT hr; + + /* is this check right? (pixelformat can be copied from primary) */ + if ((pDDSD->dwFlags&(DDSD_HEIGHT|DDSD_WIDTH)) != (DDSD_HEIGHT|DDSD_WIDTH)) + return DDERR_INVALIDPARAMS; + + ddsd = *pDDSD; + + if (!(ddsd.dwFlags & DDSD_PIXELFORMAT)) + { + ddsd.u4.ddpfPixelFormat = This->pixelformat; + } + + if (!(ddsd.dwFlags & DDSD_PITCH)) + { + ddsd.u1.lPitch = DDRAW_width_bpp_to_pitch(ddsd.dwWidth, + GET_BPP(ddsd)*8); + } + + ddsd.dwFlags |= DDSD_PITCH | DDSD_PIXELFORMAT; + + hr = This->create_offscreen(This, &ddsd, ppSurf, pUnkOuter); + if (FAILED(hr)) return hr; + + return hr; +} + +HRESULT WINAPI +Main_DirectDraw_CreateSurface(LPDIRECTDRAW7 iface, LPDDSURFACEDESC2 pDDSD, + LPDIRECTDRAWSURFACE7 *ppSurf, + IUnknown *pUnkOuter) +{ + HRESULT hr; + ICOM_THIS(IDirectDrawImpl, iface); + + TRACE("(%p)->(%p,%p,%p)\n",This,pDDSD,ppSurf,pUnkOuter); + TRACE("Requested Caps: 0x%x\n", pDDSD->ddsCaps.dwCaps); + + if (pUnkOuter != NULL) + return CLASS_E_NOAGGREGATION; /* unchecked */ + + if (!(pDDSD->dwFlags & DDSD_CAPS)) + return DDERR_INVALIDPARAMS; /* unchecked */ + + if (ppSurf == NULL) + return E_POINTER; /* unchecked */ + + if (pDDSD->ddsCaps.dwCaps & DDSCAPS_PRIMARYSURFACE) + { + /* create primary surface & backbuffers */ + hr = create_primary(This, pDDSD, ppSurf, pUnkOuter); + } + else if (pDDSD->ddsCaps.dwCaps & DDSCAPS_BACKBUFFER) + { + /* create backbuffer surface */ + hr = This->create_backbuffer(This, pDDSD, ppSurf, pUnkOuter, NULL); + } + else if (pDDSD->ddsCaps.dwCaps & DDSCAPS_OFFSCREENPLAIN) + { + /* create offscreenplain surface */ + hr = create_offscreen(This, pDDSD, ppSurf, pUnkOuter); + } + else if (pDDSD->ddsCaps.dwCaps & DDSCAPS_ZBUFFER) + { + /* create z-buffer */ + hr = This->create_zbuffer(This, pDDSD, ppSurf, pUnkOuter); + } + else if (pDDSD->ddsCaps.dwCaps & DDSCAPS_TEXTURE) + { + /* create texture */ + hr = create_texture(This, pDDSD, ppSurf, pUnkOuter); + } + else + { + /* Otherwise, assume offscreenplain surface */ + FIXME("App didn't request a valid surface type - assuming offscreenplain\n"); + hr = create_offscreen(This, pDDSD, ppSurf, pUnkOuter); + } + + if (FAILED(hr)) return hr; + + return DD_OK; +} + +HRESULT WINAPI +Main_DirectDraw_DuplicateSurface(LPDIRECTDRAW7 iface, LPDIRECTDRAWSURFACE7 src, + LPDIRECTDRAWSURFACE7* dst) +{ + ICOM_THIS(IDirectDrawImpl,iface); + + IDirectDrawSurfaceImpl *pSrc = ICOM_OBJECT(IDirectDrawSurfaceImpl, + IDirectDrawSurface7, src); + + TRACE("(%p)->(%p,%p)\n",This,src,dst); + + return pSrc->duplicate_surface(pSrc, dst); +} + +/* EnumDisplayModes */ + +BOOL Main_DirectDraw_DDPIXELFORMAT_Match(const DDPIXELFORMAT *requested, + const DDPIXELFORMAT *provided) +{ + /* Some flags must be present in both or neither for a match. */ + static const DWORD must_match = DDPF_PALETTEINDEXED1 | DDPF_PALETTEINDEXED2 + | DDPF_PALETTEINDEXED4 | DDPF_PALETTEINDEXED8 | DDPF_FOURCC + | DDPF_ZBUFFER | DDPF_STENCILBUFFER; + + if ((requested->dwFlags & provided->dwFlags) != requested->dwFlags) + return FALSE; + + if ((requested->dwFlags & must_match) != (provided->dwFlags & must_match)) + return FALSE; + + if (requested->dwFlags & DDPF_FOURCC) + if (requested->dwFourCC != provided->dwFourCC) + return FALSE; + + if (requested->dwFlags & (DDPF_RGB|DDPF_YUV|DDPF_ZBUFFER|DDPF_ALPHA + |DDPF_LUMINANCE|DDPF_BUMPDUDV)) + if (requested->u1.dwRGBBitCount != provided->u1.dwRGBBitCount) + return FALSE; + + if (requested->dwFlags & (DDPF_RGB|DDPF_YUV|DDPF_STENCILBUFFER + |DDPF_LUMINANCE|DDPF_BUMPDUDV)) + if (requested->u2.dwRBitMask != provided->u2.dwRBitMask) + return FALSE; + + if (requested->dwFlags & (DDPF_RGB|DDPF_YUV|DDPF_ZBUFFER|DDPF_BUMPDUDV)) + if (requested->u3.dwGBitMask != provided->u3.dwGBitMask) + return FALSE; + + /* I could be wrong about the bumpmapping. MSDN docs are vague. */ + if (requested->dwFlags & (DDPF_RGB|DDPF_YUV|DDPF_STENCILBUFFER + |DDPF_BUMPDUDV)) + if (requested->u4.dwBBitMask != provided->u4.dwBBitMask) + return FALSE; + + if (requested->dwFlags & (DDPF_ALPHAPIXELS|DDPF_ZPIXELS)) + if (requested->u5.dwRGBAlphaBitMask != provided->u5.dwRGBAlphaBitMask) + return FALSE; + + return TRUE; +} + +BOOL Main_DirectDraw_DDSD_Match(const DDSURFACEDESC2* requested, + const DDSURFACEDESC2* provided) +{ + struct compare_info + { + DWORD flag; + ptrdiff_t offset; + size_t size; }; - static int depths[4] = {8,16,24,32}; - int i,j; - TRACE("(%p)->(0x%08lx,%p,%p,%p)\n",This,dwFlags,lpddsfd,context,modescb); - ddsfd.dwSize = sizeof(ddsfd); - ddsfd.dwFlags = DDSD_HEIGHT|DDSD_WIDTH|DDSD_BACKBUFFERCOUNT|DDSD_PIXELFORMAT|DDSD_CAPS; - if (dwFlags & DDEDM_REFRESHRATES) { - ddsfd.dwFlags |= DDSD_REFRESHRATE; - ddsfd.u.dwRefreshRate = 60; +#define CMP(FLAG, FIELD) \ + { DDSD_##FLAG, offsetof(DDSURFACEDESC2, FIELD), \ + sizeof(((DDSURFACEDESC2 *)(NULL))->FIELD) } + + static const struct compare_info compare[] = { + CMP(ALPHABITDEPTH, dwAlphaBitDepth), + CMP(BACKBUFFERCOUNT, dwBackBufferCount), + CMP(CAPS, ddsCaps), + CMP(CKDESTBLT, ddckCKDestBlt), + CMP(CKDESTOVERLAY, u3.ddckCKDestOverlay), + CMP(CKSRCBLT, ddckCKSrcBlt), + CMP(CKSRCOVERLAY, ddckCKSrcOverlay), + CMP(HEIGHT, dwHeight), + CMP(LINEARSIZE, u1.dwLinearSize), + CMP(LPSURFACE, lpSurface), + CMP(MIPMAPCOUNT, u2.dwMipMapCount), + CMP(PITCH, u1.lPitch), + /* PIXELFORMAT: manual */ + CMP(REFRESHRATE, u2.dwRefreshRate), + CMP(TEXTURESTAGE, dwTextureStage), + CMP(WIDTH, dwWidth), + /* ZBUFFERBITDEPTH: "obsolete" */ + }; + +#undef CMP + + int i; + + if ((requested->dwFlags & provided->dwFlags) != requested->dwFlags) + return FALSE; + + for (i=0; i < sizeof(compare)/sizeof(compare[0]); i++) + { + if (requested->dwFlags & compare[i].flag + && memcmp((const char *)provided + compare[i].offset, + (const char *)requested + compare[i].offset, + compare[i].size) != 0) + return FALSE; } - ddsfd.ddsCaps.dwCaps = 0; - ddsfd.dwBackBufferCount = 1; - for (i=0;i 8 */ - if (depths[i]==8) { - ddsfd.ddpfPixelFormat.u1.dwRBitMask = 0; - ddsfd.ddpfPixelFormat.u2.dwGBitMask = 0; - ddsfd.ddpfPixelFormat.u3.dwBBitMask = 0; - ddsfd.ddpfPixelFormat.u4.dwRGBAlphaBitMask= 0; - ddsfd.ddsCaps.dwCaps=DDSCAPS_PALETTE; - ddsfd.ddpfPixelFormat.dwFlags|=DDPF_PALETTEINDEXED8; - } else { - ddsfd.ddpfPixelFormat.u4.dwRGBAlphaBitMask= 0; - - /* FIXME: We should query those from X itself */ - switch (depths[i]) { - case 16: - ddsfd.ddpfPixelFormat.u1.dwRBitMask = 0xF800; - ddsfd.ddpfPixelFormat.u2.dwGBitMask = 0x07E0; - ddsfd.ddpfPixelFormat.u3.dwBBitMask= 0x001F; - break; - case 24: - ddsfd.ddpfPixelFormat.u1.dwRBitMask = 0x00FF0000; - ddsfd.ddpfPixelFormat.u2.dwGBitMask = 0x0000FF00; - ddsfd.ddpfPixelFormat.u3.dwBBitMask= 0x000000FF; - break; - case 32: - ddsfd.ddpfPixelFormat.u1.dwRBitMask = 0x00FF0000; - ddsfd.ddpfPixelFormat.u2.dwGBitMask = 0x0000FF00; - ddsfd.ddpfPixelFormat.u3.dwBBitMask= 0x000000FF; - break; - } - } + if (requested->dwFlags & DDSD_PIXELFORMAT) + { + if (!Main_DirectDraw_DDPIXELFORMAT_Match(&requested->u4.ddpfPixelFormat, + &provided->u4.ddpfPixelFormat)) + return FALSE; + } - ddsfd.dwWidth = GetSystemMetrics(SM_CXSCREEN); - ddsfd.dwHeight = GetSystemMetrics(SM_CYSCREEN); - TRACE(" enumerating (%ldx%ldx%d)\n",ddsfd.dwWidth,ddsfd.dwHeight,depths[i]); - if (!modescb(&ddsfd,context)) return DD_OK; + return TRUE; +} - for (j=0;jsurfaces; surf != NULL; surf = surf->next_ddraw) + { + if (all + || (nomatch != Main_DirectDraw_DDSD_Match(lpDDSD2, + &surf->surface_desc))) + { + LPDIRECTDRAWSURFACE7 surface = ICOM_INTERFACE(surf, + IDirectDrawSurface7); + + /* BOGUS! Violates COM rules, but MSDN says so. */ + IDirectDrawSurface7_AddRef(surface); + + if (callback(surface, &surf->surface_desc, context) + == DDENUMRET_CANCEL) + break; } } + return DD_OK; } -HRESULT WINAPI IDirectDraw2Impl_GetDisplayMode( - LPDIRECTDRAW2 iface,LPDDSURFACEDESC lpddsfd -) { - ICOM_THIS(IDirectDraw2Impl,iface); - TRACE("(%p)->GetDisplayMode(%p)\n",This,lpddsfd); - lpddsfd->dwFlags = DDSD_HEIGHT|DDSD_WIDTH|DDSD_PITCH|DDSD_BACKBUFFERCOUNT|DDSD_PIXELFORMAT|DDSD_CAPS; - lpddsfd->dwHeight = This->d->height; - lpddsfd->dwWidth = This->d->width; - lpddsfd->lPitch =lpddsfd->dwWidth*PFGET_BPP(This->d->directdraw_pixelformat); - lpddsfd->dwBackBufferCount = 2; - lpddsfd->u.dwRefreshRate = 60; - lpddsfd->ddsCaps.dwCaps = DDSCAPS_PALETTE; - lpddsfd->ddpfPixelFormat = This->d->directdraw_pixelformat; - if (TRACE_ON(ddraw)) - _dump_surface_desc(lpddsfd); +/* I really don't understand how this is supposed to work. + * We only consider dwHeight, dwWidth and ddpfPixelFormat.dwFlags. */ +HRESULT +Main_DirectDraw_EnumCreateableSurfaces(IDirectDrawImpl *This, DWORD dwFlags, + LPDDSURFACEDESC2 lpDDSD2, + LPVOID context, + LPDDENUMSURFACESCALLBACK7 callback) +{ + FIXME("This isn't going to work.\n"); + + if ((dwFlags & DDENUMSURFACES_MATCHTYPE) != DDENUMSURFACES_MATCH) + return DDERR_INVALIDPARAMS; + + /* TODO: implement this. + * Does this work before SCL is called? + * Does it only consider off-screen surfaces? + */ + + return E_FAIL; +} + +/* For unsigned x. 0 is not a power of 2. */ +#define IS_POW_2(x) (((x) & ((x) - 1)) == 0) + +HRESULT WINAPI +Main_DirectDraw_EnumSurfaces(LPDIRECTDRAW7 iface, DWORD dwFlags, + LPDDSURFACEDESC2 lpDDSD2, LPVOID context, + LPDDENUMSURFACESCALLBACK7 callback) +{ + ICOM_THIS(IDirectDrawImpl, iface); + TRACE("(%p)->(0x%lx, %p, %p, %p)\n", iface, dwFlags, lpDDSD2, context, + callback); + + if (callback == NULL) + return DDERR_INVALIDPARAMS; + + if (dwFlags & ~(DDENUMSURFACES_SEARCHTYPE|DDENUMSURFACES_MATCHTYPE)) + return DDERR_INVALIDPARAMS; + + if (!IS_POW_2(dwFlags & DDENUMSURFACES_SEARCHTYPE) + || !IS_POW_2(dwFlags & DDENUMSURFACES_MATCHTYPE)) + return DDERR_INVALIDPARAMS; + + if (dwFlags & DDENUMSURFACES_DOESEXIST) + { + return Main_DirectDraw_EnumExistingSurfaces(This, dwFlags, lpDDSD2, + context, callback); + } + else + { + return Main_DirectDraw_EnumCreateableSurfaces(This, dwFlags, lpDDSD2, + context, callback); + } +} + +HRESULT WINAPI +Main_DirectDraw_EvaluateMode(LPDIRECTDRAW7 iface,DWORD a,DWORD* b) +{ + ICOM_THIS(IDirectDrawImpl,iface); + FIXME("(%p)->() stub\n", This); + return DD_OK; } -HRESULT WINAPI IDirectDraw2Impl_FlipToGDISurface(LPDIRECTDRAW2 iface) { - ICOM_THIS(IDirectDraw2Impl,iface); - FIXME("(%p)->()\n",This); +HRESULT WINAPI +Main_DirectDraw_FlipToGDISurface(LPDIRECTDRAW7 iface) +{ + ICOM_THIS(IDirectDrawImpl,iface); + TRACE("(%p)->()\n",This); return DD_OK; } -HRESULT WINAPI IDirectDraw2Impl_GetMonitorFrequency( - LPDIRECTDRAW2 iface,LPDWORD freq -) { - ICOM_THIS(IDirectDraw2Impl,iface); +/* GetCaps */ +/* GetDeviceIdentifier */ +/* GetDIsplayMode */ + +HRESULT WINAPI +Main_DirectDraw_GetFourCCCodes(LPDIRECTDRAW7 iface, LPDWORD pNumCodes, + LPDWORD pCodes) +{ + ICOM_THIS(IDirectDrawImpl,iface); + FIXME("(%p,%p,%p), stub\n",This,pNumCodes,pCodes); + return DD_OK; +} + +HRESULT WINAPI +Main_DirectDraw_GetGDISurface(LPDIRECTDRAW7 iface, + LPDIRECTDRAWSURFACE7 *lplpGDIDDSSurface) +{ + ICOM_THIS(IDirectDrawImpl,iface); + TRACE("(%p)->(%p)\n", This, lplpGDIDDSSurface); + TRACE("returning primary (%p)\n", This->primary_surface); + *lplpGDIDDSSurface = ICOM_INTERFACE(This->primary_surface, IDirectDrawSurface7); + if (*lplpGDIDDSSurface) + IDirectDrawSurface7_AddRef(*lplpGDIDDSSurface); + return DD_OK; +} + +HRESULT WINAPI +Main_DirectDraw_GetMonitorFrequency(LPDIRECTDRAW7 iface,LPDWORD freq) +{ + ICOM_THIS(IDirectDrawImpl,iface); FIXME("(%p)->(%p) returns 60 Hz always\n",This,freq); *freq = 60*100; /* 60 Hz */ return DD_OK; } -HRESULT WINAPI IDirectDraw2Impl_GetFourCCCodes( - LPDIRECTDRAW2 iface,LPDWORD x,LPDWORD y -) { - ICOM_THIS(IDirectDraw2Impl,iface); - FIXME("(%p,%p,%p), stub\n",This,x,y); - return DD_OK; -} - -HRESULT WINAPI IDirectDraw2Impl_EnumSurfaces( - LPDIRECTDRAW2 iface,DWORD x,LPDDSURFACEDESC ddsfd,LPVOID context, - LPDDENUMSURFACESCALLBACK ddsfcb -) { - ICOM_THIS(IDirectDraw2Impl,iface); - FIXME("(%p)->(0x%08lx,%p,%p,%p),stub!\n",This,x,ddsfd,context,ddsfcb); - return DD_OK; -} - -HRESULT WINAPI IDirectDraw2Impl_Compact( LPDIRECTDRAW2 iface ) { - ICOM_THIS(IDirectDraw2Impl,iface); - FIXME("(%p)->()\n", This ); - return DD_OK; -} - -HRESULT WINAPI IDirectDraw2Impl_GetGDISurface( - LPDIRECTDRAW2 iface, LPDIRECTDRAWSURFACE *lplpGDIDDSSurface -) { - ICOM_THIS(IDirectDraw2Impl,iface); - FIXME("(%p)->(%p)\n", This, lplpGDIDDSSurface); - return DD_OK; -} - -HRESULT WINAPI IDirectDraw2Impl_GetScanLine( - LPDIRECTDRAW2 iface, LPDWORD lpdwScanLine -) { - ICOM_THIS(IDirectDraw2Impl,iface); +HRESULT WINAPI +Main_DirectDraw_GetScanLine(LPDIRECTDRAW7 iface, LPDWORD lpdwScanLine) +{ + ICOM_THIS(IDirectDrawImpl,iface); FIXME("(%p)->(%p)\n", This, lpdwScanLine); - if (lpdwScanLine) - *lpdwScanLine = 1; + *lpdwScanLine = 1; + return DD_OK; } -HRESULT WINAPI IDirectDraw2Impl_Initialize(LPDIRECTDRAW2 iface, GUID *lpGUID) { - ICOM_THIS(IDirectDraw2Impl,iface); - FIXME("(%p)->(%p)\n", This, lpGUID); +HRESULT WINAPI +Main_DirectDraw_GetSurfaceFromDC(LPDIRECTDRAW7 iface, HDC hdc, + LPDIRECTDRAWSURFACE7 *lpDDS) +{ + ICOM_THIS(IDirectDrawImpl,iface); + FIXME("(%p)->(%08ld,%p)\n", This, (DWORD) hdc, lpDDS); + return DD_OK; } -/***************************************************************************** - * IDirectDraw2 - * - * We only need to list the changed/new functions. - */ -HRESULT WINAPI IDirectDraw2Impl_SetDisplayMode( - LPDIRECTDRAW2 iface,DWORD width,DWORD height,DWORD depth, - DWORD dwRefreshRate, DWORD dwFlags -) { - FIXME("Ignoring parameters (0x%08lx,0x%08lx)\n", dwRefreshRate, dwFlags ); - return IDirectDrawImpl_SetDisplayMode((LPDIRECTDRAW)iface,width,height,depth); +HRESULT WINAPI +Main_DirectDraw_GetVerticalBlankStatus(LPDIRECTDRAW7 iface, LPBOOL status) +{ + ICOM_THIS(IDirectDrawImpl,iface); + TRACE("(%p)->(%p)\n",This,status); + *status = TRUE; + return DD_OK; } -HRESULT WINAPI IDirectDraw2Impl_GetAvailableVidMem( - LPDIRECTDRAW2 iface,LPDDSCAPS ddscaps,LPDWORD total,LPDWORD free -) { - ICOM_THIS(IDirectDraw2Impl,iface); +/* If we were not initialised then Uninit_Main_IDirectDraw7_Initialize would + * have been called instead. */ +HRESULT WINAPI +Main_DirectDraw_Initialize(LPDIRECTDRAW7 iface, LPGUID lpGuid) +{ + TRACE("(%p)->(%s)\n", iface, debugstr_guid(lpGuid)); + + return DDERR_ALREADYINITIALIZED; +} + +HRESULT WINAPI +Main_DirectDraw_RestoreAllSurfaces(LPDIRECTDRAW7 iface) +{ + ICOM_THIS(IDirectDrawImpl,iface); + IDirectDrawSurfaceImpl* surf; + + TRACE("(%p)->()\n", This); + + for (surf = This->surfaces; surf != NULL; surf = surf->next_ddraw) + IDirectDrawSurface7_Restore(ICOM_INTERFACE(surf, IDirectDrawSurface7)); + + return DD_OK; +} + +static void DDRAW_SubclassWindow(IDirectDrawImpl* This) +{ + /* Well we don't actually subclass the window yet. */ + SetPropA(This->window, ddProp, (LONG)This); +} + +static void DDRAW_UnsubclassWindow(IDirectDrawImpl* This) +{ + RemovePropA(This->window, ddProp); +} + +HRESULT WINAPI +Main_DirectDraw_SetCooperativeLevel(LPDIRECTDRAW7 iface, HWND hwnd, + DWORD cooplevel) +{ + ICOM_THIS(IDirectDrawImpl,iface); + + FIXME("(%p)->(%08lx,%08lx)\n",This,(DWORD)hwnd,cooplevel); + DDRAW_dump_cooperativelevel(cooplevel); + + /* Makes realMYST test happy. */ + if (This->cooperative_level == cooplevel + && This->window == hwnd) + return DD_OK; + + if ((This->cooperative_level & DDSCL_EXCLUSIVE) && + (cooplevel & DDSCL_EXCLUSIVE)) + return DDERR_EXCLUSIVEMODEALREADYSET; + + /* XXX "It cannot be reset while the process has surfaces or palettes + * created." Otherwise the window can be changed??? + * + * This appears to be wrong - comment it out for now. + if (This->window) + return DDERR_HWNDALREADYSET; + */ + + if (!(cooplevel & (DDSCL_EXCLUSIVE|DDSCL_NORMAL))) + return DDERR_INVALIDPARAMS; + + This->window = hwnd; + This->cooperative_level = cooplevel; + + ShowWindow(hwnd, SW_SHOW); + + DDRAW_SubclassWindow(This); + + /* TODO Does it also get resized to the current screen size? */ + + return DD_OK; +} + +HRESULT WINAPI +Main_DirectDraw_SetDisplayMode(LPDIRECTDRAW7 iface, DWORD dwWidth, + DWORD dwHeight, LONG lPitch, + DWORD dwRefreshRate, DWORD dwFlags, + const DDPIXELFORMAT* pixelformat) +{ + short screenX; + short screenY; + + ICOM_THIS(IDirectDrawImpl,iface); + + TRACE("(%p)->SetDisplayMode(%ld,%ld)\n",This,dwWidth,dwHeight); + + if (!(This->cooperative_level & DDSCL_EXCLUSIVE)) + return DDERR_NOEXCLUSIVEMODE; + + if (!IsWindow(This->window)) + return DDERR_GENERIC; /* unchecked */ + + LosePrimarySurface(This); + + screenX = GetSystemMetrics(SM_CXSCREEN); + screenY = GetSystemMetrics(SM_CYSCREEN); + + This->width = dwWidth; + This->height = dwHeight; + This->pitch = lPitch; + This->pixelformat = *pixelformat; + + /* Position the window in the center of the screen - don't center for now */ + /* MoveWindow(This->window, (screenX-dwWidth)/2, (screenY-dwHeight)/2, + dwWidth, dwHeight, TRUE);*/ + MoveWindow(This->window, 0, 0, dwWidth, dwHeight, TRUE); + + SetFocus(This->window); + + return DD_OK; +} + +HRESULT WINAPI +Main_DirectDraw_RestoreDisplayMode(LPDIRECTDRAW7 iface) +{ + ICOM_THIS(IDirectDrawImpl,iface); + + TRACE("(%p)\n",This); + if (!(This->cooperative_level & DDSCL_EXCLUSIVE)) + return DDERR_NOEXCLUSIVEMODE; + + /* Lose the primary surface if the resolution changes. */ + if (This->orig_width != This->width || This->orig_height != This->height + || This->orig_pitch != This->pitch + || This->orig_pixelformat.dwFlags != This->pixelformat.dwFlags + || !Main_DirectDraw_DDPIXELFORMAT_Match(&This->pixelformat, + &This->orig_pixelformat)) + { + LosePrimarySurface(This); + } + + /* TODO Move the window back where it belongs. */ + + return DD_OK; +} + +HRESULT WINAPI +Main_DirectDraw_WaitForVerticalBlank(LPDIRECTDRAW7 iface, DWORD dwFlags, + HANDLE h) +{ + ICOM_THIS(IDirectDrawImpl,iface); + FIXME("(%p)->(flags=0x%08lx,handle=0x%08x)\n",This,dwFlags,h); + return DD_OK; +} + +HRESULT WINAPI +Main_DirectDraw_GetDisplayMode(LPDIRECTDRAW7 iface, LPDDSURFACEDESC2 pDDSD) +{ + ICOM_THIS(IDirectDrawImpl,iface); + TRACE("(%p)->GetDisplayMode(%p)\n",This,pDDSD); + + pDDSD->dwFlags = DDSD_HEIGHT|DDSD_WIDTH|DDSD_PITCH|DDSD_PIXELFORMAT|DDSD_REFRESHRATE; + pDDSD->dwHeight = This->height; + pDDSD->dwWidth = This->width; + pDDSD->u1.lPitch = This->pitch; + pDDSD->u2.dwRefreshRate = 60; + pDDSD->u4.ddpfPixelFormat = This->pixelformat; + pDDSD->ddsCaps.dwCaps = 0; + + return DD_OK; +} + +HRESULT WINAPI +Main_DirectDraw_GetAvailableVidMem(LPDIRECTDRAW7 iface, LPDDSCAPS2 ddscaps, + LPDWORD total, LPDWORD free) +{ + ICOM_THIS(IDirectDrawImpl,iface); TRACE("(%p)->(%p,%p,%p)\n", This,ddscaps,total,free); /* We have 16 MB videomemory */ @@ -480,122 +993,436 @@ HRESULT WINAPI IDirectDraw2Impl_GetAvailableVidMem( return DD_OK; } -/***************************************************************************** - * IDirectDraw4 - * +HRESULT WINAPI Main_DirectDraw_TestCooperativeLevel(LPDIRECTDRAW7 iface) { + ICOM_THIS(IDirectDrawImpl,iface); + TRACE("(%p)->(): stub\n", This); + + return DD_OK; +} + +HRESULT WINAPI +Main_DirectDraw_StartModeTest(LPDIRECTDRAW7 iface, LPSIZE pModes, + DWORD dwNumModes, DWORD dwFlags) +{ + ICOM_THIS(IDirectDrawImpl,iface); + FIXME("(%p)->() stub\n", This); + + return DD_OK; +} + +/*** Owned object management. */ + +void Main_DirectDraw_AddSurface(IDirectDrawImpl* This, + IDirectDrawSurfaceImpl* surface) +{ + assert(surface->ddraw_owner == NULL || surface->ddraw_owner == This); + + surface->ddraw_owner = This; + + /* where should it go? */ + surface->next_ddraw = This->surfaces; + surface->prev_ddraw = NULL; + if (This->surfaces) + This->surfaces->prev_ddraw = surface; + This->surfaces = surface; +} + +void Main_DirectDraw_RemoveSurface(IDirectDrawImpl* This, + IDirectDrawSurfaceImpl* surface) +{ + assert(surface->ddraw_owner == This); + + if (This->surfaces == surface) + This->surfaces = surface->next_ddraw; + + if (This->primary_surface == surface) + This->primary_surface = NULL; + + if (surface->next_ddraw) + surface->next_ddraw->prev_ddraw = surface->prev_ddraw; + if (surface->prev_ddraw) + surface->prev_ddraw->next_ddraw = surface->next_ddraw; +} + +static void Main_DirectDraw_DeleteSurfaces(IDirectDrawImpl* This) +{ + while (This->surfaces != NULL) + Main_DirectDrawSurface_ForceDestroy(This->surfaces); +} + +void Main_DirectDraw_AddClipper(IDirectDrawImpl* This, + IDirectDrawClipperImpl* clipper) +{ + assert(clipper->ddraw_owner == NULL || clipper->ddraw_owner == This); + + clipper->ddraw_owner = This; + + clipper->next_ddraw = This->clippers; + clipper->prev_ddraw = NULL; + if (This->clippers) + This->clippers->prev_ddraw = clipper; + This->clippers = clipper; +} + +void Main_DirectDraw_RemoveClipper(IDirectDrawImpl* This, + IDirectDrawClipperImpl* clipper) +{ + assert(clipper->ddraw_owner == This); + + if (This->clippers == clipper) + This->clippers = clipper->next_ddraw; + + if (clipper->next_ddraw) + clipper->next_ddraw->prev_ddraw = clipper->prev_ddraw; + if (clipper->prev_ddraw) + clipper->prev_ddraw->next_ddraw = clipper->next_ddraw; +} + +static void Main_DirectDraw_DeleteClippers(IDirectDrawImpl* This) +{ + while (This->clippers != NULL) + Main_DirectDrawClipper_ForceDestroy(This->clippers); +} + +void Main_DirectDraw_AddPalette(IDirectDrawImpl* This, + IDirectDrawPaletteImpl* palette) +{ + assert(palette->ddraw_owner == NULL || palette->ddraw_owner == This); + + palette->ddraw_owner = This; + + /* where should it go? */ + palette->next_ddraw = This->palettes; + palette->prev_ddraw = NULL; + if (This->palettes) + This->palettes->prev_ddraw = palette; + This->palettes = palette; +} + +void Main_DirectDraw_RemovePalette(IDirectDrawImpl* This, + IDirectDrawPaletteImpl* palette) +{ + assert(palette->ddraw_owner == This); + + if (This->palettes == palette) + This->palettes = palette->next_ddraw; + + if (palette->next_ddraw) + palette->next_ddraw->prev_ddraw = palette->prev_ddraw; + if (palette->prev_ddraw) + palette->prev_ddraw->next_ddraw = palette->next_ddraw; +} + +static void Main_DirectDraw_DeletePalettes(IDirectDrawImpl* This) +{ + while (This->palettes != NULL) + Main_DirectDrawPalette_ForceDestroy(This->palettes); +} + +/*** ??? */ + +static void +LoseSurface(IDirectDrawSurfaceImpl *surface) +{ + if (surface != NULL) surface->lose_surface(surface); +} + +static void +LosePrimarySurface(IDirectDrawImpl *This) +{ + /* MSDN: "If another application changes the display mode, the primary + * surface is lost, and the method returns DDERR_SURFACELOST until the + * primary surface is recreated to match the new display mode." + * + * We mark all the primary surfaces as lost as soon as the display + * mode is changed (by any application). */ + + LoseSurface(This->primary_surface); +} + +/****************************************************************************** + * Uninitialised DirectDraw functions + * + * This vtable is used when a DirectDraw object is created with + * CoCreateInstance. The only usable method is Initialize. */ -HRESULT WINAPI IDirectDraw4Impl_GetSurfaceFromDC( - LPDIRECTDRAW4 iface, HDC hdc, LPDIRECTDRAWSURFACE *lpDDS -) { - ICOM_THIS(IDirectDraw4Impl,iface); - FIXME("(%p)->(%08ld,%p)\n", This, (DWORD) hdc, lpDDS); - - return DD_OK; +void Uninit_DirectDraw_final_release(IDirectDrawImpl *This) +{ + Main_DirectDraw_final_release(This); } -HRESULT WINAPI IDirectDraw4Impl_RestoreAllSurfaces(LPDIRECTDRAW4 iface) { - ICOM_THIS(IDirectDraw4Impl,iface); - FIXME("(%p)->()\n", This); +static ICOM_VTABLE(IDirectDraw7) Uninit_DirectDraw_VTable; - return DD_OK; +/* Not called from the vtable. */ +HRESULT Uninit_DirectDraw_Construct(IDirectDrawImpl *This, BOOL ex) +{ + HRESULT hr; + + hr = Main_DirectDraw_Construct(This, ex); + if (FAILED(hr)) return hr; + + This->final_release = Uninit_DirectDraw_final_release; + ICOM_INIT_INTERFACE(This, IDirectDraw7, Uninit_DirectDraw_VTable); + + return S_OK; } -HRESULT WINAPI IDirectDraw4Impl_TestCooperativeLevel(LPDIRECTDRAW4 iface) { - ICOM_THIS(IDirectDraw4Impl,iface); - FIXME("(%p)->()\n", This); +HRESULT Uninit_DirectDraw_Create(const GUID* pGUID, + LPDIRECTDRAW7* pIface, + IUnknown* pUnkOuter, BOOL ex) +{ + HRESULT hr; + IDirectDrawImpl* This; - return DD_OK; + assert(pUnkOuter == NULL); /* XXX no: we must check this */ + + This = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, + sizeof(IDirectDrawImpl)); + if (This == NULL) return E_OUTOFMEMORY; + + hr = Uninit_DirectDraw_Construct(This, ex); + if (FAILED(hr)) + HeapFree(GetProcessHeap(), HEAP_ZERO_MEMORY, This); + else + *pIface = ICOM_INTERFACE(This, IDirectDraw7); + + return hr; } -HRESULT WINAPI IDirectDraw4Impl_GetDeviceIdentifier( - LPDIRECTDRAW4 iface,LPDDDEVICEIDENTIFIER lpdddi,DWORD dwFlags -) { - ICOM_THIS(IDirectDraw4Impl,iface); - FIXME("(%p)->(%p,%08lx)\n", This, lpdddi, dwFlags); +static HRESULT WINAPI +Uninit_DirectDraw_Initialize(LPDIRECTDRAW7 iface, LPGUID pDeviceGuid) +{ + const ddraw_driver* driver; + ICOM_THIS(IDirectDrawImpl, iface); - /* just guessing values */ - strcpy(lpdddi->szDriver,"directdraw"); - strcpy(lpdddi->szDescription,"WINE DirectDraw"); - lpdddi->liDriverVersion.s.HighPart = 7; - lpdddi->liDriverVersion.s.LowPart = 0; - /* Do I smell PCI ids here ? -MM */ - lpdddi->dwVendorId = 0; - lpdddi->dwDeviceId = 0; - lpdddi->dwSubSysId = 0; - lpdddi->dwRevision = 1; - memset(&(lpdddi->guidDeviceIdentifier),0,sizeof(lpdddi->guidDeviceIdentifier)); - return DD_OK; + TRACE("(%p)->(%p)", iface, pDeviceGuid); + + driver = DDRAW_FindDriver(pDeviceGuid); + /* XXX This return value is not documented. (Not checked.) */ + if (driver == NULL) return DDERR_INVALIDDIRECTDRAWGUID; + + return driver->init(This, pDeviceGuid); } -HRESULT WINAPI IDirectDraw7Impl_StartModeTest( - LPDIRECTDRAW7 iface,LPSIZE lpModesToTest,DWORD dwNumEntries,DWORD dwFlags -) { - FIXME("(%p)->(%p,%ld,0x%08lx),empty stub!\n",iface, - lpModesToTest,dwNumEntries,dwFlags - ); - return DD_OK; +static HRESULT WINAPI +Uninit_DirectDraw_Compact(LPDIRECTDRAW7 iface) +{ + return DDERR_NOTINITIALIZED; } -HRESULT WINAPI IDirectDraw7Impl_EvaluateMode( - LPDIRECTDRAW7 iface,DWORD dwFlags, DWORD *pSecondsUntilTimeout -) { - FIXME("(%p)->(0x%08lx,%p),empty stub!\n",iface, - dwFlags,pSecondsUntilTimeout - ); - return DD_OK; +static HRESULT WINAPI +Uninit_DirectDraw_CreateClipper(LPDIRECTDRAW7 iface, DWORD dwFlags, + LPDIRECTDRAWCLIPPER *lplpDDClipper, + IUnknown *pUnkOuter) + +{ + return DDERR_NOTINITIALIZED; } -HRESULT common_off_screen_CreateSurface( - IDirectDraw2Impl* This,IDirectDrawSurfaceImpl* lpdsf -) { - int bpp; - - /* The surface was already allocated when entering in this function */ - TRACE("using system memory for a surface (%p) \n", lpdsf); - - if (lpdsf->s.surface_desc.dwFlags & DDSD_ZBUFFERBITDEPTH) { - /* This is a Z Buffer */ - TRACE("Creating Z-Buffer of %ld bit depth\n", lpdsf->s.surface_desc.u.dwZBufferBitDepth); - bpp = lpdsf->s.surface_desc.u.dwZBufferBitDepth / 8; - } else { - /* This is a standard image */ - if (!(lpdsf->s.surface_desc.dwFlags & DDSD_PIXELFORMAT)) { - /* No pixel format => use DirectDraw's format */ - lpdsf->s.surface_desc.ddpfPixelFormat = This->d->directdraw_pixelformat; - lpdsf->s.surface_desc.dwFlags |= DDSD_PIXELFORMAT; - } - bpp = GET_BPP(lpdsf->s.surface_desc); - - /* When the application is requesting a 24 bpp surface and the Direct Draw bpp - is set to 32, we 'upgrade' the requested bpp to 32 to make the blit faster - from off-screen surface to visible surfaces. - - This can also happen with 15 / 16 bpp. - - With this, Windows Media Player works in 32 bpp mode. - Lionel - */ - if (((bpp == 3) && (PFGET_BPP(This->d->directdraw_pixelformat) == 4)) || - ((bpp == 2) && (PFGET_BPP(This->d->directdraw_pixelformat) == 2) && - (lpdsf->s.surface_desc.ddpfPixelFormat.u1.dwRBitMask != This->d->directdraw_pixelformat.u1.dwRBitMask))) { - TRACE("Warning: 'upgrading' requested pixel format to screen pixel format for blit efficiency\n"); - TRACE(" some applications may have problems with it.\n"); - bpp = PFGET_BPP(This->d->directdraw_pixelformat); - lpdsf->s.surface_desc.ddpfPixelFormat = This->d->directdraw_pixelformat; - } - } - - if (lpdsf->s.surface_desc.dwFlags & DDSD_LPSURFACE) - ERR("Creates a surface that is already allocated : assuming this is an application bug !\n"); - - lpdsf->s.surface_desc.dwFlags |= DDSD_PITCH|DDSD_LPSURFACE; - lpdsf->s.surface_desc.u1.lpSurface =(LPBYTE)VirtualAlloc( - NULL, - lpdsf->s.surface_desc.dwWidth * lpdsf->s.surface_desc.dwHeight * bpp, - MEM_RESERVE | MEM_COMMIT, - PAGE_READWRITE - ); - lpdsf->s.surface_desc.lPitch = lpdsf->s.surface_desc.dwWidth * bpp; - return DD_OK; +static HRESULT WINAPI +Uninit_DirectDraw_CreatePalette(LPDIRECTDRAW7 iface, DWORD dwFlags, + LPPALETTEENTRY lpColorTable, + LPDIRECTDRAWPALETTE *lplpDDPalette, + IUnknown *pUnkOuter) +{ + return DDERR_NOTINITIALIZED; } + +static HRESULT WINAPI +Uninit_DirectDraw_CreateSurface(LPDIRECTDRAW7 iface, + LPDDSURFACEDESC2 lpDDSurfaceDesc, + LPDIRECTDRAWSURFACE7 *lplpDDSurface, + IUnknown *pUnkOuter) +{ + return DDERR_NOTINITIALIZED; +} + +static HRESULT WINAPI +Uninit_DirectDraw_DuplicateSurface(LPDIRECTDRAW7 iface, + LPDIRECTDRAWSURFACE7 pSurf, + LPDIRECTDRAWSURFACE7 *pDupSurf) + +{ + return DDERR_NOTINITIALIZED; +} + +static HRESULT WINAPI +Uninit_DirectDraw_EnumDisplayModes(LPDIRECTDRAW7 iface, DWORD dwFlags, + LPDDSURFACEDESC2 lpDDSD, + LPVOID context, + LPDDENUMMODESCALLBACK2 cb) +{ + return DDERR_NOTINITIALIZED; +} + +static HRESULT WINAPI +Uninit_DirectDraw_EnumSurfaces(LPDIRECTDRAW7 iface, DWORD dwFlags, + LPDDSURFACEDESC2 pDDSD, LPVOID context, + LPDDENUMSURFACESCALLBACK7 cb) +{ + return DDERR_NOTINITIALIZED; +} + +static HRESULT WINAPI +Uninit_DirectDraw_FlipToGDISurface(LPDIRECTDRAW7 iface) +{ + return DDERR_NOTINITIALIZED; +} + +static HRESULT WINAPI +Uninit_DirectDraw_GetCaps(LPDIRECTDRAW7 iface, LPDDCAPS pDriverCaps, + LPDDCAPS pHELCaps) +{ + return DDERR_NOTINITIALIZED; +} + +static HRESULT WINAPI +Uninit_DirectDraw_GetDisplayMode(LPDIRECTDRAW7 iface, + LPDDSURFACEDESC2 pDDSD) +{ + return DDERR_NOTINITIALIZED; +} + +static HRESULT WINAPI +Uninit_DirectDraw_GetFourCCCodes(LPDIRECTDRAW7 iface, LPDWORD pNumCodes, + LPDWORD pCodes) +{ + return DDERR_NOTINITIALIZED; +} + +static HRESULT WINAPI +Uninit_DirectDraw_GetGDISurface(LPDIRECTDRAW7 iface, + LPDIRECTDRAWSURFACE7 *pGDISurf) +{ + return DDERR_NOTINITIALIZED; +} + +static HRESULT WINAPI +Uninit_DirectDraw_GetMonitorFrequency(LPDIRECTDRAW7 iface, LPDWORD pdwFreq) +{ + return DDERR_NOTINITIALIZED; +} + +static HRESULT WINAPI +Uninit_DirectDraw_GetScanLine(LPDIRECTDRAW7 iface, LPDWORD pdwScanLine) +{ + return DDERR_NOTINITIALIZED; +} + +static HRESULT WINAPI +Uninit_DirectDraw_GetVerticalBlankStatus(LPDIRECTDRAW7 iface, PBOOL pbIsInVB) +{ + return DDERR_NOTINITIALIZED; +} + +static HRESULT WINAPI +Uninit_DirectDraw_RestoreDisplayMode(LPDIRECTDRAW7 iface) +{ + return DDERR_NOTINITIALIZED; +} + +static HRESULT WINAPI +Uninit_DirectDraw_SetCooperativeLevel(LPDIRECTDRAW7 iface, HWND hWnd, + DWORD dwFlags) +{ + return DDERR_NOTINITIALIZED; +} + +static HRESULT WINAPI +Uninit_DirectDraw_SetDisplayMode(LPDIRECTDRAW7 iface, DWORD dwWidth, + DWORD dwHeight, DWORD dwBPP, + DWORD dwRefreshRate, DWORD dwFlags) +{ + return DDERR_NOTINITIALIZED; +} + +static HRESULT WINAPI +Uninit_DirectDraw_WaitForVerticalBlank(LPDIRECTDRAW7 iface, DWORD dwFlags, + HANDLE hEvent) +{ + return DDERR_NOTINITIALIZED; +} + +static HRESULT WINAPI +Uninit_DirectDraw_GetAvailableVidMem(LPDIRECTDRAW7 iface, LPDDSCAPS2 pDDCaps, + LPDWORD pdwTotal, LPDWORD pdwFree) +{ + return DDERR_NOTINITIALIZED; +} + +static HRESULT WINAPI +Uninit_DirectDraw_GetSurfaceFromDC(LPDIRECTDRAW7 iface, HDC hDC, + LPDIRECTDRAWSURFACE7 *pSurf) +{ + return DDERR_NOTINITIALIZED; +} + +static HRESULT WINAPI +Uninit_DirectDraw_RestoreAllSurfaces(LPDIRECTDRAW7 iface) +{ + return DDERR_NOTINITIALIZED; +} + +static HRESULT WINAPI +Uninit_DirectDraw_TestCooperativeLevel(LPDIRECTDRAW7 iface) +{ + return DDERR_NOTINITIALIZED; +} + +static HRESULT WINAPI +Uninit_DirectDraw_GetDeviceIdentifier(LPDIRECTDRAW7 iface, + LPDDDEVICEIDENTIFIER2 pDDDI, + DWORD dwFlags) +{ + return DDERR_NOTINITIALIZED; +} + +static HRESULT WINAPI +Uninit_DirectDraw_StartModeTest(LPDIRECTDRAW7 iface, LPSIZE pszModes, + DWORD cModes, DWORD dwFlags) +{ + return DDERR_NOTINITIALIZED; +} + +static HRESULT WINAPI +Uninit_DirectDraw_EvaluateMode(LPDIRECTDRAW7 iface, DWORD dwFlags, + LPDWORD pTimeout) +{ + return DDERR_NOTINITIALIZED; +} + +static ICOM_VTABLE(IDirectDraw7) Uninit_DirectDraw_VTable = +{ + ICOM_MSVTABLE_COMPAT_DummyRTTIVALUE + Main_DirectDraw_QueryInterface, + Main_DirectDraw_AddRef, + Main_DirectDraw_Release, + Uninit_DirectDraw_Compact, + Uninit_DirectDraw_CreateClipper, + Uninit_DirectDraw_CreatePalette, + Uninit_DirectDraw_CreateSurface, + Uninit_DirectDraw_DuplicateSurface, + Uninit_DirectDraw_EnumDisplayModes, + Uninit_DirectDraw_EnumSurfaces, + Uninit_DirectDraw_FlipToGDISurface, + Uninit_DirectDraw_GetCaps, + Uninit_DirectDraw_GetDisplayMode, + Uninit_DirectDraw_GetFourCCCodes, + Uninit_DirectDraw_GetGDISurface, + Uninit_DirectDraw_GetMonitorFrequency, + Uninit_DirectDraw_GetScanLine, + Uninit_DirectDraw_GetVerticalBlankStatus, + Uninit_DirectDraw_Initialize, + Uninit_DirectDraw_RestoreDisplayMode, + Uninit_DirectDraw_SetCooperativeLevel, + Uninit_DirectDraw_SetDisplayMode, + Uninit_DirectDraw_WaitForVerticalBlank, + Uninit_DirectDraw_GetAvailableVidMem, + Uninit_DirectDraw_GetSurfaceFromDC, + Uninit_DirectDraw_RestoreAllSurfaces, + Uninit_DirectDraw_TestCooperativeLevel, + Uninit_DirectDraw_GetDeviceIdentifier, + Uninit_DirectDraw_StartModeTest, + Uninit_DirectDraw_EvaluateMode +}; diff --git a/dlls/ddraw/ddraw/main.h b/dlls/ddraw/ddraw/main.h new file mode 100644 index 00000000000..1801d11f620 --- /dev/null +++ b/dlls/ddraw/ddraw/main.h @@ -0,0 +1,105 @@ +/* Copyright 2000 TransGaming Technologies Inc. */ + +#ifndef WINE_DDRAW_DDRAW_MAIN_H_INCLUDED +#define WINE_DDRAW_DDRAW_MAIN_H_INCLUDED + +/* internal virtual functions */ +void Main_DirectDraw_final_release(IDirectDrawImpl* This); +HRESULT +Main_create_offscreen(IDirectDrawImpl* This, const DDSURFACEDESC2 *pDDSD, + LPDIRECTDRAWSURFACE7* ppSurf, LPUNKNOWN pOuter); +HRESULT +Main_create_texture(IDirectDrawImpl* This, const DDSURFACEDESC2 *pDDSD, + LPDIRECTDRAWSURFACE7* ppSurf, LPUNKNOWN pOuter, + DWORD dwMipMapLevel); +HRESULT +Main_create_zbuffer(IDirectDrawImpl* This, const DDSURFACEDESC2 *pDDSD, + LPDIRECTDRAWSURFACE7* ppSurf, LPUNKNOWN pOuter); + +/* internal functions */ +HRESULT Main_DirectDraw_Construct(IDirectDrawImpl *This, BOOL ex); +void Main_DirectDraw_AddSurface(IDirectDrawImpl* This, + IDirectDrawSurfaceImpl* surface); +void Main_DirectDraw_RemoveSurface(IDirectDrawImpl* This, + IDirectDrawSurfaceImpl* surface); +void Main_DirectDraw_AddClipper(IDirectDrawImpl* This, + IDirectDrawClipperImpl* clipper); +void Main_DirectDraw_RemoveClipper(IDirectDrawImpl* This, + IDirectDrawClipperImpl* clipper); +void Main_DirectDraw_AddPalette(IDirectDrawImpl* This, + IDirectDrawPaletteImpl* surface); +void Main_DirectDraw_RemovePalette(IDirectDrawImpl* This, + IDirectDrawPaletteImpl* palette); + + +/* interface functions */ + +ULONG WINAPI Main_DirectDraw_AddRef(LPDIRECTDRAW7 iface); +ULONG WINAPI Main_DirectDraw_Release(LPDIRECTDRAW7 iface); +HRESULT WINAPI Main_DirectDraw_QueryInterface(LPDIRECTDRAW7 iface, + REFIID refiid,LPVOID *obj); +HRESULT WINAPI Main_DirectDraw_Compact(LPDIRECTDRAW7 iface); +HRESULT WINAPI Main_DirectDraw_CreateClipper(LPDIRECTDRAW7 iface, + DWORD dwFlags, + LPDIRECTDRAWCLIPPER *ppClipper, + IUnknown *pUnkOuter); +HRESULT WINAPI +Main_DirectDraw_CreatePalette(LPDIRECTDRAW7 iface, DWORD dwFlags, + LPPALETTEENTRY palent, + LPDIRECTDRAWPALETTE* ppPalette, + LPUNKNOWN pUnknown); +HRESULT WINAPI +Main_DirectDraw_CreateSurface(LPDIRECTDRAW7 iface, LPDDSURFACEDESC2 pDDSD, + LPDIRECTDRAWSURFACE7 *ppSurf, + IUnknown *pUnkOuter); +HRESULT WINAPI +Main_DirectDraw_DuplicateSurface(LPDIRECTDRAW7 iface, LPDIRECTDRAWSURFACE7 src, + LPDIRECTDRAWSURFACE7* dst); +HRESULT WINAPI +Main_DirectDraw_EnumSurfaces(LPDIRECTDRAW7 iface, DWORD dwFlags, + LPDDSURFACEDESC2 lpDDSD2, LPVOID context, + LPDDENUMSURFACESCALLBACK7 callback); +HRESULT WINAPI +Main_DirectDraw_EvaluateMode(LPDIRECTDRAW7 iface,DWORD a,DWORD* b); +HRESULT WINAPI Main_DirectDraw_FlipToGDISurface(LPDIRECTDRAW7 iface); +HRESULT WINAPI +Main_DirectDraw_GetFourCCCodes(LPDIRECTDRAW7 iface, LPDWORD pNumCodes, + LPDWORD pCodes); +HRESULT WINAPI +Main_DirectDraw_GetGDISurface(LPDIRECTDRAW7 iface, + LPDIRECTDRAWSURFACE7 *lplpGDIDDSSurface); +HRESULT WINAPI +Main_DirectDraw_GetMonitorFrequency(LPDIRECTDRAW7 iface,LPDWORD freq); +HRESULT WINAPI +Main_DirectDraw_GetScanLine(LPDIRECTDRAW7 iface, LPDWORD lpdwScanLine); +HRESULT WINAPI +Main_DirectDraw_GetSurfaceFromDC(LPDIRECTDRAW7 iface, HDC hdc, + LPDIRECTDRAWSURFACE7 *lpDDS); +HRESULT WINAPI +Main_DirectDraw_GetVerticalBlankStatus(LPDIRECTDRAW7 iface, LPBOOL status); +HRESULT WINAPI +Main_DirectDraw_Initialize(LPDIRECTDRAW7 iface, LPGUID lpGuid); +HRESULT WINAPI Main_DirectDraw_RestoreAllSurfaces(LPDIRECTDRAW7 iface); +HRESULT WINAPI +Main_DirectDraw_SetCooperativeLevel(LPDIRECTDRAW7 iface, HWND hwnd, + DWORD cooplevel); +HRESULT WINAPI +Main_DirectDraw_SetDisplayMode(LPDIRECTDRAW7 iface, DWORD dwWidth, + DWORD dwHeight, LONG lPitch, + DWORD dwRefreshRate, DWORD dwFlags, + const DDPIXELFORMAT* pixelformat); +HRESULT WINAPI Main_DirectDraw_RestoreDisplayMode(LPDIRECTDRAW7 iface); +HRESULT WINAPI +Main_DirectDraw_WaitForVerticalBlank(LPDIRECTDRAW7 iface, DWORD dwFlags, + HANDLE h); +HRESULT WINAPI +Main_DirectDraw_GetDisplayMode(LPDIRECTDRAW7 iface, LPDDSURFACEDESC2 pDDSD); +HRESULT WINAPI +Main_DirectDraw_GetAvailableVidMem(LPDIRECTDRAW7 iface,LPDDSCAPS2 ddscaps, + LPDWORD total, LPDWORD free); +HRESULT WINAPI Main_DirectDraw_TestCooperativeLevel(LPDIRECTDRAW7 iface); +HRESULT WINAPI +Main_DirectDraw_StartModeTest(LPDIRECTDRAW7 iface, LPSIZE pModes, + DWORD dwNumModes, DWORD dwFlags); + +#endif diff --git a/dlls/ddraw/ddraw/thunks.c b/dlls/ddraw/ddraw/thunks.c new file mode 100644 index 00000000000..c76f7a3174d --- /dev/null +++ b/dlls/ddraw/ddraw/thunks.c @@ -0,0 +1,963 @@ +/* Direct Draw Thunks and old vtables + * Copyright 2000 TransGaming Technologies Inc. + */ +#include +#include "ddraw_private.h" +#include "ddcomimpl.h" + +static HRESULT WINAPI +IDirectDrawImpl_QueryInterface(LPDIRECTDRAW This, REFIID iid, LPVOID *ppObj) +{ + return IDirectDraw7_QueryInterface(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw, + IDirectDraw7, This), + iid, ppObj); +} + +static HRESULT WINAPI +IDirectDraw2Impl_QueryInterface(LPDIRECTDRAW2 This, REFIID iid, LPVOID *ppObj) +{ + return IDirectDraw7_QueryInterface(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw2, + IDirectDraw7, This), + iid, ppObj); +} + + +static HRESULT WINAPI +IDirectDraw4Impl_QueryInterface(LPDIRECTDRAW4 This, REFIID iid, LPVOID *ppObj) +{ + return IDirectDraw7_QueryInterface(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw4, + IDirectDraw7, This), + iid, ppObj); +} + +static ULONG WINAPI +IDirectDrawImpl_AddRef(LPDIRECTDRAW This) +{ + return IDirectDraw7_AddRef(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw, IDirectDraw7, + This)); +} + +static ULONG WINAPI +IDirectDraw2Impl_AddRef(LPDIRECTDRAW2 This) +{ + return IDirectDraw7_AddRef(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw2, IDirectDraw7, + This)); +} + +static ULONG WINAPI +IDirectDraw4Impl_AddRef(LPDIRECTDRAW4 This) +{ + return IDirectDraw7_AddRef(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw4, IDirectDraw7, + This)); +} + +static ULONG WINAPI +IDirectDrawImpl_Release(LPDIRECTDRAW This) +{ + return IDirectDraw7_Release(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw, IDirectDraw7, + This)); +} + +static ULONG WINAPI +IDirectDraw2Impl_Release(LPDIRECTDRAW2 This) +{ + return IDirectDraw7_Release(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw2, IDirectDraw7, + This)); +} + +static ULONG WINAPI +IDirectDraw4Impl_Release(LPDIRECTDRAW4 This) +{ + return IDirectDraw7_Release(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw4, IDirectDraw7, + This)); +} + +static HRESULT WINAPI +IDirectDrawImpl_Compact(LPDIRECTDRAW This) +{ + return IDirectDraw7_Compact(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw, IDirectDraw7, + This)); +} + +static HRESULT WINAPI +IDirectDraw2Impl_Compact(LPDIRECTDRAW2 This) +{ + return IDirectDraw7_Compact(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw2, IDirectDraw7, + This)); +} + +static HRESULT WINAPI +IDirectDraw4Impl_Compact(LPDIRECTDRAW4 This) +{ + return IDirectDraw7_Compact(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw4, IDirectDraw7, + This)); +} + +static HRESULT WINAPI +IDirectDrawImpl_CreateClipper(LPDIRECTDRAW This, DWORD dwFlags, + LPDIRECTDRAWCLIPPER *ppClipper, + IUnknown *pUnkOuter) +{ + return IDirectDraw7_CreateClipper(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw, + IDirectDraw7, + This), + dwFlags, ppClipper, pUnkOuter); +} + +static HRESULT WINAPI +IDirectDraw2Impl_CreateClipper(LPDIRECTDRAW2 This, DWORD dwFlags, + LPDIRECTDRAWCLIPPER *ppClipper, + IUnknown *pUnkOuter) +{ + return IDirectDraw7_CreateClipper(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw2, + IDirectDraw7, + This), + dwFlags, ppClipper, pUnkOuter); +} + +static HRESULT WINAPI +IDirectDraw4Impl_CreateClipper(LPDIRECTDRAW4 This, DWORD dwFlags, + LPDIRECTDRAWCLIPPER *ppClipper, + IUnknown *pUnkOuter) +{ + return IDirectDraw7_CreateClipper(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw4, + IDirectDraw7, + This), + dwFlags, ppClipper, pUnkOuter); +} + +static HRESULT WINAPI +IDirectDrawImpl_CreatePalette(LPDIRECTDRAW This, DWORD dwFlags, + LPPALETTEENTRY pEntries, + LPDIRECTDRAWPALETTE *ppPalette, + IUnknown *pUnkOuter) +{ + return IDirectDraw7_CreatePalette(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw, + IDirectDraw7, + This), + dwFlags, pEntries, ppPalette, pUnkOuter); +} + +static HRESULT WINAPI +IDirectDraw2Impl_CreatePalette(LPDIRECTDRAW2 This, DWORD dwFlags, + LPPALETTEENTRY pEntries, + LPDIRECTDRAWPALETTE *ppPalette, + IUnknown *pUnkOuter) +{ + return IDirectDraw7_CreatePalette(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw2, + IDirectDraw7, + This), + dwFlags, pEntries, ppPalette, pUnkOuter); +} + +static HRESULT WINAPI +IDirectDraw4Impl_CreatePalette(LPDIRECTDRAW4 This, DWORD dwFlags, + LPPALETTEENTRY pEntries, + LPDIRECTDRAWPALETTE *ppPalette, + IUnknown *pUnkOuter) +{ + return IDirectDraw7_CreatePalette(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw4, + IDirectDraw7, + This), + dwFlags, pEntries, ppPalette, pUnkOuter); +} + +static HRESULT WINAPI +IDirectDrawImpl_CreateSurface(LPDIRECTDRAW This, LPDDSURFACEDESC pSDesc, + LPDIRECTDRAWSURFACE *ppSurface, + IUnknown *pUnkOuter) +{ + LPDIRECTDRAWSURFACE7 pSurface7; + HRESULT hr; + + hr = IDirectDraw7_CreateSurface(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw, + IDirectDraw7, + This), + pSDesc, &pSurface7, pUnkOuter); + + *ppSurface = COM_INTERFACE_CAST(IDirectDrawSurfaceImpl, + IDirectDrawSurface7, IDirectDrawSurface3, + pSurface7); + + return hr; +} + +static HRESULT WINAPI +IDirectDraw2Impl_CreateSurface(LPDIRECTDRAW2 This, LPDDSURFACEDESC pSDesc, + LPDIRECTDRAWSURFACE *ppSurface, + IUnknown *pUnkOuter) +{ + LPDIRECTDRAWSURFACE7 pSurface7; + HRESULT hr; + + hr = IDirectDraw7_CreateSurface(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw, + IDirectDraw7, + This), + pSDesc, &pSurface7, pUnkOuter); + + *ppSurface = COM_INTERFACE_CAST(IDirectDrawSurfaceImpl, + IDirectDrawSurface7, IDirectDrawSurface3, + pSurface7); + + return hr; +} + +static HRESULT WINAPI +IDirectDraw4Impl_CreateSurface(LPDIRECTDRAW4 This, LPDDSURFACEDESC2 pSDesc, + LPDIRECTDRAWSURFACE4 *ppSurface, + IUnknown *pUnkOuter) +{ + return IDirectDraw7_CreateSurface(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw4, + IDirectDraw7, + This), + pSDesc, + (LPDIRECTDRAWSURFACE7 *)ppSurface, + pUnkOuter); +} + +static HRESULT WINAPI +IDirectDrawImpl_DuplicateSurface(LPDIRECTDRAW This, LPDIRECTDRAWSURFACE pSrc, + LPDIRECTDRAWSURFACE *ppDst) +{ + LPDIRECTDRAWSURFACE7 pDst7; + HRESULT hr; + + hr = IDirectDraw7_DuplicateSurface(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw, + IDirectDraw7, This), + COM_INTERFACE_CAST(IDirectDrawSurfaceImpl, + IDirectDrawSurface3, + IDirectDrawSurface7, + pSrc), + &pDst7); + + *ppDst = COM_INTERFACE_CAST(IDirectDrawSurfaceImpl, IDirectDrawSurface7, + IDirectDrawSurface3, pDst7); + + return hr; +} + +static HRESULT WINAPI +IDirectDraw2Impl_DuplicateSurface(LPDIRECTDRAW2 This, LPDIRECTDRAWSURFACE pSrc, + LPDIRECTDRAWSURFACE *ppDst) +{ + LPDIRECTDRAWSURFACE7 pDst7; + HRESULT hr; + + hr = IDirectDraw7_DuplicateSurface(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw2, + IDirectDraw7, This), + COM_INTERFACE_CAST(IDirectDrawSurfaceImpl, + IDirectDrawSurface3, + IDirectDrawSurface7, + pSrc), + &pDst7); + + *ppDst = COM_INTERFACE_CAST(IDirectDrawSurfaceImpl, IDirectDrawSurface7, + IDirectDrawSurface3, pDst7); + + return hr; +} + +static HRESULT WINAPI +IDirectDraw4Impl_DuplicateSurface(LPDIRECTDRAW4 This, + LPDIRECTDRAWSURFACE4 pSrc, + LPDIRECTDRAWSURFACE4 *ppDst) +{ + return IDirectDraw7_DuplicateSurface(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw4, + IDirectDraw7, + This), + (LPDIRECTDRAWSURFACE7)pSrc, + (LPDIRECTDRAWSURFACE7 *)ppDst); +} + +struct displaymodescallback_context +{ + LPDDENUMMODESCALLBACK func; + LPVOID context; +}; + +static HRESULT CALLBACK +EnumDisplayModesCallbackThunk(LPDDSURFACEDESC2 pDDSD2, LPVOID context) +{ + struct displaymodescallback_context *cbcontext = context; + + return cbcontext->func((LPDDSURFACEDESC)pDDSD2, cbcontext->context); +} + +static HRESULT WINAPI +IDirectDrawImpl_EnumDisplayModes(LPDIRECTDRAW This, DWORD dwFlags, + LPDDSURFACEDESC pDDSD, LPVOID context, + LPDDENUMMODESCALLBACK cb) +{ + struct displaymodescallback_context cbcontext = { cb, context }; + + return IDirectDraw7_EnumDisplayModes(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw, + IDirectDraw7, + This), + dwFlags, pDDSD, &cbcontext, + EnumDisplayModesCallbackThunk); +} + +static HRESULT WINAPI +IDirectDraw2Impl_EnumDisplayModes(LPDIRECTDRAW2 This, DWORD dwFlags, + LPDDSURFACEDESC pDDSD, LPVOID context, + LPDDENUMMODESCALLBACK cb) +{ + struct displaymodescallback_context cbcontext = { cb, context }; + + return IDirectDraw7_EnumDisplayModes(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw2, + IDirectDraw7, + This), + dwFlags, pDDSD, &cbcontext, + EnumDisplayModesCallbackThunk); +} + +static HRESULT WINAPI +IDirectDraw4Impl_EnumDisplayModes(LPDIRECTDRAW4 This, DWORD dwFlags, + LPDDSURFACEDESC2 pDDSD, LPVOID context, + LPDDENUMMODESCALLBACK2 cb) +{ + return IDirectDraw7_EnumDisplayModes(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw4, + IDirectDraw7, + This), + dwFlags, pDDSD, context, cb); +} + +struct surfacescallback_context +{ + LPDDENUMSURFACESCALLBACK func; + LPVOID context; +}; + +static HRESULT CALLBACK +EnumSurfacesCallbackThunk(LPDIRECTDRAWSURFACE7 pSurf, LPDDSURFACEDESC2 pDDSD, + LPVOID context) +{ + struct surfacescallback_context *cbcontext = context; + + return cbcontext->func(COM_INTERFACE_CAST(IDirectDrawSurfaceImpl, + IDirectDrawSurface7, + IDirectDrawSurface3, pSurf), + (LPDDSURFACEDESC)pDDSD, cbcontext->context); +} + +static HRESULT WINAPI +IDirectDrawImpl_EnumSurfaces(LPDIRECTDRAW This, DWORD dwFlags, + LPDDSURFACEDESC pDDSD, LPVOID context, + LPDDENUMSURFACESCALLBACK cb) +{ + struct surfacescallback_context cbcontext = { cb, context }; + return IDirectDraw7_EnumSurfaces(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw, + IDirectDraw7, This), + dwFlags, (LPDDSURFACEDESC2)pDDSD, + &cbcontext, EnumSurfacesCallbackThunk); +} + +static HRESULT WINAPI +IDirectDraw2Impl_EnumSurfaces(LPDIRECTDRAW2 This, DWORD dwFlags, + LPDDSURFACEDESC pDDSD, LPVOID context, + LPDDENUMSURFACESCALLBACK cb) +{ + struct surfacescallback_context cbcontext = { cb, context }; + return IDirectDraw7_EnumSurfaces(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw2, + IDirectDraw7, This), + dwFlags, (LPDDSURFACEDESC2)pDDSD, + &cbcontext, EnumSurfacesCallbackThunk); +} + +static HRESULT WINAPI +IDirectDraw4Impl_EnumSurfaces(LPDIRECTDRAW4 This, DWORD dwFlags, + LPDDSURFACEDESC2 pDDSD, LPVOID context, + LPDDENUMSURFACESCALLBACK2 cb) +{ + return IDirectDraw7_EnumSurfaces(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw4, + IDirectDraw7, This), + dwFlags, pDDSD, context, + (LPDDENUMSURFACESCALLBACK7)cb); +} + +static HRESULT WINAPI +IDirectDrawImpl_FlipToGDISurface(LPDIRECTDRAW This) +{ + return IDirectDraw7_FlipToGDISurface(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw, + IDirectDraw7, + This)); +} + +static HRESULT WINAPI +IDirectDraw2Impl_FlipToGDISurface(LPDIRECTDRAW2 This) +{ + return IDirectDraw7_FlipToGDISurface(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw2, + IDirectDraw7, + This)); +} + +static HRESULT WINAPI +IDirectDraw4Impl_FlipToGDISurface(LPDIRECTDRAW4 This) +{ + return IDirectDraw7_FlipToGDISurface(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw4, + IDirectDraw7, + This)); +} + +static HRESULT WINAPI +IDirectDrawImpl_GetCaps(LPDIRECTDRAW This, LPDDCAPS pDDC1, LPDDCAPS pDDC2) +{ + return IDirectDraw7_GetCaps(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw, IDirectDraw7, + This), pDDC1, pDDC2); +} + +static HRESULT WINAPI +IDirectDraw2Impl_GetCaps(LPDIRECTDRAW2 This, LPDDCAPS pDDC1, LPDDCAPS pDDC2) +{ + return IDirectDraw7_GetCaps(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw2, IDirectDraw7, + This), pDDC1, pDDC2); +} + +static HRESULT WINAPI +IDirectDraw4Impl_GetCaps(LPDIRECTDRAW4 This, LPDDCAPS pDDC1, LPDDCAPS pDDC2) +{ + return IDirectDraw7_GetCaps(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw4, IDirectDraw7, + This), pDDC1, pDDC2); +} + +static HRESULT WINAPI +IDirectDrawImpl_GetDisplayMode(LPDIRECTDRAW This, LPDDSURFACEDESC pDDSD) +{ + return IDirectDraw7_GetDisplayMode(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw, + IDirectDraw7, This), + (LPDDSURFACEDESC2)pDDSD); +} + +static HRESULT WINAPI +IDirectDraw2Impl_GetDisplayMode(LPDIRECTDRAW2 This, LPDDSURFACEDESC pDDSD) +{ + return IDirectDraw7_GetDisplayMode(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw2, + IDirectDraw7, This), + (LPDDSURFACEDESC2)pDDSD); +} + +static HRESULT WINAPI +IDirectDraw4Impl_GetDisplayMode(LPDIRECTDRAW4 This, LPDDSURFACEDESC2 pDDSD) +{ + return IDirectDraw7_GetDisplayMode(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw4, + IDirectDraw7, This), + pDDSD); +} + +static HRESULT WINAPI +IDirectDrawImpl_GetFourCCCodes(LPDIRECTDRAW This, LPDWORD lpNumCodes, + LPDWORD lpCodes) +{ + return IDirectDraw7_GetFourCCCodes(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw, + IDirectDraw7, + This), + lpNumCodes, lpCodes); +} + +static HRESULT WINAPI +IDirectDraw2Impl_GetFourCCCodes(LPDIRECTDRAW2 This, LPDWORD lpNumCodes, + LPDWORD lpCodes) +{ + return IDirectDraw7_GetFourCCCodes(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw2, + IDirectDraw7, + This), + lpNumCodes, lpCodes); +} + +static HRESULT WINAPI +IDirectDraw4Impl_GetFourCCCodes(LPDIRECTDRAW4 This, LPDWORD lpNumCodes, + LPDWORD lpCodes) +{ + return IDirectDraw7_GetFourCCCodes(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw4, + IDirectDraw7, + This), + lpNumCodes, lpCodes); +} + +static HRESULT WINAPI +IDirectDrawImpl_GetGDISurface(LPDIRECTDRAW This, LPDIRECTDRAWSURFACE *ppSurf) +{ + LPDIRECTDRAWSURFACE7 pSurf7; + HRESULT hr; + + hr = IDirectDraw7_GetGDISurface(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw, + IDirectDraw7, + This), &pSurf7); + + *ppSurf = COM_INTERFACE_CAST(IDirectDrawSurfaceImpl, IDirectDrawSurface7, + IDirectDrawSurface3, pSurf7); + + return hr; +} + +static HRESULT WINAPI +IDirectDraw2Impl_GetGDISurface(LPDIRECTDRAW2 This, LPDIRECTDRAWSURFACE *ppSurf) +{ + LPDIRECTDRAWSURFACE7 pSurf7; + HRESULT hr; + + hr = IDirectDraw7_GetGDISurface(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw2, + IDirectDraw7, + This), &pSurf7); + + *ppSurf = COM_INTERFACE_CAST(IDirectDrawSurfaceImpl, IDirectDrawSurface7, + IDirectDrawSurface3, pSurf7); + + return hr; +} + +static HRESULT WINAPI +IDirectDraw4Impl_GetGDISurface(LPDIRECTDRAW4 This, + LPDIRECTDRAWSURFACE4 *ppSurf) +{ + return IDirectDraw7_GetGDISurface(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw4, + IDirectDraw7, + This), + (LPDIRECTDRAWSURFACE7 *)ppSurf); +} + +static HRESULT WINAPI +IDirectDrawImpl_GetMonitorFrequency(LPDIRECTDRAW This, LPDWORD pdwFreq) +{ + return IDirectDraw7_GetMonitorFrequency(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw, + IDirectDraw7, + This), + pdwFreq); +} + +static HRESULT WINAPI +IDirectDraw2Impl_GetMonitorFrequency(LPDIRECTDRAW2 This, LPDWORD pdwFreq) +{ + return IDirectDraw7_GetMonitorFrequency(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw2, + IDirectDraw7, + This), + pdwFreq); +} + +static HRESULT WINAPI +IDirectDraw4Impl_GetMonitorFrequency(LPDIRECTDRAW4 This, LPDWORD pdwFreq) +{ + return IDirectDraw7_GetMonitorFrequency(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw4, + IDirectDraw7, + This), + pdwFreq); +} + +static HRESULT WINAPI +IDirectDrawImpl_GetScanLine(LPDIRECTDRAW This, LPDWORD pdwLine) +{ + return IDirectDraw7_GetScanLine(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw, + IDirectDraw7, + This), pdwLine); +} + +static HRESULT WINAPI +IDirectDraw2Impl_GetScanLine(LPDIRECTDRAW2 This, LPDWORD pdwLine) +{ + return IDirectDraw7_GetScanLine(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw2, + IDirectDraw7, + This), pdwLine); +} + +static HRESULT WINAPI +IDirectDraw4Impl_GetScanLine(LPDIRECTDRAW4 This, LPDWORD pdwLine) +{ + return IDirectDraw7_GetScanLine(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw4, + IDirectDraw7, + This), pdwLine); +} + +static HRESULT WINAPI +IDirectDrawImpl_GetVerticalBlankStatus(LPDIRECTDRAW This, LPBOOL lpbIsInVB) +{ + return IDirectDraw7_GetVerticalBlankStatus(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw, + IDirectDraw7, + This), + lpbIsInVB); +} + +static HRESULT WINAPI +IDirectDraw2Impl_GetVerticalBlankStatus(LPDIRECTDRAW2 This, LPBOOL lpbIsInVB) +{ + return IDirectDraw7_GetVerticalBlankStatus(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw2, + IDirectDraw7, + This), + lpbIsInVB); +} + +static HRESULT WINAPI +IDirectDraw4Impl_GetVerticalBlankStatus(LPDIRECTDRAW4 This, LPBOOL lpbIsInVB) +{ + return IDirectDraw7_GetVerticalBlankStatus(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw4, + IDirectDraw7, + This), + lpbIsInVB); +} + +static HRESULT WINAPI +IDirectDrawImpl_Initialize(LPDIRECTDRAW This, LPGUID pGUID) +{ + return IDirectDraw7_Initialize(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw, + IDirectDraw7, This), + pGUID); +} + +static HRESULT WINAPI +IDirectDraw2Impl_Initialize(LPDIRECTDRAW2 This, LPGUID pGUID) +{ + return IDirectDraw7_Initialize(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw2, + IDirectDraw7, This), + pGUID); +} + +static HRESULT WINAPI +IDirectDraw4Impl_Initialize(LPDIRECTDRAW4 This, LPGUID pGUID) +{ + return IDirectDraw7_Initialize(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw4, + IDirectDraw7, This), + pGUID); +} + +static HRESULT WINAPI +IDirectDrawImpl_RestoreDisplayMode(LPDIRECTDRAW This) +{ + return IDirectDraw7_RestoreDisplayMode(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw, + IDirectDraw7, + This)); +} + +static HRESULT WINAPI +IDirectDraw2Impl_RestoreDisplayMode(LPDIRECTDRAW2 This) +{ + return IDirectDraw7_RestoreDisplayMode(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw2, + IDirectDraw7, + This)); +} + +static HRESULT WINAPI +IDirectDraw4Impl_RestoreDisplayMode(LPDIRECTDRAW4 This) +{ + return IDirectDraw7_RestoreDisplayMode(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw4, + IDirectDraw7, + This)); +} + +static HRESULT WINAPI +IDirectDrawImpl_SetCooperativeLevel(LPDIRECTDRAW This, HWND hWnd, + DWORD dwFlags) +{ + return IDirectDraw7_SetCooperativeLevel(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw, + IDirectDraw7, + This), + hWnd, dwFlags); +} + +static HRESULT WINAPI +IDirectDraw2Impl_SetCooperativeLevel(LPDIRECTDRAW2 This, HWND hWnd, + DWORD dwFlags) +{ + return IDirectDraw7_SetCooperativeLevel(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw2, + IDirectDraw7, + This), + hWnd, dwFlags); +} + +static HRESULT WINAPI +IDirectDraw4Impl_SetCooperativeLevel(LPDIRECTDRAW4 This, HWND hWnd, + DWORD dwFlags) +{ + return IDirectDraw7_SetCooperativeLevel(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw4, + IDirectDraw7, + This), + hWnd, dwFlags); +} + +static HRESULT WINAPI +IDirectDrawImpl_SetDisplayMode(LPDIRECTDRAW This, DWORD a, DWORD b, DWORD c) +{ + return IDirectDraw7_SetDisplayMode(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw, + IDirectDraw7, + This), + a, b, c, 0, 0); +} + +static HRESULT WINAPI +IDirectDraw2Impl_SetDisplayMode(LPDIRECTDRAW2 This, DWORD a, DWORD b, DWORD c, + DWORD d, DWORD e) +{ + return IDirectDraw7_SetDisplayMode(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw2, + IDirectDraw7, + This), + a, b, c, d, e); +} + +static HRESULT WINAPI +IDirectDraw4Impl_SetDisplayMode(LPDIRECTDRAW4 This, DWORD a, DWORD b, DWORD c, + DWORD d, DWORD e) +{ + return IDirectDraw7_SetDisplayMode(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw4, + IDirectDraw7, + This), + a, b, c, d, e); +} + +static HRESULT WINAPI +IDirectDrawImpl_WaitForVerticalBlank(LPDIRECTDRAW This, DWORD dwFlags, + HANDLE hEvent) +{ + return IDirectDraw7_WaitForVerticalBlank(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw, + IDirectDraw7, + This), + dwFlags, hEvent); +} + +static HRESULT WINAPI +IDirectDraw2Impl_WaitForVerticalBlank(LPDIRECTDRAW2 This, DWORD dwFlags, + HANDLE hEvent) +{ + return IDirectDraw7_WaitForVerticalBlank(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw2, + IDirectDraw7, + This), + dwFlags, hEvent); +} + +static HRESULT WINAPI +IDirectDraw4Impl_WaitForVerticalBlank(LPDIRECTDRAW4 This, DWORD dwFlags, + HANDLE hEvent) +{ + return IDirectDraw7_WaitForVerticalBlank(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw4, + IDirectDraw7, + This), + dwFlags, hEvent); +} + +static HRESULT WINAPI +IDirectDraw2Impl_GetAvailableVidMem(LPDIRECTDRAW2 This, LPDDSCAPS pCaps, + LPDWORD pdwTotal, LPDWORD pdwFree) +{ + DDSCAPS2 Caps2; + DDRAW_Convert_DDSCAPS_1_To_2(pCaps, &Caps2); + + return IDirectDraw7_GetAvailableVidMem(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw2, + IDirectDraw7, + This), + &Caps2, pdwTotal, pdwFree); +} + +static HRESULT WINAPI +IDirectDraw4Impl_GetAvailableVidMem(LPDIRECTDRAW4 This, LPDDSCAPS2 pCaps, + LPDWORD pdwTotal, LPDWORD pdwFree) +{ + return IDirectDraw7_GetAvailableVidMem(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw2, + IDirectDraw7, + This), + pCaps, pdwTotal, pdwFree); +} + +static HRESULT WINAPI +IDirectDraw4Impl_GetSurfaceFromDC(LPDIRECTDRAW4 This, HDC hDC, + LPDIRECTDRAWSURFACE4 *pSurf) +{ + return IDirectDraw7_GetSurfaceFromDC(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw4, + IDirectDraw7, + This), + hDC, (LPDIRECTDRAWSURFACE7 *)pSurf); +} + +static HRESULT WINAPI +IDirectDraw4Impl_RestoreAllSurfaces(LPDIRECTDRAW4 This) +{ + return IDirectDraw7_RestoreAllSurfaces(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw4, + IDirectDraw7, + This)); +} + +static HRESULT WINAPI +IDirectDraw4Impl_TestCooperativeLevel(LPDIRECTDRAW4 This) +{ + return IDirectDraw7_TestCooperativeLevel(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw4, + IDirectDraw7, + This)); +} + +static HRESULT WINAPI +IDirectDraw4Impl_GetDeviceIdentifier(LPDIRECTDRAW4 This, + LPDDDEVICEIDENTIFIER pDDDI, DWORD dwFlags) +{ + DDDEVICEIDENTIFIER2 DDDI2; + HRESULT hr; + + hr = IDirectDraw7_GetDeviceIdentifier(COM_INTERFACE_CAST(IDirectDrawImpl, + IDirectDraw4, + IDirectDraw7, + This), + &DDDI2, dwFlags); + + DDRAW_Convert_DDDEVICEIDENTIFIER_2_To_1(pDDDI, &DDDI2); + + return hr; +} + +ICOM_VTABLE(IDirectDraw) DDRAW_IDirectDraw_VTable = +{ + ICOM_MSVTABLE_COMPAT_DummyRTTIVALUE + IDirectDrawImpl_QueryInterface, + IDirectDrawImpl_AddRef, + IDirectDrawImpl_Release, + IDirectDrawImpl_Compact, + IDirectDrawImpl_CreateClipper, + IDirectDrawImpl_CreatePalette, + IDirectDrawImpl_CreateSurface, + IDirectDrawImpl_DuplicateSurface, + IDirectDrawImpl_EnumDisplayModes, + IDirectDrawImpl_EnumSurfaces, + IDirectDrawImpl_FlipToGDISurface, + IDirectDrawImpl_GetCaps, + IDirectDrawImpl_GetDisplayMode, + IDirectDrawImpl_GetFourCCCodes, + IDirectDrawImpl_GetGDISurface, + IDirectDrawImpl_GetMonitorFrequency, + IDirectDrawImpl_GetScanLine, + IDirectDrawImpl_GetVerticalBlankStatus, + IDirectDrawImpl_Initialize, + IDirectDrawImpl_RestoreDisplayMode, + IDirectDrawImpl_SetCooperativeLevel, + IDirectDrawImpl_SetDisplayMode, + IDirectDrawImpl_WaitForVerticalBlank, +}; + +ICOM_VTABLE(IDirectDraw2) DDRAW_IDirectDraw2_VTable = +{ + ICOM_MSVTABLE_COMPAT_DummyRTTIVALUE + IDirectDraw2Impl_QueryInterface, + IDirectDraw2Impl_AddRef, + IDirectDraw2Impl_Release, + IDirectDraw2Impl_Compact, + IDirectDraw2Impl_CreateClipper, + IDirectDraw2Impl_CreatePalette, + IDirectDraw2Impl_CreateSurface, + IDirectDraw2Impl_DuplicateSurface, + IDirectDraw2Impl_EnumDisplayModes, + IDirectDraw2Impl_EnumSurfaces, + IDirectDraw2Impl_FlipToGDISurface, + IDirectDraw2Impl_GetCaps, + IDirectDraw2Impl_GetDisplayMode, + IDirectDraw2Impl_GetFourCCCodes, + IDirectDraw2Impl_GetGDISurface, + IDirectDraw2Impl_GetMonitorFrequency, + IDirectDraw2Impl_GetScanLine, + IDirectDraw2Impl_GetVerticalBlankStatus, + IDirectDraw2Impl_Initialize, + IDirectDraw2Impl_RestoreDisplayMode, + IDirectDraw2Impl_SetCooperativeLevel, + IDirectDraw2Impl_SetDisplayMode, + IDirectDraw2Impl_WaitForVerticalBlank, + IDirectDraw2Impl_GetAvailableVidMem +}; + +ICOM_VTABLE(IDirectDraw4) DDRAW_IDirectDraw4_VTable = +{ + ICOM_MSVTABLE_COMPAT_DummyRTTIVALUE + IDirectDraw4Impl_QueryInterface, + IDirectDraw4Impl_AddRef, + IDirectDraw4Impl_Release, + IDirectDraw4Impl_Compact, + IDirectDraw4Impl_CreateClipper, + IDirectDraw4Impl_CreatePalette, + IDirectDraw4Impl_CreateSurface, + IDirectDraw4Impl_DuplicateSurface, + IDirectDraw4Impl_EnumDisplayModes, + IDirectDraw4Impl_EnumSurfaces, + IDirectDraw4Impl_FlipToGDISurface, + IDirectDraw4Impl_GetCaps, + IDirectDraw4Impl_GetDisplayMode, + IDirectDraw4Impl_GetFourCCCodes, + IDirectDraw4Impl_GetGDISurface, + IDirectDraw4Impl_GetMonitorFrequency, + IDirectDraw4Impl_GetScanLine, + IDirectDraw4Impl_GetVerticalBlankStatus, + IDirectDraw4Impl_Initialize, + IDirectDraw4Impl_RestoreDisplayMode, + IDirectDraw4Impl_SetCooperativeLevel, + IDirectDraw4Impl_SetDisplayMode, + IDirectDraw4Impl_WaitForVerticalBlank, + IDirectDraw4Impl_GetAvailableVidMem, + IDirectDraw4Impl_GetSurfaceFromDC, + IDirectDraw4Impl_RestoreAllSurfaces, + IDirectDraw4Impl_TestCooperativeLevel, + IDirectDraw4Impl_GetDeviceIdentifier +}; diff --git a/dlls/ddraw/ddraw/user.c b/dlls/ddraw/ddraw/user.c new file mode 100644 index 00000000000..e8c78fc7e97 --- /dev/null +++ b/dlls/ddraw/ddraw/user.c @@ -0,0 +1,540 @@ +/* DirectDraw driver for User-based primary surfaces + * + * Copyright 2000 TransGaming Technologies Inc. + */ + +#include "config.h" +#include "debugtools.h" +#include + +#include + +#include "ddraw_private.h" +#include "ddraw/main.h" +#include "ddraw/user.h" +#include "dclipper/main.h" +#include "dpalette/main.h" +#include "dsurface/main.h" +#include "dsurface/dib.h" +#include "dsurface/user.h" + +DEFAULT_DEBUG_CHANNEL(ddraw); + +static ICOM_VTABLE(IDirectDraw7) User_DirectDraw_VTable; + +static const DDDEVICEIDENTIFIER2 user_device = +{ + "User Driver", + "WINE DirectDraw on User (and GDI)", + { { 0x00010001, 0x00010001 } }, + 0, 0, 0, 0, + /* fe38440c-8969-4283-bc73-749e7bc3c2eb */ + {0xfe38440c,0x8969,0x428e, {0x73,0xbc,0x74,0x9e,0x7b,0xc3,0xc2,0xeb}}, + 0 +}; + +static const DDPIXELFORMAT pixelformats[] = +{ + /* 8bpp paletted */ + { sizeof(DDPIXELFORMAT), DDPF_RGB|DDPF_PALETTEINDEXED8, 0, { 8 } }, + /* 15bpp 5/5/5 */ + { sizeof(DDPIXELFORMAT), DDPF_RGB, 0, { 16 }, { 0x7C00 }, { 0x3E0 }, + { 0x1F } }, + /* 16bpp 5/6/5 */ + { sizeof(DDPIXELFORMAT), DDPF_RGB, 0, { 16 }, { 0xF800 }, { 0x7E0 }, + { 0x1F } }, + /* 24bpp 8/8/8 */ + { sizeof(DDPIXELFORMAT), DDPF_RGB, 0, { 24 }, { 0xFF0000 }, + { 0x00FF00 }, { 0x0000FF } }, + /* 32bpp 8/8/8 */ + { sizeof(DDPIXELFORMAT), DDPF_RGB, 0, { 32 }, { 0xFF0000 }, + { 0x00FF00 }, { 0x0000FF } } +}; + +HRESULT User_DirectDraw_Create(const GUID* pGUID, LPDIRECTDRAW7* pIface, + IUnknown* pUnkOuter, BOOL ex); +HRESULT User_DirectDraw_Initialize(IDirectDrawImpl*, const GUID*); + +static const ddraw_driver user_driver = +{ + &user_device, + 10, + User_DirectDraw_Create, + User_DirectDraw_Initialize +}; + +BOOL DDRAW_User_Init(HINSTANCE hInstDLL, DWORD fdwReason, LPVOID lpv) +{ + if (fdwReason == DLL_PROCESS_ATTACH) + DDRAW_register_driver(&user_driver); + + return TRUE; +} + +/* If you change this function, you probably want to change the enumeration + * code in EnumDisplayModes. */ +static BOOL +IsValidDisplayMode(DWORD dwWidth, DWORD dwHeight, DWORD dwBPP, + DWORD dwRefreshRate, DWORD dwFlags) +{ + if (dwWidth > GetSystemMetrics(SM_CXSCREEN) + || dwHeight > GetSystemMetrics(SM_CYSCREEN)) + return FALSE; + + switch (dwBPP) + { + case 8: + case 15: + case 16: + case 24: + case 32: + break; + + default: + return FALSE; + } + + return TRUE; +} + +static const DDPIXELFORMAT* pixelformat_for_depth(DWORD depth) +{ + switch (depth) + { + case 8: return pixelformats + 0; + case 15: return pixelformats + 1; + case 16: return pixelformats + 2; + case 24: return pixelformats + 3; + case 32: return pixelformats + 4; + default: return NULL; + } +} + +/* Not called from the vtable. */ +HRESULT User_DirectDraw_Construct(IDirectDrawImpl *This, BOOL ex) +{ + HRESULT hr; + DWORD depth; + HDC hDC; + + TRACE("(%p,%d)\n",This,ex); + + hr = Main_DirectDraw_Construct(This, ex); + if (FAILED(hr)) return hr; + + This->final_release = User_DirectDraw_final_release; + + This->create_primary = User_DirectDraw_create_primary; + This->create_backbuffer = User_DirectDraw_create_backbuffer; + + hDC = CreateDCA("DISPLAY", NULL, NULL, NULL); + depth = GetDeviceCaps(hDC, BITSPIXEL) * GetDeviceCaps(hDC, PLANES); + DeleteDC(hDC); + + This->width = GetSystemMetrics(SM_CXSCREEN); + This->height = GetSystemMetrics(SM_CYSCREEN); + This->pitch = DDRAW_width_bpp_to_pitch(This->width, depth); + This->pixelformat = *pixelformat_for_depth(depth); + + This->orig_width = This->width; + This->orig_height = This->height; + This->orig_pitch = This->pitch; + This->orig_pixelformat = This->pixelformat; + + ICOM_INIT_INTERFACE(This, IDirectDraw7, User_DirectDraw_VTable); + + return S_OK; +} + +/* This function is called from DirectDrawCreate(Ex) on the most-derived + * class to start construction. + * Not called from the vtable. */ +HRESULT User_DirectDraw_Create(const GUID* pGUID, LPDIRECTDRAW7* pIface, + IUnknown* pUnkOuter, BOOL ex) +{ + HRESULT hr; + IDirectDrawImpl* This; + + assert(pUnkOuter == NULL); + + This = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, + sizeof(IDirectDrawImpl) + sizeof(User_DirectDrawImpl)); + if (This == NULL) return E_OUTOFMEMORY; + + /* Note that this relation does *not* hold true if the DD object was + * CoCreateInstanced then Initialized. */ + This->private = (User_DirectDrawImpl *)(This+1); + + hr = User_DirectDraw_Construct(This, ex); + if (FAILED(hr)) + HeapFree(GetProcessHeap(), 0, This); + else + *pIface = ICOM_INTERFACE(This, IDirectDraw7); + + return hr; +} + +/* This function is called from Uninit_DirectDraw_Initialize on the + * most-derived-class to start initialization. + * Not called from the vtable. */ +HRESULT User_DirectDraw_Initialize(IDirectDrawImpl *This, const GUID* guid) +{ + HRESULT hr; + This->private = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, + sizeof(User_DirectDrawImpl)); + if (This->private == NULL) return E_OUTOFMEMORY; + + hr = User_DirectDraw_Construct(This, TRUE); /* XXX ex? */ + if (FAILED(hr)) + { + HeapFree(GetProcessHeap(), 0, This->private); + return hr; + } + + return DD_OK; +} + +/* Called from an internal function pointer. */ +void User_DirectDraw_final_release(IDirectDrawImpl *This) +{ + Main_DirectDraw_final_release(This); +} + +/* Compact: generic */ +/* CreateClipper: generic */ +/* CreatePalette: generic (with callback) */ +/* CreateSurface: generic (with callbacks) */ + +HRESULT +User_DirectDraw_create_primary(IDirectDrawImpl* This, + const DDSURFACEDESC2* pDDSD, + LPDIRECTDRAWSURFACE7* ppSurf, + IUnknown* pUnkOuter) +{ + return User_DirectDrawSurface_Create(This, pDDSD, ppSurf, pUnkOuter); +} + +HRESULT +User_DirectDraw_create_backbuffer(IDirectDrawImpl* This, + const DDSURFACEDESC2* pDDSD, + LPDIRECTDRAWSURFACE7* ppSurf, + IUnknown* pUnkOuter, + IDirectDrawSurfaceImpl* primary) +{ + return User_DirectDrawSurface_Create(This, pDDSD, ppSurf, pUnkOuter); +} + +/* DuplicateSurface: generic */ + +/* Derived from Xlib_IDirectDraw2Impl_EnumDisplayModes. + * Very fake: just enumerate some arbitrary modes. + * + * The screen sizes are plausible-looking screen sizes and will be limited + * by (virtual) screen size. + * + * The depths are whatever DIBsections support on the client side. + * Should they be limited by screen depth? + */ +HRESULT WINAPI +User_DirectDraw_EnumDisplayModes(LPDIRECTDRAW7 iface, DWORD dwFlags, + LPDDSURFACEDESC2 pDDSD, LPVOID context, + LPDDENUMMODESCALLBACK2 callback) +{ + struct mode + { + int width; + int height; + }; + + static const struct mode modes[] = + { + { 512, 384 }, { 640, 400 }, { 640, 480 }, { 800, 600 }, { 1024, 768 }, + { 1152, 864 }, { 1280, 1024 }, { 1600, 1200 } + }; + + static const int num_modes = sizeof(modes)/sizeof(modes[0]); + + static const int num_pixelformats + = sizeof(pixelformats)/sizeof(pixelformats[0]); + + DDSURFACEDESC2 callback_sd; + + int max_width, max_height; + int i, j; + + TRACE("(%p)->(0x%08lx,%p,%p,%p)\n",iface,dwFlags,pDDSD,context,callback); + + /* Unfortunately this is the virtual screen size, not physical. */ + max_width = GetSystemMetrics(SM_CXSCREEN); + max_height = GetSystemMetrics(SM_CYSCREEN); + + ZeroMemory(&callback_sd, sizeof(callback_sd)); + callback_sd.dwSize = sizeof(callback_sd); + + callback_sd.dwFlags = DDSD_HEIGHT|DDSD_WIDTH|DDSD_PIXELFORMAT|DDSD_CAPS + | DDSD_PITCH; + + if (dwFlags & DDEDM_REFRESHRATES) + callback_sd.dwFlags |= DDSD_REFRESHRATE; + + callback_sd.u2.dwRefreshRate = 60.0; + + for (i = 0; i < num_modes; i++) + { + if (modes[i].width > max_width || modes[i].height > max_height) + continue; + + callback_sd.dwHeight = modes[i].height; + callback_sd.dwWidth = modes[i].width; + + TRACE("- mode: %ldx%ld\n", callback_sd.dwWidth, callback_sd.dwHeight); + for (j = 0; j < num_pixelformats; j++) + { + callback_sd.u1.lPitch + = DDRAW_width_bpp_to_pitch(modes[i].width, + pixelformats[j].u1.dwRGBBitCount); + + callback_sd.u4.ddpfPixelFormat = pixelformats[j]; + + callback_sd.ddsCaps.dwCaps = 0; + if (pixelformats[j].dwFlags & DDPF_PALETTEINDEXED8) /* ick */ + callback_sd.ddsCaps.dwCaps |= DDSCAPS_PALETTE; + + assert(IsValidDisplayMode(callback_sd.dwWidth, + callback_sd.dwHeight, + callback_sd.u4.ddpfPixelFormat.u1.dwRGBBitCount, + 0, 0)); + + TRACE(" - %2ld bpp, R=%08lx G=%08lx B=%08lx\n", + callback_sd.u4.ddpfPixelFormat.u1.dwRGBBitCount, + callback_sd.u4.ddpfPixelFormat.u2.dwRBitMask, + callback_sd.u4.ddpfPixelFormat.u3.dwGBitMask, + callback_sd.u4.ddpfPixelFormat.u4.dwBBitMask); + if (callback(&callback_sd, context) == DDENUMRET_CANCEL) + return DD_OK; + } + } + + return DD_OK; +} + +/* EnumSurfaces: generic */ +/* FlipToGDISurface: ??? */ + +HRESULT WINAPI +User_DirectDraw_GetCaps(LPDIRECTDRAW7 iface, LPDDCAPS pDriverCaps, + LPDDCAPS pHELCaps) +{ +/* Based on my guesses for what is appropriate with some clues from the + * NVidia driver. Not everything is actually implemented yet. + * NV has but we don't: Overlays, Video Ports, DDCAPS_READSCANLINE, + * DDCAPS2_CERTIFIED (heh), DDSCAPS2_NONLOCALVIDMEM, DDSCAPS2_COPYFOURCC. + * It actually has no FX alpha caps. + * Oddly, it doesn't list DDPCAPS_PRIMARYSURFACE. + * And the HEL caps make little sense. + */ +#define BLIT_CAPS (DDCAPS_BLT | DDCAPS_BLTCOLORFILL | DDCAPS_BLTDEPTHFILL \ + | DDCAPS_BLTSTRETCH | DDCAPS_CANBLTSYSMEM | DDCAPS_CANCLIP \ + | DDCAPS_CANCLIPSTRETCHED | DDCAPS_COLORKEY \ + | DDCAPS_COLORKEYHWASSIST) + +#define CKEY_CAPS (DDCKEYCAPS_DESTBLT | DDCKEYCAPS_SRCBLT) + +#define FX_CAPS (DDFXCAPS_BLTALPHA | DDFXCAPS_BLTMIRRORLEFTRIGHT \ + | DDFXCAPS_BLTMIRRORUPDOWN | DDFXCAPS_BLTROTATION90 \ + | DDFXCAPS_BLTSHRINKX | DDFXCAPS_BLTSHRINKXN \ + | DDFXCAPS_BLTSHRINKY | DDFXCAPS_BLTSHRINKXN \ + | DDFXCAPS_BLTSTRETCHX | DDFXCAPS_BLTSTRETCHXN \ + | DDFXCAPS_BLTSTRETCHY | DDFXCAPS_BLTSTRETCHYN) + +#if 0 +#define ROPS { SRCCOPY, SRCPAINT, SRCAND, SRCINVERT, SRCERASE, NOTSRCCOPY, \ + NOTSRCERASE, MERGEPAINT, BLACKNESS, WHITENESS, } +#else +#define ROPS { 0, } +#endif + + static const DDCAPS caps = + { sizeof(DDCAPS), + DDCAPS_3D | DDCAPS_GDI | DDCAPS_PALETTE | BLIT_CAPS, + DDCAPS2_CANMANAGETEXTURE | DDCAPS2_CANRENDERWINDOWED | DDCAPS2_CERTIFIED + | DDCAPS2_NOPAGELOCKREQUIRED | DDCAPS2_PRIMARYGAMMA + | DDCAPS2_WIDESURFACES, + CKEY_CAPS, + FX_CAPS, + 0, /* dwFXAlphaCaps */ + DDPCAPS_8BIT | DDPCAPS_PRIMARYSURFACE, + 0, /* dwSVCaps */ + 0, /* ? dwAlphaBitConstBitDepths */ + 0, /* ? dwAlphaBitPixelPitDepths */ + 0, /* ? dwAlphaBltSurfaceBitDepths */ + 0, /* ? dwAlphaOverlayConstBitDepths */ + 0, /* ? dwAlphaOverlayPixelBitDepths */ + 0, /* ? dwAlphaOverlaySurfaceBitDepths */ + DDBD_16, /* ? dwZBufferBitDepths */ + 16*1024*1024, /* dwVidMemTotal */ + 16*1024*1024, /* dwVidMemFree */ + 0, /* dwMaxVisibleOverlays */ + 0, /* dwCurrVisibleOverlays */ + 0, /* dwNumFourCCCodes */ + 0, /* dwAlignBoundarySrc */ + 0, /* dwAlignSizeSrc */ + 0, /* dwAlignBoundaryDest */ + 0, /* dwAlignSizeDest */ + 0, /* dwAlignStrideAlign */ + ROPS, /* XXX dwRops[DD_ROP_SPACE] */ + { 0, }, /* XXX ddsOldCaps */ + 1000, /* dwMinOverlayStretch */ + 1000, /* dwMaxOverlayStretch */ + 1000, /* dwMinLiveVideoStretch */ + 1000, /* dwMaxLiveVideoStretch */ + 1000, /* dwMinHwCodecStretch */ + 1000, /* dwMaxHwCodecStretch */ + 0, 0, 0, /* dwReserved1, 2, 3 */ + BLIT_CAPS, /* dwSVBCaps */ + CKEY_CAPS, /* dwSVBCKeyCaps */ + FX_CAPS, /* dwSVBFXCaps */ + ROPS, /* dwSVBRops */ + BLIT_CAPS, /* dwVSBCaps */ + CKEY_CAPS, /* dwVSBCKeyCaps */ + FX_CAPS, /* dwVSBFXCaps */ + ROPS, /* dwVSBRops */ + BLIT_CAPS, /* dwSSBCaps */ + CKEY_CAPS, /* dwSSBCKeyCaps */ + FX_CAPS, /* dwSSBFXCaps */ + ROPS, /* dwSSBRops */ + 0, /* dwMaxVideoPorts */ + 0, /* dwCurrVideoPorts */ + 0, /* ? dwSVBCaps2 */ + BLIT_CAPS, /* ? dwNLVBCaps */ + 0, /* ? dwNLVBCaps2 */ + CKEY_CAPS, /* dwNLVBCKeyCaps */ + FX_CAPS, /* dwNLVBFXCaps */ + ROPS, /* dwNLVBRops */ + { /* ddsCaps */ + DDSCAPS_3DDEVICE | DDSCAPS_ALPHA | DDSCAPS_BACKBUFFER | DDSCAPS_FLIP + | DDSCAPS_FRONTBUFFER | DDSCAPS_MIPMAP | DDSCAPS_OFFSCREENPLAIN + | DDSCAPS_PALETTE | DDSCAPS_PRIMARYSURFACE | DDSCAPS_SYSTEMMEMORY + | DDSCAPS_TEXTURE | DDSCAPS_VIDEOMEMORY | DDSCAPS_VISIBLE + | DDSCAPS_ZBUFFER, + DDSCAPS2_CUBEMAP, + 0, + 0 + } + }; + +#undef BLIT_CAPS +#undef CKEY_CAPS +#undef FX_CAPS +#undef ROPS + + ICOM_THIS(IDirectDrawImpl, iface); + + TRACE("(%p)->(%p,%p)\n",This,pDriverCaps,pHELCaps); + if ((pDriverCaps != NULL && pDriverCaps->dwSize != sizeof(DDCAPS)) + || (pHELCaps != NULL && pHELCaps->dwSize != sizeof(DDCAPS))) + { + FIXME("unsupported structure versions: %lu/%lu vs %u\n", + pDriverCaps ? pDriverCaps->dwSize : sizeof(DDCAPS), + pHELCaps ? pHELCaps->dwSize : sizeof(DDCAPS), + sizeof(DDCAPS)); + /* The old DD caps structures are contained in the DX7 SDK, and since + * it's changed every version, we should probably try to support the + * old ones. */ + } + + if (pDriverCaps != NULL) + memcpy(pDriverCaps, &caps, pDriverCaps->dwSize); + + if (pHELCaps != NULL) + memcpy(pHELCaps, &caps, pHELCaps->dwSize); + + return DD_OK; +} + +HRESULT WINAPI +User_DirectDraw_GetDeviceIdentifier(LPDIRECTDRAW7 iface, + LPDDDEVICEIDENTIFIER2 pDDDI, + DWORD dwFlags) +{ + TRACE("(%p)->(%p,%08lx)\n",iface,pDDDI,dwFlags); + *pDDDI = user_device; + return DD_OK; +} + +/* GetDisplayMode: generic */ +/* GetFourCCCodes: generic */ +/* GetGDISurface: ??? */ +/* GetMonitorFrequency: generic */ +/* GetScanLine: generic */ +/* GetSurfaceFromDC: generic */ +/* GetVerticalBlankStatus: generic */ +/* Initialize: generic */ +/* RestoreAllSurfaces: generic */ +/* RestoreDisplayMode: generic */ +/* SetCooperativeLevel: ??? */ + +HRESULT WINAPI +User_DirectDraw_SetDisplayMode(LPDIRECTDRAW7 iface, DWORD dwWidth, + DWORD dwHeight, DWORD dwBPP, + DWORD dwRefreshRate, DWORD dwFlags) +{ + ICOM_THIS(IDirectDrawImpl, iface); + + const DDPIXELFORMAT* pixelformat; + LONG pitch; + + TRACE("(%p)->(%ldx%ldx%ld,%ld Hz,%08lx)\n",This,dwWidth,dwHeight,dwBPP,dwRefreshRate,dwFlags); + if (!IsValidDisplayMode(dwWidth, dwHeight, dwBPP, dwRefreshRate, dwFlags)) + return DDERR_INVALIDMODE; + + pixelformat = pixelformat_for_depth(dwBPP); + if (pixelformat == NULL) + { + assert(0); + return DDERR_GENERIC; + } + + pitch = DDRAW_width_bpp_to_pitch(dwWidth, dwBPP); + + return Main_DirectDraw_SetDisplayMode(iface, dwWidth, dwHeight, pitch, + dwRefreshRate, dwFlags, pixelformat); +} + +/* StartModeTest: ??? */ +/* TestCooperativeLevel: generic? */ +/* WaitForVerticalBlank: ??? */ + +static ICOM_VTABLE(IDirectDraw7) User_DirectDraw_VTable = +{ + Main_DirectDraw_QueryInterface, + Main_DirectDraw_AddRef, + Main_DirectDraw_Release, + Main_DirectDraw_Compact, + Main_DirectDraw_CreateClipper, + Main_DirectDraw_CreatePalette, + Main_DirectDraw_CreateSurface, + Main_DirectDraw_DuplicateSurface, + User_DirectDraw_EnumDisplayModes, + Main_DirectDraw_EnumSurfaces, + Main_DirectDraw_FlipToGDISurface, + User_DirectDraw_GetCaps, + Main_DirectDraw_GetDisplayMode, + Main_DirectDraw_GetFourCCCodes, + Main_DirectDraw_GetGDISurface, + Main_DirectDraw_GetMonitorFrequency, + Main_DirectDraw_GetScanLine, + Main_DirectDraw_GetVerticalBlankStatus, + Main_DirectDraw_Initialize, + Main_DirectDraw_RestoreDisplayMode, + Main_DirectDraw_SetCooperativeLevel, + User_DirectDraw_SetDisplayMode, + Main_DirectDraw_WaitForVerticalBlank, + Main_DirectDraw_GetAvailableVidMem, + Main_DirectDraw_GetSurfaceFromDC, + Main_DirectDraw_RestoreAllSurfaces, + Main_DirectDraw_TestCooperativeLevel, + User_DirectDraw_GetDeviceIdentifier, + Main_DirectDraw_StartModeTest, + Main_DirectDraw_EvaluateMode +}; diff --git a/dlls/ddraw/ddraw/user.h b/dlls/ddraw/ddraw/user.h new file mode 100644 index 00000000000..ff15a64c55b --- /dev/null +++ b/dlls/ddraw/ddraw/user.h @@ -0,0 +1,50 @@ +/* Copyright 2000 TransGaming Technologies Inc. */ + +#ifndef WINE_DDRAW_DDRAW_USER_H_INCLUDED +#define WINE_DDRAW_DDRAW_USER_H_INCLUDED + +#define USER_DDRAW_PRIV(ddraw) ((User_DirectDrawImpl*)((ddraw)->private)) +#define USER_DDRAW_PRIV_VAR(name,ddraw) \ + User_DirectDrawImpl* name = USER_DDRAW_PRIV(ddraw) + +typedef struct +{ + /* empty */ +} User_DirectDrawImpl_Part; + +typedef struct +{ + User_DirectDrawImpl_Part user; +} User_DirectDrawImpl; + +void User_DirectDraw_final_release(IDirectDrawImpl* This); +HRESULT User_DirectDraw_create_primary(IDirectDrawImpl* This, + const DDSURFACEDESC2* pDDSD, + LPDIRECTDRAWSURFACE7* ppSurf, + LPUNKNOWN pOuter); +HRESULT User_DirectDraw_create_backbuffer(IDirectDrawImpl* This, + const DDSURFACEDESC2* pDDSD, + LPDIRECTDRAWSURFACE7* ppSurf, + LPUNKNOWN pOuter, + IDirectDrawSurfaceImpl* primary); +HRESULT User_DirectDraw_Construct(IDirectDrawImpl *This, BOOL ex); +HRESULT User_DirectDraw_Create(const GUID* pGUID, LPDIRECTDRAW7* pIface, + IUnknown* pUnkOuter, BOOL ex); + +HRESULT WINAPI +User_DirectDraw_EnumDisplayModes(LPDIRECTDRAW7 iface, DWORD dwFlags, + LPDDSURFACEDESC2 pDDSD, LPVOID context, + LPDDENUMMODESCALLBACK2 callback); +HRESULT WINAPI +User_DirectDraw_GetCaps(LPDIRECTDRAW7 iface, LPDDCAPS pDriverCaps, + LPDDCAPS pHELCaps); +HRESULT WINAPI +User_DirectDraw_GetDeviceIdentifier(LPDIRECTDRAW7 iface, + LPDDDEVICEIDENTIFIER2 pDDDI, + DWORD dwFlags); +HRESULT WINAPI +User_DirectDraw_SetDisplayMode(LPDIRECTDRAW7 iface, DWORD dwWidth, + DWORD dwHeight, DWORD dwBPP, + DWORD dwRefreshRate, DWORD dwFlags); + +#endif diff --git a/dlls/ddraw/ddraw/x11.c b/dlls/ddraw/ddraw/x11.c deleted file mode 100644 index b827e81aa91..00000000000 --- a/dlls/ddraw/ddraw/x11.c +++ /dev/null @@ -1,1335 +0,0 @@ -/* DirectDraw IDirectDraw Xlib interface - * - * Copyright 1997-2000 Marcus Meissner - * Copyright 1998-2000 Lionel Ulmer (most of Direct3D stuff) - */ -/* - * This file contains the Xlib specific interface functions. - */ - -#include "config.h" - -#include -#include -#include -#include -#include -#include - -#include "winerror.h" -#include "ddraw.h" -#include "d3d.h" -#include "win.h" -#include "debugtools.h" -#include "options.h" - -DEFAULT_DEBUG_CHANNEL(ddraw); - -#include "x11_private.h" - -#define DDPRIVATE(x) x11_dd_private *ddpriv = ((x11_dd_private*)(x)->d->private) -#define DPPRIVATE(x) x11_dp_private *dppriv = ((x11_dp_private*)(x)->private) -#define DSPRIVATE(x) x11_ds_private *dspriv = ((x11_ds_private*)(x)->private) - -static inline BOOL get_option( const char *name, BOOL def ) { - return PROFILE_GetWineIniBool( "x11drv", name, def ); -} - -int _common_depth_to_pixelformat(DWORD depth,LPDIRECTDRAW ddraw) -{ - ICOM_THIS(IDirectDrawImpl,ddraw); - XVisualInfo *vi; - XPixmapFormatValues *pf; - XVisualInfo vt; - int nvisuals, npixmap, i; - int match = 0; - int index = -2; - DDPIXELFORMAT *pixelformat = &(This->d->directdraw_pixelformat); - DDPIXELFORMAT *screen_pixelformat = &(This->d->screen_pixelformat); - - This->d->pixel_convert = NULL; - This->d->palette_convert = NULL; - - vi = TSXGetVisualInfo(display, VisualNoMask, &vt, &nvisuals); - pf = TSXListPixmapFormats(display, &npixmap); - - for (i = 0; i < npixmap; i++) { - if (pf[i].depth == depth) { - int j; - - for (j = 0; j < nvisuals; j++) { - if (vi[j].depth == pf[i].depth) { - pixelformat->dwSize = sizeof(*pixelformat); - if (depth == 8) { - pixelformat->dwFlags = DDPF_PALETTEINDEXED8|DDPF_RGB; - pixelformat->u1.dwRBitMask = 0; - pixelformat->u2.dwGBitMask = 0; - pixelformat->u3.dwBBitMask = 0; - } else { - pixelformat->dwFlags = DDPF_RGB; - pixelformat->u1.dwRBitMask = vi[j].red_mask; - pixelformat->u2.dwGBitMask = vi[j].green_mask; - pixelformat->u3.dwBBitMask = vi[j].blue_mask; - } - pixelformat->dwFourCC = 0; - pixelformat->u.dwRGBBitCount = pf[i].bits_per_pixel; - pixelformat->u4.dwRGBAlphaBitMask= 0; - *screen_pixelformat = *pixelformat; - This->d->pixmap_depth = depth; - match = 1; - index = -1; - goto clean_up_and_exit; - } - } - FIXME("No visual corresponding to pixmap format (depth=%ld)!\n",depth); - } - } - - if (match == 0) { - /* We try now to find an emulated mode */ - int c; - - for (c = 0; c < sizeof(ModeEmulations) / sizeof(Convert); c++) { - if ((ModeEmulations[c].dest.depth == depth) && - (ModeEmulations[c].dest.bpp == depth) - ) { - /* Found an emulation function, now tries to find a matching visual / pixel format pair */ - for (i = 0; i < npixmap; i++) { - if ((pf[i].depth == ModeEmulations[c].screen.depth) && - (pf[i].bits_per_pixel == ModeEmulations[c].screen.bpp)) { - int j; - - for (j = 0; j < nvisuals; j++) { - if (vi[j].depth == pf[i].depth) { - screen_pixelformat->dwSize = sizeof(*screen_pixelformat); - screen_pixelformat->dwFlags = DDPF_RGB; - screen_pixelformat->dwFourCC = 0; - screen_pixelformat->u.dwRGBBitCount = pf[i].bits_per_pixel; - screen_pixelformat->u1.dwRBitMask = vi[j].red_mask; - screen_pixelformat->u2.dwGBitMask = vi[j].green_mask; - screen_pixelformat->u3.dwBBitMask = vi[j].blue_mask; - screen_pixelformat->u4.dwRGBAlphaBitMask= 0; - - pixelformat->dwSize = sizeof(*pixelformat); - pixelformat->dwFourCC = 0; - if (depth == 8) { - pixelformat->dwFlags = DDPF_RGB|DDPF_PALETTEINDEXED8; - pixelformat->u.dwRGBBitCount = 8; - pixelformat->u1.dwRBitMask = 0; - pixelformat->u2.dwGBitMask = 0; - pixelformat->u3.dwBBitMask = 0; - } else { - pixelformat->dwFlags = DDPF_RGB; - pixelformat->u.dwRGBBitCount = ModeEmulations[c].dest.bpp; - pixelformat->u1.dwRBitMask = ModeEmulations[c].dest.rmask; - pixelformat->u2.dwGBitMask = ModeEmulations[c].dest.gmask; - pixelformat->u3.dwBBitMask = ModeEmulations[c].dest.bmask; - } - pixelformat->u4.dwRGBAlphaBitMask= 0; - This->d->pixmap_depth = vi[j].depth; - match = 2; - index = c; - This->d->pixel_convert =ModeEmulations[c].funcs.pixel_convert; - This->d->palette_convert=ModeEmulations[c].funcs.palette_convert; - goto clean_up_and_exit; - } - } - } - } - } - } - ERR("No emulation found for depth %ld!\n",depth); - } - -clean_up_and_exit: - TSXFree(vi); - TSXFree(pf); - - return index; -} - -#ifdef HAVE_LIBXXF86VM -static XF86VidModeModeInfo *orig_mode = NULL; - -void -xf86vmode_setdisplaymode(DWORD width, DWORD height) { - int i, mode_count; - XF86VidModeModeInfo **all_modes, *vidmode = NULL; - XF86VidModeModeLine mod_tmp; - /* int dotclock_tmp; */ - - /* save original video mode and set fullscreen if available */ - orig_mode = (XF86VidModeModeInfo *)malloc(sizeof(XF86VidModeModeInfo)); - TSXF86VidModeGetModeLine(display, DefaultScreen(display), &orig_mode->dotclock, &mod_tmp); - orig_mode->hdisplay = mod_tmp.hdisplay; - orig_mode->hsyncstart = mod_tmp.hsyncstart; - orig_mode->hsyncend = mod_tmp.hsyncend; - orig_mode->htotal = mod_tmp.htotal; - orig_mode->vdisplay = mod_tmp.vdisplay; - orig_mode->vsyncstart = mod_tmp.vsyncstart; - orig_mode->vsyncend = mod_tmp.vsyncend; - orig_mode->vtotal = mod_tmp.vtotal; - orig_mode->flags = mod_tmp.flags; - /* copy private data to our orig_mode structure */ - orig_mode->privsize = mod_tmp.privsize; - if (orig_mode->privsize) - { - orig_mode->private = malloc(mod_tmp.privsize); - memcpy(orig_mode->private, mod_tmp.private, mod_tmp.privsize); - } - - TSXF86VidModeGetAllModeLines(display,DefaultScreen(display),&mode_count,&all_modes); - for (i=0;ihdisplay == width && - all_modes[i]->vdisplay == height - ) { - vidmode = (XF86VidModeModeInfo *)malloc(sizeof(XF86VidModeModeInfo)); - *vidmode = *(all_modes[i]); - break; - } else - TSXFree(all_modes[i]->private); - } - for (i++;iprivate); - TSXFree(all_modes); - - if (!vidmode) - WARN("Fullscreen mode not available!\n"); - - if (vidmode) { - TRACE("SwitchToMode(%dx%d)\n",vidmode->hdisplay,vidmode->vdisplay); - TSXF86VidModeSwitchToMode(display, DefaultScreen(display), vidmode); -#if 0 /* This messes up my screen (XF86_Mach64, 3.3.2.3a) for some reason, and should now be unnecessary */ - TSXF86VidModeSetViewPort(display, DefaultScreen(display), 0, 0); -#endif - } -} - -void xf86vmode_restore() { - if (!orig_mode) - return; - TSXF86VidModeSwitchToMode(display,DefaultScreen(display),orig_mode); - /* manually free the private data if it was allocated */ - if (orig_mode->privsize) - free(orig_mode->private); - - free(orig_mode); - orig_mode = NULL; -} -#else -void xf86vmode_setdisplaymode(DWORD width, DWORD height) {} -void xf86vmode_restore() {} -#endif - - -/******************************************************************************* - * IDirectDraw - */ -#ifdef HAVE_LIBXXSHM -/* Error handlers for Image creation */ -static int XShmErrorHandler(Display *dpy, XErrorEvent *event) { - XShmErrorFlag = 1; - return 0; -} - -static XImage *create_xshmimage( - IDirectDraw2Impl* This, IDirectDrawSurface4Impl* lpdsf -) { - DSPRIVATE(lpdsf); - DDPRIVATE(This); - XImage *img; - int (*WineXHandler)(Display *, XErrorEvent *); - - img = TSXShmCreateImage(display, - DefaultVisualOfScreen(X11DRV_GetXScreen()), - This->d->pixmap_depth, - ZPixmap, - NULL, - &(dspriv->shminfo), - lpdsf->s.surface_desc.dwWidth, - lpdsf->s.surface_desc.dwHeight - ); - - if (img == NULL) { - FIXME("Couldn't create XShm image (due to X11 remote display or failure).\nReverting to standard X images !\n"); - ddpriv->xshm_active = 0; - return NULL; - } - - dspriv->shminfo.shmid = shmget( IPC_PRIVATE, img->bytes_per_line * img->height, IPC_CREAT|0777 ); - - if (dspriv->shminfo.shmid < 0) { - FIXME("Couldn't create shared memory segment (due to X11 remote display or failure).\nReverting to standard X images !\n"); - ddpriv->xshm_active = 0; - TSXDestroyImage(img); - return NULL; - } - - dspriv->shminfo.shmaddr=img->data=(char*)shmat(dspriv->shminfo.shmid,0,0); - - if (img->data == (char *) -1) { - FIXME("Couldn't attach shared memory segment (due to X11 remote display or failure).\nReverting to standard X images !\n"); - ddpriv->xshm_active = 0; - TSXDestroyImage(img); - shmctl(dspriv->shminfo.shmid, IPC_RMID, 0); - return NULL; - } - dspriv->shminfo.readOnly = False; - - /* This is where things start to get trickier.... - * First, we flush the current X connections to be sure to catch all - * non-XShm related errors - */ - TSXSync(display, False); - /* Then we enter in the non-thread safe part of the tests */ - EnterCriticalSection( &X11DRV_CritSection ); - - /* Reset the error flag, sets our new error handler and try to attach - * the surface - */ - XShmErrorFlag = 0; - WineXHandler = XSetErrorHandler(XShmErrorHandler); - XShmAttach(display, &(dspriv->shminfo)); - XSync(display, False); - - /* Check the error flag */ - if (XShmErrorFlag) { - /* An error occured */ - XFlush(display); - XShmErrorFlag = 0; - XDestroyImage(img); - shmdt(dspriv->shminfo.shmaddr); - shmctl(dspriv->shminfo.shmid, IPC_RMID, 0); - XSetErrorHandler(WineXHandler); - - FIXME("Couldn't attach shared memory segment to X server (due to X11 remote display or failure).\nReverting to standard X images !\n"); - ddpriv->xshm_active = 0; - - /* Leave the critical section */ - LeaveCriticalSection( &X11DRV_CritSection ); - return NULL; - } - /* Here, to be REALLY sure, I should do a XShmPutImage to check if - * this works, but it may be a bit overkill.... - */ - XSetErrorHandler(WineXHandler); - LeaveCriticalSection( &X11DRV_CritSection ); - - shmctl(dspriv->shminfo.shmid, IPC_RMID, 0); - - if (This->d->pixel_convert != NULL) { - int bpp = PFGET_BPP(This->d->directdraw_pixelformat); - lpdsf->s.surface_desc.u1.lpSurface = VirtualAlloc( - NULL, - lpdsf->s.surface_desc.dwWidth * - lpdsf->s.surface_desc.dwHeight * - bpp, - MEM_RESERVE | MEM_COMMIT, - PAGE_READWRITE - ); - } else { - lpdsf->s.surface_desc.u1.lpSurface = img->data; - VirtualAlloc(img->data, img->bytes_per_line * img->height, MEM_RESERVE|MEM_SYSTEM, PAGE_READWRITE); - } - return img; -} -#endif /* HAVE_LIBXXSHM */ - -static XImage *create_ximage(IDirectDraw2Impl* This, IDirectDrawSurface4Impl* lpdsf) { - XImage *img = NULL; - DDPRIVATE(This); - void *img_data; - int bpp = PFGET_BPP(This->d->directdraw_pixelformat); - int screen_bpp = PFGET_BPP(This->d->screen_pixelformat); - -#ifdef HAVE_LIBXXSHM - if (ddpriv->xshm_active) - img = create_xshmimage(This, lpdsf); - - if (img == NULL) { -#endif - /* Allocate surface memory */ - lpdsf->s.surface_desc.u1.lpSurface = VirtualAlloc( - NULL, - lpdsf->s.surface_desc.dwWidth * - lpdsf->s.surface_desc.dwHeight * - bpp, - MEM_RESERVE | MEM_COMMIT, - PAGE_READWRITE - ); - - if (This->d->pixel_convert != NULL) - img_data = VirtualAlloc( - NULL, - lpdsf->s.surface_desc.dwWidth * - lpdsf->s.surface_desc.dwHeight * - screen_bpp, - MEM_RESERVE | MEM_COMMIT, - PAGE_READWRITE - ); - else - img_data = lpdsf->s.surface_desc.u1.lpSurface; - - /* In this case, create an XImage */ - img = TSXCreateImage(display, - DefaultVisualOfScreen(X11DRV_GetXScreen()), - This->d->pixmap_depth, - ZPixmap, - 0, - img_data, - lpdsf->s.surface_desc.dwWidth, - lpdsf->s.surface_desc.dwHeight, - 32, - lpdsf->s.surface_desc.dwWidth*screen_bpp - ); -#ifdef HAVE_LIBXXSHM - } -#endif - if (This->d->pixel_convert != NULL) - lpdsf->s.surface_desc.lPitch = bpp*lpdsf->s.surface_desc.dwWidth; - else - lpdsf->s.surface_desc.lPitch = img->bytes_per_line; - return img; -} - -#ifdef HAVE_XVIDEO -#ifdef HAVE_LIBXXSHM -static XvImage *create_xvshmimage(IDirectDraw2Impl* This, IDirectDrawSurface4Impl* lpdsf) { - DSPRIVATE(lpdsf); - DDPRIVATE(This); - XvImage *img; - int (*WineXHandler)(Display *, XErrorEvent *); - - img = TSXvShmCreateImage(display, - ddpriv->port_id, - (int) lpdsf->s.surface_desc.ddpfPixelFormat.dwFourCC, - NULL, - lpdsf->s.surface_desc.dwWidth, - lpdsf->s.surface_desc.dwHeight, - &(dspriv->shminfo)); - - if (img == NULL) { - FIXME("Couldn't create XShm XvImage (due to X11 remote display or failure).\nReverting to standard X images !\n"); - ddpriv->xshm_active = 0; - return NULL; - } - - dspriv->shminfo.shmid = shmget( IPC_PRIVATE, img->data_size, IPC_CREAT|0777 ); - - if (dspriv->shminfo.shmid < 0) { - FIXME("Couldn't create shared memory segment (due to X11 remote display or failure).\nReverting to standard X images !\n"); - ddpriv->xshm_active = 0; - TSXFree(img); - return NULL; - } - - dspriv->shminfo.shmaddr=img->data=(char*)shmat(dspriv->shminfo.shmid,0,0); - - if (img->data == (char *) -1) { - FIXME("Couldn't attach shared memory segment (due to X11 remote display or failure).\nReverting to standard X images !\n"); - ddpriv->xshm_active = 0; - TSXFree(img); - shmctl(dspriv->shminfo.shmid, IPC_RMID, 0); - return NULL; - } - dspriv->shminfo.readOnly = False; - - /* This is where things start to get trickier.... - * First, we flush the current X connections to be sure to catch all - * non-XShm related errors - */ - TSXSync(display, False); - /* Then we enter in the non-thread safe part of the tests */ - EnterCriticalSection( &X11DRV_CritSection ); - - /* Reset the error flag, sets our new error handler and try to attach - * the surface - */ - XShmErrorFlag = 0; - WineXHandler = XSetErrorHandler(XShmErrorHandler); - XShmAttach(display, &(dspriv->shminfo)); - XSync(display, False); - - /* Check the error flag */ - if (XShmErrorFlag) { - /* An error occured */ - XFlush(display); - XShmErrorFlag = 0; - XFree(img); - shmdt(dspriv->shminfo.shmaddr); - shmctl(dspriv->shminfo.shmid, IPC_RMID, 0); - XSetErrorHandler(WineXHandler); - - FIXME("Couldn't attach shared memory segment to X server (due to X11 remote display or failure).\nReverting to standard X images !\n"); - ddpriv->xshm_active = 0; - - /* Leave the critical section */ - LeaveCriticalSection( &X11DRV_CritSection ); - return NULL; - } - /* Here, to be REALLY sure, I should do a XShmPutImage to check if - * this works, but it may be a bit overkill.... - */ - XSetErrorHandler(WineXHandler); - LeaveCriticalSection( &X11DRV_CritSection ); - - shmctl(dspriv->shminfo.shmid, IPC_RMID, 0); - - lpdsf->s.surface_desc.u1.lpSurface = img->data; - VirtualAlloc(img->data, img->data_size, MEM_RESERVE|MEM_SYSTEM, PAGE_READWRITE); - - return img; -} -#endif - -static XvImage *create_xvimage(IDirectDraw2Impl* This, IDirectDrawSurface4Impl* lpdsf, HRESULT *err_code) { - XvImage *img = NULL; - DDPRIVATE(This); - void *img_data; - XvImageFormatValues *fo; - int formats, i; - int bpp = PFGET_BPP(lpdsf->s.surface_desc.ddpfPixelFormat); - - *err_code = DDERR_OUTOFVIDEOMEMORY; - - if (!(lpdsf->s.surface_desc.ddpfPixelFormat.dwFlags & DDPF_FOURCC)) { - /* Hmmm, overlay without FOURCC code.. Baaaaaad */ - ERR("Overlay without a FOURCC pixel format !\n"); - *err_code = DDERR_INVALIDPIXELFORMAT; - return NULL; - } - - /* First, find out if we support this PixelFormat. - I make the assumption here that the id of the XvImage format is the - same as the Windows FOURCC code. */ - fo = TSXvListImageFormats(display, ddpriv->port_id, &formats); - for (i = 0; i < formats; i++) - if (fo[i].id == lpdsf->s.surface_desc.ddpfPixelFormat.dwFourCC) break; - if (fo) - TSXFree(fo); - - if (i == formats) { - ERR("FOURCC code not supported by the video card !\n"); - *err_code = DDERR_INVALIDPIXELFORMAT; - return NULL; - } - -#ifdef HAVE_LIBXXSHM - if (ddpriv->xshm_active) - img = create_xvshmimage(This, lpdsf); - - if (img == NULL) { -#endif - /* Allocate surface memory */ - lpdsf->s.surface_desc.u1.lpSurface = - VirtualAlloc(NULL, - lpdsf->s.surface_desc.dwWidth * - lpdsf->s.surface_desc.dwHeight * - bpp, - MEM_RESERVE | MEM_COMMIT, - PAGE_READWRITE); - img_data = lpdsf->s.surface_desc.u1.lpSurface; - - /* In this case, create an XvImage */ - img = TSXvCreateImage(display, - ddpriv->port_id, - (int) lpdsf->s.surface_desc.ddpfPixelFormat.dwFourCC, - img_data, - lpdsf->s.surface_desc.dwWidth, - lpdsf->s.surface_desc.dwHeight); -#ifdef HAVE_LIBXXSHM - } -#endif - lpdsf->s.surface_desc.lPitch = ((XvImage *) img)->pitches[0]; - return img; -} -#else -static XvImage *create_xvimage(IDirectDraw2Impl* This, IDirectDrawSurface4Impl* lpdsf, HRESULT *err_code) { - *err_code = DDERR_INVALIDPIXELFORMAT; - return NULL; -} -#endif - -ULONG WINAPI Xlib_IDirectDraw2Impl_Release(LPDIRECTDRAW2 iface) { - ICOM_THIS(IDirectDraw2Impl,iface); - TRACE("(%p)->() decrementing from %lu.\n", This, This->ref ); - - if (!--(This->ref)) { - if (!--(This->d->ref)) { - if (This->d->window && GetPropA(This->d->window,ddProp)) - DestroyWindow(This->d->window); - HeapFree(GetProcessHeap(),0,This->d); - } - HeapFree(GetProcessHeap(),0,This); - xf86vmode_restore(); - return S_OK; - } - return This->ref; -} - -static HRESULT WINAPI Xlib_IDirectDraw2Impl_CreateSurface( - LPDIRECTDRAW2 iface,LPDDSURFACEDESC lpddsd,LPDIRECTDRAWSURFACE *lpdsf, - IUnknown *lpunk -) { - ICOM_THIS(IDirectDraw2Impl,iface); - IDirectDrawSurfaceImpl* dsurf; - x11_ds_private *dspriv; - - TRACE("(%p)->CreateSurface(%p,%p,%p)\n", This,lpddsd,lpdsf,lpunk); - - if (TRACE_ON(ddraw)) _dump_surface_desc(lpddsd); - - *lpdsf = HeapAlloc( - GetProcessHeap(), - HEAP_ZERO_MEMORY, - sizeof(IDirectDrawSurfaceImpl) - ); - dsurf = (IDirectDrawSurfaceImpl*)*lpdsf; - dsurf->ref = 1; - dsurf->private = HeapAlloc( - GetProcessHeap(), - HEAP_ZERO_MEMORY, - sizeof(x11_ds_private) - ); - ICOM_VTBL(dsurf) = (ICOM_VTABLE(IDirectDrawSurface)*)&xlib_dds4vt; - dspriv = (x11_ds_private*)dsurf->private; - - dsurf->s.ddraw = This; - IDirectDraw2_AddRef(iface); - - dsurf->s.palette = NULL; - dsurf->s.lpClipper = NULL; - dspriv->is_overlay = FALSE; - dspriv->info.image = NULL; /* This is for off-screen buffers */ - - /* Copy the surface description */ - dsurf->s.surface_desc = *lpddsd; - - if (!(lpddsd->dwFlags & DDSD_WIDTH)) - dsurf->s.surface_desc.dwWidth = This->d->width; - if (!(lpddsd->dwFlags & DDSD_HEIGHT)) - dsurf->s.surface_desc.dwHeight = This->d->height; - dsurf->s.surface_desc.dwFlags |= DDSD_WIDTH|DDSD_HEIGHT; - - /* Check if this a 'primary surface' or an overlay */ - if ((lpddsd->dwFlags & DDSD_CAPS) && - ((lpddsd->ddsCaps.dwCaps & DDSCAPS_PRIMARYSURFACE) || - (lpddsd->ddsCaps.dwCaps & DDSCAPS_OVERLAY)) - ) { - /* Add flags if there were not present */ - dsurf->s.surface_desc.dwFlags |= DDSD_WIDTH|DDSD_HEIGHT|DDSD_PITCH|DDSD_LPSURFACE|DDSD_PIXELFORMAT; - dsurf->s.surface_desc.ddsCaps.dwCaps |= DDSCAPS_VIDEOMEMORY; - - if (lpddsd->ddsCaps.dwCaps & DDSCAPS_PRIMARYSURFACE) { - dsurf->s.surface_desc.ddsCaps.dwCaps |= DDSCAPS_VISIBLE; - dsurf->s.surface_desc.ddpfPixelFormat = This->d->directdraw_pixelformat; - dsurf->s.surface_desc.dwWidth = This->d->width; - dsurf->s.surface_desc.dwHeight = This->d->height; - } else { - dspriv->is_overlay = TRUE; - /* In the case of Overlay surfaces, copy the one provided by the application */ - dsurf->s.surface_desc.ddpfPixelFormat = lpddsd->ddpfPixelFormat; - } - - if (lpddsd->ddsCaps.dwCaps & DDSCAPS_OVERLAY) { - HRESULT err_code; - TRACE("using an XvImage for the overlay (%p)\n", dsurf); - dspriv->info.overlay.image = create_xvimage(This,(IDirectDrawSurface4Impl*)dsurf, &err_code); - if (dspriv->info.overlay.image == NULL) - return err_code; - } else { - TRACE("using standard XImage for a primary surface (%p)\n", dsurf); - /* Create the XImage */ - dspriv->info.image = create_ximage(This,(IDirectDrawSurface4Impl*)dsurf); - if (dspriv->info.image == NULL) - return DDERR_OUTOFMEMORY; - } - - /* Check for backbuffers */ - if (lpddsd->dwFlags & DDSD_BACKBUFFERCOUNT) { - IDirectDrawSurface4Impl* back; - int i; - - for (i=lpddsd->dwBackBufferCount;i--;) { - x11_ds_private *bspriv; - back = (IDirectDrawSurface4Impl*)HeapAlloc( - GetProcessHeap(), - HEAP_ZERO_MEMORY, - sizeof(IDirectDrawSurface4Impl) - ); - TRACE("allocated back-buffer (%p)\n", back); - - IDirectDraw2_AddRef(iface); - back->s.ddraw = This; - - back->ref = 1; - ICOM_VTBL(back)=(ICOM_VTABLE(IDirectDrawSurface4)*)&xlib_dds4vt; - /* Copy the surface description from the front buffer */ - back->s.surface_desc = dsurf->s.surface_desc; - back->s.surface_desc.u1.lpSurface = NULL; - - back->private = HeapAlloc( - GetProcessHeap(), - HEAP_ZERO_MEMORY, - sizeof(x11_ds_private) - ); - bspriv = (x11_ds_private*)back->private; - - /* Create the XImage. */ - if (lpddsd->ddsCaps.dwCaps & DDSCAPS_OVERLAY) { - HRESULT err_code; - dspriv->is_overlay = TRUE; - bspriv->info.overlay.image = create_xvimage(This, back, &err_code); - if (bspriv->info.overlay.image == NULL) - return err_code; - } else { - bspriv->info.image = create_ximage(This, back); - if (bspriv->info.image == NULL) - return DDERR_OUTOFMEMORY; - } - TRACE("bspriv = %p\n",bspriv); - - /* Add relevant info to front and back buffers */ - /* FIXME: backbuffer/frontbuffer handling broken here, but - * will be fixed up in _Flip(). - */ - SDDSCAPS(dsurf) |= DDSCAPS_FRONTBUFFER; - SDDSCAPS(back) |= DDSCAPS_BACKBUFFER|DDSCAPS_VIDEOMEMORY|DDSCAPS_FLIP; - back->s.surface_desc.dwFlags &= ~DDSD_BACKBUFFERCOUNT; - SDDSCAPS(back) &= ~(DDSCAPS_VISIBLE|DDSCAPS_PRIMARYSURFACE); - TRACE("attaching surface %p to %p\n",back,*lpdsf); - IDirectDrawSurface4_AddAttachedSurface((LPDIRECTDRAWSURFACE4)(*lpdsf),(LPDIRECTDRAWSURFACE4)back); - } - } - } else { - /* There is no Xlib-specific code here... - * Go to the common surface creation function - */ - return common_off_screen_CreateSurface(This,dsurf); - } - return DD_OK; -} - -/* - * The Xlib Implementation tries to use the passed hwnd as drawing window, - * even when the approbiate bitmasks are not specified. - */ -static HRESULT WINAPI Xlib_IDirectDraw2Impl_SetCooperativeLevel( - LPDIRECTDRAW2 iface,HWND hwnd,DWORD cooplevel -) { - ICOM_THIS(IDirectDraw2Impl,iface); - DDPRIVATE(This); - - FIXME("(%p)->(%08lx,%08lx)\n",This,(DWORD)hwnd,cooplevel); - if (TRACE_ON(ddraw)) - _dump_cooperativelevel(cooplevel); - This->d->mainWindow = hwnd; - - /* This will be overwritten in the case of Full Screen mode. - Windowed games could work with that :-) */ - if (hwnd) { - WND *tmpWnd = WIN_FindWndPtr(hwnd); - ddpriv->drawable = X11DRV_WND_GetXWindow(tmpWnd); - WIN_ReleaseWndPtr(tmpWnd); - - if( !ddpriv->drawable ) { - ddpriv->drawable = ((X11DRV_WND_DATA *) WIN_GetDesktop()->pDriverData)->window; - WIN_ReleaseDesktop(); - } - TRACE("Setting drawable to %ld\n", ddpriv->drawable); - } - return DD_OK; -} - -static HRESULT WINAPI Xlib_IDirectDrawImpl_SetDisplayMode( - LPDIRECTDRAW iface,DWORD width,DWORD height,DWORD depth -) { - ICOM_THIS(IDirectDrawImpl,iface); - DDPRIVATE(This); - char buf[200]; - WND *tmpWnd; - int c; - - TRACE("(%p)->SetDisplayMode(%ld,%ld,%ld)\n", - This, width, height, depth); - - switch ((c = _common_depth_to_pixelformat(depth,iface))) { - case -2: - sprintf(buf,"SetDisplayMode(w=%ld,h=%ld,d=%ld), unsupported depth!",width,height,depth); - MessageBoxA(0,buf,"WINE DirectDraw",MB_OK|MB_ICONSTOP); - return DDERR_UNSUPPORTEDMODE; - case -1: - /* No conversion. Good. */ - break; - default: - DPRINTF("DirectDraw warning: running in depth-conversion mode %d. Should run using a %ld depth for optimal performances.\n", c,depth); - } - - This->d->width = width; - This->d->height = height; - - _common_IDirectDrawImpl_SetDisplayMode(This); - - xf86vmode_setdisplaymode(width,height); - - tmpWnd = WIN_FindWndPtr(This->d->window); - This->d->paintable = 1; - ddpriv->drawable = ((X11DRV_WND_DATA *) tmpWnd->pDriverData)->window; - WIN_ReleaseWndPtr(tmpWnd); - - /* We don't have a context for this window. Host off the desktop */ - if( !ddpriv->drawable ) - { - ddpriv->drawable = ((X11DRV_WND_DATA *) WIN_GetDesktop()->pDriverData)->window; - WIN_ReleaseDesktop(); - } - TRACE("Setting drawable to %ld\n", ddpriv->drawable); - - if (get_option( "DXGrab", 0 )) { - /* Confine cursor movement (risky, but the user asked for it) */ - TSXGrabPointer(display, ddpriv->drawable, True, 0, GrabModeAsync, GrabModeAsync, ddpriv->drawable, None, CurrentTime); - } - - return DD_OK; -} - -static void fill_caps(LPDDCAPS caps, x11_dd_private *x11ddp) { - /* This function tries to fill the capabilities of Wine's DDraw implementation. - Need to be fixed, though.. */ - if (caps == NULL) - return; - - caps->dwSize = sizeof(*caps); - caps->dwCaps = DDCAPS_ALPHA | DDCAPS_BLT | DDCAPS_BLTSTRETCH | DDCAPS_BLTCOLORFILL | DDCAPS_BLTDEPTHFILL | DDCAPS_CANBLTSYSMEM | DDCAPS_COLORKEY | DDCAPS_PALETTE /*| DDCAPS_NOHARDWARE*/; - caps->dwCaps2 = DDCAPS2_CERTIFIED | DDCAPS2_NOPAGELOCKREQUIRED | DDCAPS2_WIDESURFACES; - caps->dwCKeyCaps = 0xFFFFFFFF; /* Should put real caps here one day... */ - caps->dwFXCaps = 0; - caps->dwFXAlphaCaps = 0; - caps->dwPalCaps = DDPCAPS_8BIT | DDPCAPS_ALLOW256; - caps->dwSVCaps = 0; - caps->dwZBufferBitDepths = DDBD_16; - /* I put here 8 Mo so that D3D applications will believe they have enough memory - to put textures in video memory. - BTW, is this only frame buffer memory or also texture memory (for Voodoo boards - for example) ? */ - caps->dwVidMemTotal = 8192 * 1024; - caps->dwVidMemFree = 8192 * 1024; - /* These are all the supported capabilities of the surfaces */ - caps->ddsCaps.dwCaps = DDSCAPS_ALPHA | DDSCAPS_BACKBUFFER | DDSCAPS_COMPLEX | DDSCAPS_FLIP | - DDSCAPS_FRONTBUFFER | DDSCAPS_LOCALVIDMEM | DDSCAPS_NONLOCALVIDMEM | DDSCAPS_OFFSCREENPLAIN | - DDSCAPS_PALETTE | DDSCAPS_PRIMARYSURFACE | DDSCAPS_SYSTEMMEMORY | - DDSCAPS_VIDEOMEMORY | DDSCAPS_VISIBLE; -#ifdef HAVE_OPENGL - caps->dwCaps |= DDCAPS_3D | DDCAPS_ZBLTS; - caps->dwCaps2 |= DDCAPS2_NO2DDURING3DSCENE; - caps->ddsCaps.dwCaps |= DDSCAPS_3DDEVICE | DDSCAPS_MIPMAP | DDSCAPS_TEXTURE | DDSCAPS_ZBUFFER; -#endif - -#ifdef HAVE_XVIDEO - if (x11ddp->xvideo_active) { - caps->dwCaps |= DDCAPS_OVERLAY | DDCAPS_OVERLAYFOURCC | DDCAPS_OVERLAYSTRETCH | DDCAPS_BLTFOURCC; - caps->dwCaps2 |= DDCAPS2_VIDEOPORT; - caps->dwMaxVisibleOverlays = 16; - caps->dwCurrVisibleOverlays = 0; - caps->dwMinOverlayStretch = 1; /* Apparently there is no 'down' stretching in XVideo, but well, Windows - Media player refuses to work when I put 1000 here :-/ */ - caps->dwMaxOverlayStretch = 100000; /* This is a 'bogus' value, I do not know the maximum stretching */ - TSXvListImageFormats(display, x11ddp->port_id, (unsigned int *) &(caps->dwNumFourCCCodes)); - caps->ddsCaps.dwCaps |= DDSCAPS_OVERLAY; - } -#endif -} - -static HRESULT WINAPI Xlib_IDirectDraw2Impl_GetCaps( - LPDIRECTDRAW2 iface,LPDDCAPS caps1,LPDDCAPS caps2 -) { - ICOM_THIS(IDirectDraw2Impl,iface); - DDPRIVATE(This); - TRACE("(%p)->GetCaps(%p,%p)\n",This,caps1,caps2); - - /* Put the same caps for the two capabilities */ - fill_caps(caps1, ddpriv); - fill_caps(caps2, ddpriv); - - return DD_OK; -} - -static HRESULT WINAPI Xlib_IDirectDraw2Impl_CreatePalette( - LPDIRECTDRAW2 iface,DWORD dwFlags,LPPALETTEENTRY palent, - LPDIRECTDRAWPALETTE *lpddpal,LPUNKNOWN lpunk -) { - ICOM_THIS(IDirectDraw2Impl,iface); - IDirectDrawPaletteImpl** ilpddpal=(IDirectDrawPaletteImpl**)lpddpal; - int xsize; - HRESULT res; - - TRACE("(%p)->(%08lx,%p,%p,%p)\n",This,dwFlags,palent,ilpddpal,lpunk); - res = common_IDirectDraw2Impl_CreatePalette(This,dwFlags,palent,ilpddpal,lpunk,&xsize); - if (res != 0) - return res; - (*ilpddpal)->private = HeapAlloc( - GetProcessHeap(), - HEAP_ZERO_MEMORY, - sizeof(x11_dp_private) - ); - ICOM_VTBL(*ilpddpal) = &xlib_ddpalvt; - return DD_OK; -} - -static HRESULT WINAPI Xlib_IDirectDraw2Impl_QueryInterface( - LPDIRECTDRAW2 iface,REFIID refiid,LPVOID *obj -) { - ICOM_THIS(IDirectDraw2Impl,iface); - - TRACE("(%p)->(%s,%p)\n",This,debugstr_guid(refiid),obj); - if ( IsEqualGUID( &IID_IUnknown, refiid ) ) { - *obj = This; - IDirectDraw2_AddRef(iface); - - TRACE(" Creating IUnknown interface (%p)\n", *obj); - - return S_OK; - } - if ( IsEqualGUID( &IID_IDirectDraw, refiid ) ) { - IDirectDrawImpl *dd = HeapAlloc(GetProcessHeap(),0,sizeof(*dd)); - IDirectDraw2_AddRef(iface); - - dd->ref = 1;ICOM_VTBL(dd) = &xlib_ddvt;dd->d = This->d;This->d->ref++; - *obj = dd; - - TRACE(" Creating IDirectDraw interface (%p)\n", *obj); - return S_OK; - } - if ( IsEqualGUID( &IID_IDirectDraw2, refiid ) ) { - IDirectDraw2Impl *dd = HeapAlloc(GetProcessHeap(),0,sizeof(*dd)); - IDirectDraw2_AddRef(iface); - - dd->ref = 1;ICOM_VTBL(dd) = &xlib_dd2vt;dd->d = This->d;This->d->ref++; - *obj = dd; - - TRACE(" Creating IDirectDraw2 interface (%p)\n", *obj); - return S_OK; - } - if ( IsEqualGUID( &IID_IDirectDraw4, refiid ) ) { - IDirectDraw4Impl *dd = HeapAlloc(GetProcessHeap(),0,sizeof(*dd)); - dd->ref = 1;ICOM_VTBL(dd) = &xlib_dd4vt;dd->d = This->d;This->d->ref++; - *obj = dd; - - IDirectDraw4_AddRef(iface); - TRACE(" Creating IDirectDraw4 interface (%p)\n", *obj); - return S_OK; - } - if ( IsEqualGUID( &IID_IDirectDraw7, refiid ) ) { - IDirectDraw4Impl *dd = HeapAlloc(GetProcessHeap(),0,sizeof(*dd)); - dd->ref = 1;ICOM_VTBL(dd) = (ICOM_VTABLE(IDirectDraw4)*)&xlib_dd7vt;dd->d = This->d;This->d->ref++; - *obj = dd; - - IDirectDraw7_AddRef(iface); - FIXME(" Creating IDirectDraw7 interface by reusing DirectDraw4!(%p)\n", *obj); - return S_OK; - } -#ifdef HAVE_OPENGL - if ( IsEqualGUID( &IID_IDirect3D, refiid ) ) - return create_direct3d(obj,This); - if ( IsEqualGUID( &IID_IDirect3D2, refiid ) ) - return create_direct3d2(obj,This); - if ( IsEqualGUID( &IID_IDirect3D3, refiid ) ) - return create_direct3d3(obj,This); -#else - if ( IsEqualGUID( &IID_IDirect3D, refiid ) || - IsEqualGUID( &IID_IDirect3D2, refiid ) || - IsEqualGUID( &IID_IDirect3D3, refiid ) - ) - { - ERR( "Cannot provide 3D support without OpenGL/Mesa installed\n" ); - } -#endif - FIXME("(%p):interface for IID %s _NOT_ found!\n",This,debugstr_guid(refiid)); - return OLE_E_ENUM_NOMORE; -} - -static HRESULT WINAPI Xlib_IDirectDraw2Impl_EnumDisplayModes( - LPDIRECTDRAW2 iface,DWORD dwFlags,LPDDSURFACEDESC lpddsfd,LPVOID context,LPDDENUMMODESCALLBACK modescb -) { - ICOM_THIS(IDirectDraw2Impl,iface); - XVisualInfo *vi; - XPixmapFormatValues *pf; - XVisualInfo vt; - int xbpp = 1, nvisuals, npixmap, i, emu; - int has_mode[] = { 0, 0, 0, 0 }; - int has_depth[] = { 8, 15, 16, 24 }; - DDSURFACEDESC ddsfd; - static struct { - int w,h; - } modes[] = { /* some of the usual modes */ - {512,384}, - {640,400}, - {640,480}, - {800,600}, - {1024,768}, - {1280,1024} - }; - DWORD maxWidth, maxHeight; - - TRACE("(%p)->(0x%08lx,%p,%p,%p)\n",This,dwFlags,lpddsfd,context,modescb); - ddsfd.dwSize = sizeof(ddsfd); - ddsfd.dwFlags = DDSD_HEIGHT|DDSD_WIDTH|DDSD_PIXELFORMAT|DDSD_CAPS|DDSD_PITCH; - if (dwFlags & DDEDM_REFRESHRATES) { - ddsfd.dwFlags |= DDSD_REFRESHRATE; - ddsfd.u.dwRefreshRate = 60; - } - maxWidth = GetSystemMetrics(SM_CXSCREEN); - maxHeight = GetSystemMetrics(SM_CYSCREEN); - - vi = TSXGetVisualInfo(display, VisualNoMask, &vt, &nvisuals); - pf = TSXListPixmapFormats(display, &npixmap); - - i = 0; - emu = 0; - while ((i < npixmap) || (emu != 4)) { - int mode_index = 0; - int send_mode = 0; - int j; - - if (i < npixmap) { - for (j = 0; j < 4; j++) { - if (has_depth[j] == pf[i].depth) { - mode_index = j; - break; - } - } - if (j == 4) { - i++; - continue; - } - - - if (has_mode[mode_index] == 0) { - if (mode_index == 0) { - send_mode = 1; - - ddsfd.ddsCaps.dwCaps = DDSCAPS_PALETTE; - ddsfd.ddpfPixelFormat.dwSize = sizeof(ddsfd.ddpfPixelFormat); - ddsfd.ddpfPixelFormat.dwFlags = DDPF_RGB|DDPF_PALETTEINDEXED8; - ddsfd.ddpfPixelFormat.dwFourCC = 0; - ddsfd.ddpfPixelFormat.u.dwRGBBitCount = 8; - ddsfd.ddpfPixelFormat.u1.dwRBitMask = 0; - ddsfd.ddpfPixelFormat.u2.dwGBitMask = 0; - ddsfd.ddpfPixelFormat.u3.dwBBitMask = 0; - ddsfd.ddpfPixelFormat.u4.dwRGBAlphaBitMask= 0; - - xbpp = 1; - - has_mode[mode_index] = 1; - } else { - /* All the 'true color' depths (15, 16 and 24) - First, find the corresponding visual to extract the bit masks */ - for (j = 0; j < nvisuals; j++) { - if (vi[j].depth == pf[i].depth) { - ddsfd.ddsCaps.dwCaps = 0; - ddsfd.ddpfPixelFormat.dwSize = sizeof(ddsfd.ddpfPixelFormat); - ddsfd.ddpfPixelFormat.dwFlags = DDPF_RGB; - ddsfd.ddpfPixelFormat.dwFourCC = 0; - ddsfd.ddpfPixelFormat.u.dwRGBBitCount = pf[i].bits_per_pixel; - ddsfd.ddpfPixelFormat.u1.dwRBitMask = vi[j].red_mask; - ddsfd.ddpfPixelFormat.u2.dwGBitMask = vi[j].green_mask; - ddsfd.ddpfPixelFormat.u3.dwBBitMask = vi[j].blue_mask; - ddsfd.ddpfPixelFormat.u4.dwRGBAlphaBitMask= 0; - - xbpp = pf[i].bits_per_pixel/8; - - send_mode = 1; - has_mode[mode_index] = 1; - break; - } - } - if (j == nvisuals) - WARN("Did not find visual corresponding to the pixmap format !\n"); - } - } - i++; - } else { - /* Now to emulated modes */ - if (has_mode[emu] == 0) { - int c; - int l; - int depth = has_depth[emu]; - - for (c = 0; (c < sizeof(ModeEmulations) / sizeof(Convert)) && (send_mode == 0); c++) { - if (ModeEmulations[c].dest.depth == depth) { - /* Found an emulation function, now tries to find a matching visual / pixel format pair */ - for (l = 0; (l < npixmap) && (send_mode == 0); l++) { - if ((pf[l].depth == ModeEmulations[c].screen.depth) && - (pf[l].bits_per_pixel == ModeEmulations[c].screen.bpp)) { - int j; - for (j = 0; (j < nvisuals) && (send_mode == 0); j++) { - if ((vi[j].depth == pf[l].depth) && - (vi[j].red_mask == ModeEmulations[c].screen.rmask) && - (vi[j].green_mask == ModeEmulations[c].screen.gmask) && - (vi[j].blue_mask == ModeEmulations[c].screen.bmask)) { - ddsfd.ddpfPixelFormat.dwSize = sizeof(ddsfd.ddpfPixelFormat); - ddsfd.ddpfPixelFormat.dwFourCC = 0; - if (depth == 8) { - ddsfd.ddpfPixelFormat.dwFlags = DDPF_RGB|DDPF_PALETTEINDEXED8; - ddsfd.ddpfPixelFormat.u.dwRGBBitCount = 8; - ddsfd.ddpfPixelFormat.u1.dwRBitMask = 0; - ddsfd.ddpfPixelFormat.u2.dwGBitMask = 0; - ddsfd.ddpfPixelFormat.u3.dwBBitMask = 0; - } else { - ddsfd.ddpfPixelFormat.dwFlags = DDPF_RGB; - ddsfd.ddpfPixelFormat.u.dwRGBBitCount = ModeEmulations[c].dest.bpp; - ddsfd.ddpfPixelFormat.u1.dwRBitMask = ModeEmulations[c].dest.rmask; - ddsfd.ddpfPixelFormat.u2.dwGBitMask = ModeEmulations[c].dest.gmask; - ddsfd.ddpfPixelFormat.u3.dwBBitMask = ModeEmulations[c].dest.bmask; - } - ddsfd.ddpfPixelFormat.u4.dwRGBAlphaBitMask= 0; - send_mode = 1; - } - - if (send_mode == 0) - WARN("No visual corresponding to pixmap format !\n"); - } - } - } - } - } - } - - emu++; - } - - if (send_mode) { - int mode; - - if (TRACE_ON(ddraw)) { - TRACE("Enumerating with pixel format : \n"); - _dump_pixelformat(&(ddsfd.ddpfPixelFormat)); - DPRINTF("\n"); - } - - for (mode = 0; mode < sizeof(modes)/sizeof(modes[0]); mode++) { - /* Do not enumerate modes we cannot handle anyway */ - if ((modes[mode].w > maxWidth) || (modes[mode].h > maxHeight)) - break; - - ddsfd.dwWidth = modes[mode].w; - ddsfd.dwHeight= modes[mode].h; - ddsfd.lPitch = ddsfd.dwWidth * xbpp; - - /* Now, send the mode description to the application */ - TRACE(" - mode %4ld - %4ld\n", ddsfd.dwWidth, ddsfd.dwHeight); - if (!modescb(&ddsfd, context)) - goto exit_enum; - } - - if (!(dwFlags & DDEDM_STANDARDVGAMODES)) { - /* modeX is not standard VGA */ - ddsfd.dwWidth = 320; - ddsfd.dwHeight = 200; - ddsfd.lPitch = 320 * xbpp; - if (!modescb(&ddsfd, context)) - goto exit_enum; - } - } - } - exit_enum: - TSXFree(vi); - TSXFree(pf); - - return DD_OK; -} - -HRESULT WINAPI Xlib_IDirectDraw2Impl_GetFourCCCodes( - LPDIRECTDRAW2 iface,LPDWORD lpNumCodes, LPDWORD lpCodes -) { -#ifdef HAVE_XVIDEO - ICOM_THIS(IDirectDraw2Impl,iface); - DDPRIVATE(This); - XvImageFormatValues *fo; - int num_codes; - - TRACE("(%p,%p,%p) - %ld slots available\n",This, lpNumCodes, lpCodes, *lpNumCodes); - - fo = TSXvListImageFormats(display, ddpriv->port_id, &num_codes); - if (lpCodes != NULL) { - /* Fill in the FourCC table */ - int i; - for (i = 0; i < *lpNumCodes; i++) lpCodes[i] = fo[i].id; - } - if (fo) { - *lpNumCodes = num_codes; - TSXFree(fo); - } else { - *lpNumCodes = 0; /* Not sure if X fills this variable in the error case */ - } - - return DD_OK; -#else - return IDirectDraw2Impl_GetFourCCCodes(iface, lpNumCodes, lpCodes); -#endif -} - -/* Note: Hack so we can reuse the old functions without compiler warnings */ -#if !defined(__STRICT_ANSI__) && defined(__GNUC__) -# define XCAST(fun) (typeof(xlib_ddvt.fn##fun)) -#else -# define XCAST(fun) (void *) -#endif - -ICOM_VTABLE(IDirectDraw) xlib_ddvt = { - ICOM_MSVTABLE_COMPAT_DummyRTTIVALUE - XCAST(QueryInterface)Xlib_IDirectDraw2Impl_QueryInterface, - XCAST(AddRef)IDirectDraw2Impl_AddRef, - XCAST(Release)Xlib_IDirectDraw2Impl_Release, - XCAST(Compact)IDirectDraw2Impl_Compact, - XCAST(CreateClipper)IDirectDraw2Impl_CreateClipper, - XCAST(CreatePalette)Xlib_IDirectDraw2Impl_CreatePalette, - XCAST(CreateSurface)Xlib_IDirectDraw2Impl_CreateSurface, - XCAST(DuplicateSurface)IDirectDraw2Impl_DuplicateSurface, - XCAST(EnumDisplayModes)Xlib_IDirectDraw2Impl_EnumDisplayModes, - XCAST(EnumSurfaces)IDirectDraw2Impl_EnumSurfaces, - XCAST(FlipToGDISurface)IDirectDraw2Impl_FlipToGDISurface, - XCAST(GetCaps)Xlib_IDirectDraw2Impl_GetCaps, - XCAST(GetDisplayMode)IDirectDraw2Impl_GetDisplayMode, - XCAST(GetFourCCCodes)Xlib_IDirectDraw2Impl_GetFourCCCodes, - XCAST(GetGDISurface)IDirectDraw2Impl_GetGDISurface, - XCAST(GetMonitorFrequency)IDirectDraw2Impl_GetMonitorFrequency, - XCAST(GetScanLine)IDirectDraw2Impl_GetScanLine, - XCAST(GetVerticalBlankStatus)IDirectDraw2Impl_GetVerticalBlankStatus, - XCAST(Initialize)IDirectDraw2Impl_Initialize, - XCAST(RestoreDisplayMode)IDirectDraw2Impl_RestoreDisplayMode, - XCAST(SetCooperativeLevel)Xlib_IDirectDraw2Impl_SetCooperativeLevel, - Xlib_IDirectDrawImpl_SetDisplayMode, - XCAST(WaitForVerticalBlank)IDirectDraw2Impl_WaitForVerticalBlank, -}; - -#undef XCAST - -/***************************************************************************** - * IDirectDraw2 - * - */ - -static HRESULT WINAPI Xlib_IDirectDraw2Impl_SetDisplayMode( - LPDIRECTDRAW2 iface,DWORD width,DWORD height,DWORD depth,DWORD dwRefreshRate,DWORD dwFlags -) { - FIXME( "Ignored parameters (0x%08lx,0x%08lx)\n", dwRefreshRate, dwFlags ); - return Xlib_IDirectDrawImpl_SetDisplayMode((LPDIRECTDRAW)iface,width,height,depth); -} - -static HRESULT WINAPI Xlib_IDirectDraw2Impl_GetAvailableVidMem( - LPDIRECTDRAW2 iface,LPDDSCAPS ddscaps,LPDWORD total,LPDWORD free -) { - ICOM_THIS(IDirectDraw2Impl,iface); - TRACE("(%p)->(%p,%p,%p)\n",This,ddscaps,total,free); - if (total) *total = 16* 1024 * 1024; - if (free) *free = 16* 1024 * 1024; - return DD_OK; -} - -ICOM_VTABLE(IDirectDraw2) xlib_dd2vt = { - ICOM_MSVTABLE_COMPAT_DummyRTTIVALUE - Xlib_IDirectDraw2Impl_QueryInterface, - IDirectDraw2Impl_AddRef, - Xlib_IDirectDraw2Impl_Release, - IDirectDraw2Impl_Compact, - IDirectDraw2Impl_CreateClipper, - Xlib_IDirectDraw2Impl_CreatePalette, - Xlib_IDirectDraw2Impl_CreateSurface, - IDirectDraw2Impl_DuplicateSurface, - Xlib_IDirectDraw2Impl_EnumDisplayModes, - IDirectDraw2Impl_EnumSurfaces, - IDirectDraw2Impl_FlipToGDISurface, - Xlib_IDirectDraw2Impl_GetCaps, - IDirectDraw2Impl_GetDisplayMode, - Xlib_IDirectDraw2Impl_GetFourCCCodes, - IDirectDraw2Impl_GetGDISurface, - IDirectDraw2Impl_GetMonitorFrequency, - IDirectDraw2Impl_GetScanLine, - IDirectDraw2Impl_GetVerticalBlankStatus, - IDirectDraw2Impl_Initialize, - IDirectDraw2Impl_RestoreDisplayMode, - Xlib_IDirectDraw2Impl_SetCooperativeLevel, - Xlib_IDirectDraw2Impl_SetDisplayMode, - IDirectDraw2Impl_WaitForVerticalBlank, - Xlib_IDirectDraw2Impl_GetAvailableVidMem -}; - -#if !defined(__STRICT_ANSI__) && defined(__GNUC__) -# define XCAST(fun) (typeof(xlib_dd4vt.fn##fun)) -#else -# define XCAST(fun) (void*) -#endif - -ICOM_VTABLE(IDirectDraw4) xlib_dd4vt = { - ICOM_MSVTABLE_COMPAT_DummyRTTIVALUE - XCAST(QueryInterface)Xlib_IDirectDraw2Impl_QueryInterface, - XCAST(AddRef)IDirectDraw2Impl_AddRef, - XCAST(Release)Xlib_IDirectDraw2Impl_Release, - XCAST(Compact)IDirectDraw2Impl_Compact, - XCAST(CreateClipper)IDirectDraw2Impl_CreateClipper, - XCAST(CreatePalette)Xlib_IDirectDraw2Impl_CreatePalette, - XCAST(CreateSurface)Xlib_IDirectDraw2Impl_CreateSurface, - XCAST(DuplicateSurface)IDirectDraw2Impl_DuplicateSurface, - XCAST(EnumDisplayModes)Xlib_IDirectDraw2Impl_EnumDisplayModes, - XCAST(EnumSurfaces)IDirectDraw2Impl_EnumSurfaces, - XCAST(FlipToGDISurface)IDirectDraw2Impl_FlipToGDISurface, - XCAST(GetCaps)Xlib_IDirectDraw2Impl_GetCaps, - XCAST(GetDisplayMode)IDirectDraw2Impl_GetDisplayMode, - XCAST(GetFourCCCodes)Xlib_IDirectDraw2Impl_GetFourCCCodes, - XCAST(GetGDISurface)IDirectDraw2Impl_GetGDISurface, - XCAST(GetMonitorFrequency)IDirectDraw2Impl_GetMonitorFrequency, - XCAST(GetScanLine)IDirectDraw2Impl_GetScanLine, - XCAST(GetVerticalBlankStatus)IDirectDraw2Impl_GetVerticalBlankStatus, - XCAST(Initialize)IDirectDraw2Impl_Initialize, - XCAST(RestoreDisplayMode)IDirectDraw2Impl_RestoreDisplayMode, - XCAST(SetCooperativeLevel)Xlib_IDirectDraw2Impl_SetCooperativeLevel, - XCAST(SetDisplayMode)Xlib_IDirectDraw2Impl_SetDisplayMode, - XCAST(WaitForVerticalBlank)IDirectDraw2Impl_WaitForVerticalBlank, - XCAST(GetAvailableVidMem)Xlib_IDirectDraw2Impl_GetAvailableVidMem, - IDirectDraw4Impl_GetSurfaceFromDC, - IDirectDraw4Impl_RestoreAllSurfaces, - IDirectDraw4Impl_TestCooperativeLevel, - IDirectDraw4Impl_GetDeviceIdentifier -}; -#undef XCAST - -#if !defined(__STRICT_ANSI__) && defined(__GNUC__) -# define XCAST(fun) (typeof(xlib_dd7vt.fn##fun)) -#else -# define XCAST(fun) (void*) -#endif - -ICOM_VTABLE(IDirectDraw7) xlib_dd7vt = { - ICOM_MSVTABLE_COMPAT_DummyRTTIVALUE - XCAST(QueryInterface)Xlib_IDirectDraw2Impl_QueryInterface, - XCAST(AddRef)IDirectDraw2Impl_AddRef, - XCAST(Release)Xlib_IDirectDraw2Impl_Release, - XCAST(Compact)IDirectDraw2Impl_Compact, - XCAST(CreateClipper)IDirectDraw2Impl_CreateClipper, - XCAST(CreatePalette)Xlib_IDirectDraw2Impl_CreatePalette, - XCAST(CreateSurface)Xlib_IDirectDraw2Impl_CreateSurface, - XCAST(DuplicateSurface)IDirectDraw2Impl_DuplicateSurface, - XCAST(EnumDisplayModes)Xlib_IDirectDraw2Impl_EnumDisplayModes, - XCAST(EnumSurfaces)IDirectDraw2Impl_EnumSurfaces, - XCAST(FlipToGDISurface)IDirectDraw2Impl_FlipToGDISurface, - XCAST(GetCaps)Xlib_IDirectDraw2Impl_GetCaps, - XCAST(GetDisplayMode)IDirectDraw2Impl_GetDisplayMode, - XCAST(GetFourCCCodes)Xlib_IDirectDraw2Impl_GetFourCCCodes, - XCAST(GetGDISurface)IDirectDraw2Impl_GetGDISurface, - XCAST(GetMonitorFrequency)IDirectDraw2Impl_GetMonitorFrequency, - XCAST(GetScanLine)IDirectDraw2Impl_GetScanLine, - XCAST(GetVerticalBlankStatus)IDirectDraw2Impl_GetVerticalBlankStatus, - XCAST(Initialize)IDirectDraw2Impl_Initialize, - XCAST(RestoreDisplayMode)IDirectDraw2Impl_RestoreDisplayMode, - XCAST(SetCooperativeLevel)Xlib_IDirectDraw2Impl_SetCooperativeLevel, - XCAST(SetDisplayMode)Xlib_IDirectDraw2Impl_SetDisplayMode, - XCAST(WaitForVerticalBlank)IDirectDraw2Impl_WaitForVerticalBlank, - XCAST(GetAvailableVidMem)Xlib_IDirectDraw2Impl_GetAvailableVidMem, - XCAST(GetSurfaceFromDC)IDirectDraw4Impl_GetSurfaceFromDC, - XCAST(RestoreAllSurfaces)IDirectDraw4Impl_RestoreAllSurfaces, - XCAST(TestCooperativeLevel)IDirectDraw4Impl_TestCooperativeLevel, - XCAST(GetDeviceIdentifier)IDirectDraw4Impl_GetDeviceIdentifier, - IDirectDraw7Impl_StartModeTest, - IDirectDraw7Impl_EvaluateMode, -}; -#undef XCAST diff --git a/dlls/ddraw/ddraw/xvidmode.c b/dlls/ddraw/ddraw/xvidmode.c new file mode 100644 index 00000000000..502df506e38 --- /dev/null +++ b/dlls/ddraw/ddraw/xvidmode.c @@ -0,0 +1,387 @@ +/* DirectDraw driver for User-based primary surfaces + * with XF86VidMode mode switching in full-screen mode. + * + * Copyright 2000 TransGaming Technologies Inc. + */ + +#include "config.h" + +#ifdef HAVE_LIBXXF86VM + +#include "debugtools.h" +#include "ts_xlib.h" +#include "ts_xf86vmode.h" +#include "x11drv.h" +#include + +#include +#include + +#include "ddraw_private.h" +#include "ddraw/main.h" +#include "ddraw/user.h" +#include "ddraw/xvidmode.h" +#include "dclipper/main.h" +#include "dpalette/main.h" +#include "dsurface/main.h" +#include "dsurface/dib.h" +#include "dsurface/user.h" + +DEFAULT_DEBUG_CHANNEL(ddraw); + +static ICOM_VTABLE(IDirectDraw7) XVidMode_DirectDraw_VTable; + +static const DDDEVICEIDENTIFIER2 xvidmode_device = +{ + "User/XF86VidMode Driver", + "WINE DirectDraw on User with XF86VidMode", + { { 0x00010001, 0x00010001 } }, + 0, 0, 0, 0, + /* 40c1b248-9d7d-4a29-b7d7-4cd8109f3d5d */ + {0x40c1b248,0x9d7d,0x4a29,{0xd7,0xb7,0x4c,0xd8,0x10,0x9f,0x3d,0x5d}}, + 0 +}; + +HRESULT XVidMode_DirectDraw_Create(const GUID* pGUID, LPDIRECTDRAW7* pIface, + IUnknown* pUnkOuter, BOOL ex); +HRESULT XVidMode_DirectDraw_Initialize(IDirectDrawImpl*, const GUID*); + +static const ddraw_driver xvidmode_driver = +{ + &xvidmode_device, + 11, /* User is 10 */ + XVidMode_DirectDraw_Create, + XVidMode_DirectDraw_Initialize +}; + +static XF86VidModeModeInfo** modes; +static DWORD num_modes; + +/* Called from DllInit, which is synchronised so there are no threading + * concerns. */ +static BOOL initialize(void) +{ + int nmodes; + int major, minor; + + if (X11DRV_GetXRootWindow() != DefaultRootWindow(display)) return FALSE; + + if (!TSXF86VidModeQueryVersion(display, &major, &minor)) return FALSE; + + if (!TSXF86VidModeGetAllModeLines(display, DefaultScreen(display), &nmodes, + &modes)) + return FALSE; + + num_modes = nmodes; + + TRACE("enabling XVidMode\n"); + + return TRUE; +} + +static void cleanup(void) +{ + TSXFree(modes); +} + +static HRESULT set_display_mode(XF86VidModeModeInfo* mode) +{ + int screen = DefaultScreen(display); + + TRACE("%d %d\n", mode->hdisplay, mode->vdisplay); + + /* This is questionable. Programs should leave switching unlocked when + * they exit. So the only reason the display should be locked is if + * another really doesn't want switches to happen. Maybe it would be better + * to detect an XF86VideModeZoomLocked error. */ + TSXF86VidModeLockModeSwitch(display, screen, False); + + TSXSync(display, False); + + TSXF86VidModeSwitchToMode(display, screen, mode); + + TSXSync(display, False); + +#if 0 /* doesn't work for me */ + TSXF86VidModeSetViewPort(display, screen, 0, 0); +#else + TSXWarpPointer(display, None, RootWindow(display, screen), 0, 0, 0, 0, 0, + 0); +#endif + + TSXFlush(display); + + return S_OK; +} + +static XF86VidModeModeInfo* choose_mode(DWORD dwWidth, DWORD dwHeight, + DWORD dwRefreshRate, DWORD dwFlags) +{ + XF86VidModeModeInfo* best = NULL; + int i; + + /* Choose the smallest mode that is large enough. */ + for (i=0; i < num_modes; i++) + { + if (modes[i]->hdisplay >= dwWidth && modes[i]->vdisplay >= dwHeight) + { + if (best == NULL) best = modes[i]; + else + { + if (modes[i]->hdisplay < best->hdisplay + || modes[i]->vdisplay < best->vdisplay) + best = modes[i]; + } + } + } + + /* all modes were too small, use the largest */ + if (best == NULL) + { + TRACE("all modes too small\n"); + + for (i=1; i < num_modes; i++) + { + if (best == NULL) best = modes[i]; + else + { + if (modes[i]->hdisplay > best->hdisplay + || modes[i]->vdisplay > best->vdisplay) + best = modes[i]; + } + } + } + + TRACE("using %d %d for %lu %lu\n", best->hdisplay, best->vdisplay, + dwWidth, dwHeight); + + return best; +} + +static XF86VidModeModeInfo* get_current_mode(void) +{ + XF86VidModeModeLine line; + int dotclock; + int i; + + TSXF86VidModeGetModeLine(display, DefaultScreen(display), &dotclock, + &line); + + for (i=0; i < num_modes; i++) + { + if (modes[i]->dotclock == dotclock + && modes[i]->hdisplay == line.hdisplay + && modes[i]->hsyncstart == line.hsyncstart + && modes[i]->hsyncend == line.hsyncend + && modes[i]->htotal == line.htotal + /* && modes[i]->hskew == line.hskew */ + && modes[i]->vdisplay == line.vdisplay + && modes[i]->vsyncstart == line.vsyncstart + && modes[i]->vsyncend == line.vsyncend + && modes[i]->vtotal == line.vtotal + && modes[i]->flags == line.flags) + return modes[i]; + } + + WARN("this can't happen\n"); + return modes[0]; /* should be the mode that X started in */ +} + +BOOL DDRAW_XVidMode_Init(HINSTANCE hInstDLL, DWORD fdwReason, LPVOID lpv) +{ + if (fdwReason == DLL_PROCESS_ATTACH) + { + if (initialize()) + DDRAW_register_driver(&xvidmode_driver); + } + else if (fdwReason == DLL_PROCESS_DETACH) + { + cleanup(); + } + + return TRUE; +} + +/* Not called from the vtable. */ +HRESULT XVidMode_DirectDraw_Construct(IDirectDrawImpl *This, BOOL ex) +{ + XVIDMODE_DDRAW_PRIV_VAR(priv,This); + HRESULT hr; + + TRACE("\n"); + + hr = User_DirectDraw_Construct(This, ex); + if (FAILED(hr)) return hr; + + This->final_release = XVidMode_DirectDraw_final_release; + + priv->xvidmode.original_mode = get_current_mode(); + priv->xvidmode.current_mode = priv->xvidmode.original_mode; + + ICOM_INIT_INTERFACE(This, IDirectDraw7, XVidMode_DirectDraw_VTable); + + return S_OK; +} + +/* This function is called from DirectDrawCreate(Ex) on the most-derived + * class to start construction. + * Not called from the vtable. */ +HRESULT XVidMode_DirectDraw_Create(const GUID* pGUID, LPDIRECTDRAW7* pIface, + IUnknown* pUnkOuter, BOOL ex) +{ + HRESULT hr; + IDirectDrawImpl* This; + + TRACE("\n"); + + assert(pUnkOuter == NULL); + + This = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, + sizeof(IDirectDrawImpl) + + sizeof(XVidMode_DirectDrawImpl)); + if (This == NULL) return E_OUTOFMEMORY; + + /* Note that this relation does *not* hold true if the DD object was + * CoCreateInstanced then Initialized. */ + This->private = (XVidMode_DirectDrawImpl *)(This+1); + + hr = XVidMode_DirectDraw_Construct(This, ex); + if (FAILED(hr)) + HeapFree(GetProcessHeap(), 0, This); + else + *pIface = ICOM_INTERFACE(This, IDirectDraw7); + + return hr; +} + +/* This function is called from Uninit_DirectDraw_Initialize on the + * most-derived-class to start initialization. + * Not called from the vtable. */ +HRESULT XVidMode_DirectDraw_Initialize(IDirectDrawImpl *This, const GUID* guid) +{ + HRESULT hr; + + TRACE("\n"); + + This->private = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, + sizeof(XVidMode_DirectDrawImpl)); + if (This->private == NULL) return E_OUTOFMEMORY; + + hr = XVidMode_DirectDraw_Construct(This, TRUE); /* XXX ex? */ + if (FAILED(hr)) + { + HeapFree(GetProcessHeap(), 0, This->private); + return hr; + } + + return DD_OK; +} + +/* Called from an internal function pointer. */ +void XVidMode_DirectDraw_final_release(IDirectDrawImpl *This) +{ + XVIDMODE_DDRAW_PRIV_VAR(priv, This); + + if (priv->xvidmode.current_mode != priv->xvidmode.original_mode) + set_display_mode(priv->xvidmode.original_mode); + + User_DirectDraw_final_release(This); +} + +HRESULT WINAPI +XVidMode_DirectDraw_GetDeviceIdentifier(LPDIRECTDRAW7 iface, + LPDDDEVICEIDENTIFIER2 pDDDI, + DWORD dwFlags) +{ + *pDDDI = xvidmode_device; + return DD_OK; +} + +HRESULT WINAPI +XVidMode_DirectDraw_RestoreDisplayMode(LPDIRECTDRAW7 iface) +{ + ICOM_THIS(IDirectDrawImpl, iface); + HRESULT hr; + + TRACE("\n"); + + hr = Main_DirectDraw_RestoreDisplayMode(iface); + if (SUCCEEDED(hr)) + { + XVIDMODE_DDRAW_PRIV_VAR(priv, This); + + if (priv->xvidmode.current_mode != priv->xvidmode.original_mode) + { + set_display_mode(priv->xvidmode.original_mode); + priv->xvidmode.current_mode = priv->xvidmode.original_mode; + } + } + + return hr; +} + +HRESULT WINAPI +XVidMode_DirectDraw_SetDisplayMode(LPDIRECTDRAW7 iface, DWORD dwWidth, + DWORD dwHeight, DWORD dwBPP, + DWORD dwRefreshRate, DWORD dwFlags) +{ + ICOM_THIS(IDirectDrawImpl, iface); + + HRESULT hr; + + TRACE("(%p)->(%ldx%ldx%ld,%ld Hz,%08lx)\n",This,dwWidth,dwHeight,dwBPP,dwRefreshRate,dwFlags); + hr = User_DirectDraw_SetDisplayMode(iface, dwWidth, dwHeight, dwBPP, + dwRefreshRate, dwFlags); + + if (SUCCEEDED(hr)) + { + XVIDMODE_DDRAW_PRIV_VAR(priv, This); + XF86VidModeModeInfo* new_mode; + + new_mode = choose_mode(dwWidth, dwHeight, dwRefreshRate, dwFlags); + + if (new_mode != NULL && new_mode != priv->xvidmode.current_mode) + { + priv->xvidmode.current_mode = new_mode; + set_display_mode(priv->xvidmode.current_mode); + } + } + + return hr; +} + +static ICOM_VTABLE(IDirectDraw7) XVidMode_DirectDraw_VTable = +{ + Main_DirectDraw_QueryInterface, + Main_DirectDraw_AddRef, + Main_DirectDraw_Release, + Main_DirectDraw_Compact, + Main_DirectDraw_CreateClipper, + Main_DirectDraw_CreatePalette, + Main_DirectDraw_CreateSurface, + Main_DirectDraw_DuplicateSurface, + User_DirectDraw_EnumDisplayModes, + Main_DirectDraw_EnumSurfaces, + Main_DirectDraw_FlipToGDISurface, + User_DirectDraw_GetCaps, + Main_DirectDraw_GetDisplayMode, + Main_DirectDraw_GetFourCCCodes, + Main_DirectDraw_GetGDISurface, + Main_DirectDraw_GetMonitorFrequency, + Main_DirectDraw_GetScanLine, + Main_DirectDraw_GetVerticalBlankStatus, + Main_DirectDraw_Initialize, + XVidMode_DirectDraw_RestoreDisplayMode, + Main_DirectDraw_SetCooperativeLevel, + XVidMode_DirectDraw_SetDisplayMode, + Main_DirectDraw_WaitForVerticalBlank, + Main_DirectDraw_GetAvailableVidMem, + Main_DirectDraw_GetSurfaceFromDC, + Main_DirectDraw_RestoreAllSurfaces, + Main_DirectDraw_TestCooperativeLevel, + XVidMode_DirectDraw_GetDeviceIdentifier, + Main_DirectDraw_StartModeTest, + Main_DirectDraw_EvaluateMode +}; + +#endif /* HAVE_LIBXXF86VM */ diff --git a/dlls/ddraw/ddraw/xvidmode.h b/dlls/ddraw/ddraw/xvidmode.h new file mode 100644 index 00000000000..8ba0b18b829 --- /dev/null +++ b/dlls/ddraw/ddraw/xvidmode.h @@ -0,0 +1,39 @@ +/* Copyright 2000 TransGaming Technologies, Inc. */ +#ifndef WINE_DDRAW_DDRAW_XVIDMODE_H_INCLUDED +#define WINE_DDRAW_DDRAW_XVIDMODE_H_INCLUDED + +#include + +#define XVIDMODE_DDRAW_PRIV(ddraw) \ + ((XVidMode_DirectDrawImpl*)((ddraw)->private)) +#define XVIDMODE_DDRAW_PRIV_VAR(name,ddraw) \ + XVidMode_DirectDrawImpl* name = XVIDMODE_DDRAW_PRIV(ddraw) + +typedef struct +{ + XF86VidModeModeInfo* original_mode; + XF86VidModeModeInfo* current_mode; +} XVidMode_DirectDrawImpl_Part; + +typedef struct +{ + User_DirectDrawImpl_Part user; + XVidMode_DirectDrawImpl_Part xvidmode; +} XVidMode_DirectDrawImpl; + +void XVidMode_DirectDraw_final_release(IDirectDrawImpl* This); +HRESULT XVidMode_DirectDraw_Construct(IDirectDrawImpl *This, BOOL ex); +HRESULT XVidMode_DirectDraw_Create(const GUID* pGUID, LPDIRECTDRAW7* pIface, + IUnknown* pUnkOuter, BOOL ex); +HRESULT WINAPI +XVidMode_DirectDraw_GetDeviceIdentifier(LPDIRECTDRAW7 iface, + LPDDDEVICEIDENTIFIER2 pDDDI, + DWORD dwFlags); +HRESULT WINAPI +XVidMode_DirectDraw_SetDisplayMode(LPDIRECTDRAW7 iface, DWORD dwWidth, + DWORD dwHeight, DWORD dwBPP, + DWORD dwRefreshRate, DWORD dwFlags); +HRESULT WINAPI +XVidMode_DirectDraw_RestoreDisplayMode(LPDIRECTDRAW7 iface); + +#endif diff --git a/dlls/ddraw/ddraw_private.h b/dlls/ddraw/ddraw_private.h index 803a4b5dfcf..20617fc051d 100644 --- a/dlls/ddraw/ddraw_private.h +++ b/dlls/ddraw/ddraw_private.h @@ -1,3 +1,5 @@ +/* Copyright 2000 TransGaming Technologies Inc. */ + #ifndef __WINE_DLLS_DDRAW_DDRAW_PRIVATE_H #define __WINE_DLLS_DDRAW_DDRAW_PRIVATE_H @@ -8,223 +10,146 @@ #include "wingdi.h" #include "winuser.h" #include "ddraw.h" +#include "ddcomimpl.h" -static const char WINE_UNUSED *ddProp = "WINE_DDRAW_Property"; - -/**************************************************************************** - * This is the main DirectDraw driver interface. It is supposed to be called - * only from the base functions and only used by those. It should neither be - * be called nor used within the interfaces. - */ -typedef struct ddraw_driver { - LPGUID guid; /*under which we are referenced and enumerated*/ - CHAR type[20]; /* type, usually "display" */ - CHAR name[40]; /* name, like "WINE Foobar DirectDraw Driver" */ - int preference; /* how good we are. dga might get 100, xlib 50*/ - HRESULT (*createDDRAW)(LPDIRECTDRAW*); /* also check if arg is NULL */ -} ddraw_driver; - -extern void ddraw_register_driver(ddraw_driver*); - -/***************************************************************************** - * The implementation structures. They must not contain driver specific stuff. - * - * For private data the "LPVOID private" pointer should be used. - */ - -typedef struct IDirectDrawImpl IDirectDrawImpl; -typedef struct IDirectDraw2Impl IDirectDraw2Impl; -typedef struct IDirectDraw3Impl IDirectDraw3Impl; -typedef struct IDirectDraw4Impl IDirectDraw4Impl; -typedef struct IDirectDrawPaletteImpl IDirectDrawPaletteImpl; -typedef struct IDirectDrawClipperImpl IDirectDrawClipperImpl; - -typedef struct IDirectDrawSurfaceImpl IDirectDrawSurfaceImpl; -typedef struct IDirectDrawSurface2Impl IDirectDrawSurface2Impl; -typedef struct IDirectDrawSurface4Impl IDirectDrawSurface4Impl; - - -extern struct ICOM_VTABLE(IDirectDrawClipper) ddclipvt; -extern struct ICOM_VTABLE(IDirectDrawPalette) ddraw_ddpalvt; +/* XXX Put this somewhere proper. */ +#define DD_STRUCT_INIT(x) \ + do { \ + memset((x), 0, sizeof(*(x))); \ + (x)->dwSize = sizeof(*x); \ + } while (0) /***************************************************************************** * IDirectDraw implementation structure */ -struct _common_directdrawdata + +typedef struct IDirectDrawImpl IDirectDrawImpl; +typedef struct IDirectDrawPaletteImpl IDirectDrawPaletteImpl; +typedef struct IDirectDrawClipperImpl IDirectDrawClipperImpl; +typedef struct IDirectDrawSurfaceImpl IDirectDrawSurfaceImpl; + +typedef void (*pixel_convert_func)(void *src, void *dst, DWORD width, + DWORD height, LONG pitch, + IDirectDrawPaletteImpl *palette); + +typedef void (*palette_convert_func)(LPPALETTEENTRY palent, + void *screen_palette, DWORD start, + DWORD count); + +struct IDirectDrawImpl { - int ref; /* for this structure, only once per obj */ - DDPIXELFORMAT directdraw_pixelformat; + ICOM_VFIELD_MULTI(IDirectDraw7); + ICOM_VFIELD_MULTI(IDirectDraw4); + ICOM_VFIELD_MULTI(IDirectDraw2); + ICOM_VFIELD_MULTI(IDirectDraw); + + DWORD ref; + + /* TRUE if created via DirectDrawCreateEx or CoCreateInstance, + * FALSE if created via DirectDrawCreate. */ + BOOL ex; + + /* Linked list of surfaces, joined by next_ddraw in IDirectSurfaceImpl. */ + IDirectDrawSurfaceImpl* surfaces; + /* Linked list of palettes, joined by next_ddraw. */ + IDirectDrawPaletteImpl* palettes; + /* Linked list of clippers, joined by next_ddraw. */ + IDirectDrawClipperImpl* clippers; + + IDirectDrawSurfaceImpl* primary_surface; + + HWND window; + DWORD cooperative_level; + WNDPROC original_wndproc; + + DWORD width, height; + LONG pitch; + DDPIXELFORMAT pixelformat; + + /* Should each of these go into some structure? */ + DWORD orig_width, orig_height; + LONG orig_pitch; + DDPIXELFORMAT orig_pixelformat; + + /* Called when the refcount goes to 0. */ + void (*final_release)(IDirectDrawImpl *This); + + HRESULT (*create_palette)(IDirectDrawImpl* This, DWORD dwFlags, + LPDIRECTDRAWPALETTE* ppPalette, + LPUNKNOWN pUnkOuter); + + /* Surface creation functions. For all of these, pOuter == NULL. */ + + /* Do not create any backbuffers or the flipping chain. */ + HRESULT (*create_primary)(IDirectDrawImpl* This, + const DDSURFACEDESC2* pDDSD, + LPDIRECTDRAWSURFACE7* ppSurf, LPUNKNOWN pOuter); + + /* Primary may be NULL if we are creating an unattached backbuffer. */ + HRESULT (*create_backbuffer)(IDirectDrawImpl* This, + const DDSURFACEDESC2* pDDSD, + LPDIRECTDRAWSURFACE7* ppSurf, + LPUNKNOWN pOuter, + IDirectDrawSurfaceImpl* primary); + + /* shiny happy offscreenplain surfaces */ + HRESULT (*create_offscreen)(IDirectDrawImpl* This, + const DDSURFACEDESC2* pDDSD, + LPDIRECTDRAWSURFACE7* ppSurf, + LPUNKNOWN pOuter); + + /* dwMipMapLevel is specified as per OpenGL. (i.e. 0 is base) */ + HRESULT (*create_texture)(IDirectDrawImpl* This, + const DDSURFACEDESC2* pDDSD, + LPDIRECTDRAWSURFACE7* ppSurf, LPUNKNOWN pOuter, + DWORD dwMipMapLevel); + + HRESULT (*create_zbuffer)(IDirectDrawImpl* This, + const DDSURFACEDESC2* pDDSD, + LPDIRECTDRAWSURFACE7* ppSurf, LPUNKNOWN pOuter); + + LPVOID private; + + /* Everything below here is still questionable. */ + DDPIXELFORMAT screen_pixelformat; int pixmap_depth; - void (*pixel_convert)(void *src, void *dst, DWORD width, DWORD height, LONG pitch, IDirectDrawPaletteImpl *palette); - void (*palette_convert)(LPPALETTEENTRY palent, void *screen_palette, DWORD start, DWORD count); - DWORD height,width; /* set by SetDisplayMode */ - HWND mainWindow; /* set by SetCooperativeLevel */ + pixel_convert_func pixel_convert; + palette_convert_func palette_convert; + const struct tagDC_FUNCS *funcs, *old_funcs; /* DISPLAY.DRV overrides */ /* This is for the fake mainWindow */ - ATOM winclass; - HWND window; - PAINTSTRUCT ps; - int paintable; - LPVOID private; + ATOM winclass; + PAINTSTRUCT ps; + BOOL paintable; }; -/***************************************************************************** - * IDirectDraw implementation structure - * - * Note: All the IDirectDraw*Impl structures _MUST_ have IDENTICAL layout, - * since we reuse functions across interface versions. - */ -struct IDirectDrawImpl -{ - /* IUnknown fields */ - ICOM_VFIELD(IDirectDraw); - DWORD ref; - - /* IDirectDraw fields */ - struct _common_directdrawdata *d; -}; - -struct IDirectDraw2Impl -{ - /* IUnknown fields */ - ICOM_VFIELD(IDirectDraw2); - DWORD ref; - - /* IDirectDraw fields */ - struct _common_directdrawdata *d; -}; - -extern HRESULT WINAPI IDirectDrawImpl_SetDisplayMode( - LPDIRECTDRAW iface,DWORD width,DWORD height,DWORD depth -); - -extern HRESULT WINAPI IDirectDraw2Impl_DuplicateSurface( - LPDIRECTDRAW2 iface,LPDIRECTDRAWSURFACE src,LPDIRECTDRAWSURFACE *dst -); -extern HRESULT WINAPI IDirectDraw2Impl_SetCooperativeLevel( - LPDIRECTDRAW2 iface,HWND hwnd,DWORD cooplevel -); -extern HRESULT WINAPI IDirectDraw2Impl_GetCaps( - LPDIRECTDRAW2 iface,LPDDCAPS caps1,LPDDCAPS caps2 -) ; -extern HRESULT WINAPI IDirectDraw2Impl_CreateClipper( - LPDIRECTDRAW2 iface,DWORD x,LPDIRECTDRAWCLIPPER *lpddclip,LPUNKNOWN lpunk -); -extern HRESULT WINAPI common_IDirectDraw2Impl_CreatePalette( - IDirectDraw2Impl* This,DWORD dwFlags,LPPALETTEENTRY palent, - IDirectDrawPaletteImpl **lpddpal,LPUNKNOWN lpunk,int *psize -); -extern HRESULT WINAPI IDirectDraw2Impl_CreatePalette( - LPDIRECTDRAW2 iface,DWORD dwFlags,LPPALETTEENTRY palent,LPDIRECTDRAWPALETTE *lpddpal,LPUNKNOWN lpunk -); -extern HRESULT WINAPI IDirectDraw2Impl_RestoreDisplayMode(LPDIRECTDRAW2 iface); -extern HRESULT WINAPI IDirectDraw2Impl_WaitForVerticalBlank( - LPDIRECTDRAW2 iface,DWORD x,HANDLE h -); -extern ULONG WINAPI IDirectDraw2Impl_AddRef(LPDIRECTDRAW2 iface); -extern ULONG WINAPI IDirectDraw2Impl_Release(LPDIRECTDRAW2 iface); -extern HRESULT WINAPI IDirectDraw2Impl_QueryInterface( - LPDIRECTDRAW2 iface,REFIID refiid,LPVOID *obj -); -extern HRESULT WINAPI IDirectDraw2Impl_GetVerticalBlankStatus( - LPDIRECTDRAW2 iface,BOOL *status -); -extern HRESULT WINAPI IDirectDraw2Impl_EnumDisplayModes( - LPDIRECTDRAW2 iface,DWORD dwFlags,LPDDSURFACEDESC lpddsfd,LPVOID context,LPDDENUMMODESCALLBACK modescb -); -extern HRESULT WINAPI IDirectDraw2Impl_GetDisplayMode( - LPDIRECTDRAW2 iface,LPDDSURFACEDESC lpddsfd -); -extern HRESULT WINAPI IDirectDraw2Impl_FlipToGDISurface(LPDIRECTDRAW2 iface); -extern HRESULT WINAPI IDirectDraw2Impl_GetMonitorFrequency( - LPDIRECTDRAW2 iface,LPDWORD freq -); -extern HRESULT WINAPI IDirectDraw2Impl_GetFourCCCodes( - LPDIRECTDRAW2 iface,LPDWORD x,LPDWORD y -); -extern HRESULT WINAPI IDirectDraw2Impl_EnumSurfaces( - LPDIRECTDRAW2 iface,DWORD x,LPDDSURFACEDESC ddsfd,LPVOID context, - LPDDENUMSURFACESCALLBACK ddsfcb -); -extern HRESULT WINAPI IDirectDraw2Impl_Compact( LPDIRECTDRAW2 iface ); -extern HRESULT WINAPI IDirectDraw2Impl_GetGDISurface( - LPDIRECTDRAW2 iface, LPDIRECTDRAWSURFACE *lplpGDIDDSSurface -); -extern HRESULT WINAPI IDirectDraw2Impl_GetScanLine( - LPDIRECTDRAW2 iface, LPDWORD lpdwScanLine -); -extern HRESULT WINAPI IDirectDraw2Impl_Initialize(LPDIRECTDRAW2 iface, GUID *lpGUID); -extern HRESULT WINAPI IDirectDraw2Impl_SetDisplayMode( - LPDIRECTDRAW2 iface,DWORD width,DWORD height,DWORD depth, - DWORD dwRefreshRate, DWORD dwFlags -); -extern HRESULT WINAPI IDirectDraw2Impl_GetAvailableVidMem( - LPDIRECTDRAW2 iface,LPDDSCAPS ddscaps,LPDWORD total,LPDWORD free -); -extern HRESULT common_off_screen_CreateSurface( - IDirectDraw2Impl* This,IDirectDrawSurfaceImpl* lpdsf -); - -/* - * IDirectDraw4 implementation structure - */ -struct IDirectDraw4Impl -{ - /* IUnknown fields */ - ICOM_VFIELD(IDirectDraw4); - DWORD ref; - /* IDirectDraw4 fields */ - struct _common_directdrawdata *d; -}; - -extern HRESULT WINAPI IDirectDraw4Impl_GetSurfaceFromDC( - LPDIRECTDRAW4 iface, HDC hdc, LPDIRECTDRAWSURFACE *lpDDS -); -extern HRESULT WINAPI IDirectDraw4Impl_RestoreAllSurfaces(LPDIRECTDRAW4 iface); -extern HRESULT WINAPI IDirectDraw4Impl_TestCooperativeLevel(LPDIRECTDRAW4 iface); -extern HRESULT WINAPI IDirectDraw4Impl_GetDeviceIdentifier(LPDIRECTDRAW4 iface, - LPDDDEVICEIDENTIFIER lpdddi, - DWORD dwFlags -); - -extern HRESULT WINAPI IDirectDraw7Impl_StartModeTest( - LPDIRECTDRAW7 iface,LPSIZE modetotest,DWORD num,DWORD flags -); -extern HRESULT WINAPI IDirectDraw7Impl_EvaluateMode( - LPDIRECTDRAW7 iface,DWORD flags,DWORD *seconduntiltimeout -); - /***************************************************************************** * IDirectDrawPalette implementation structure */ struct IDirectDrawPaletteImpl { /* IUnknown fields */ - ICOM_VFIELD(IDirectDrawPalette); - DWORD ref; + ICOM_VFIELD_MULTI(IDirectDrawPalette); + DWORD ref; /* IDirectDrawPalette fields */ - IDirectDrawImpl* ddraw; /* direct draw, no reference count */ + DWORD flags; + HPALETTE hpal; + WORD palVersion, palNumEntries; /* LOGPALETTE */ PALETTEENTRY palents[256]; - /* This is to store the palette in 'screen format' */ int screen_palents[256]; + + VOID (*final_release)(IDirectDrawPaletteImpl* This); + + IDirectDrawImpl* ddraw_owner; + IDirectDrawPaletteImpl* prev_ddraw; + IDirectDrawPaletteImpl* next_ddraw; + LPVOID private; }; -extern HRESULT WINAPI IDirectDrawPaletteImpl_GetEntries(LPDIRECTDRAWPALETTE,DWORD,DWORD,DWORD,LPPALETTEENTRY); -extern HRESULT WINAPI IDirectDrawPaletteImpl_SetEntries(LPDIRECTDRAWPALETTE,DWORD,DWORD,DWORD,LPPALETTEENTRY); -extern ULONG WINAPI IDirectDrawPaletteImpl_Release(LPDIRECTDRAWPALETTE); -extern ULONG WINAPI IDirectDrawPaletteImpl_AddRef(LPDIRECTDRAWPALETTE); -extern HRESULT WINAPI IDirectDrawPaletteImpl_Initialize(LPDIRECTDRAWPALETTE,LPDIRECTDRAW,DWORD,LPPALETTEENTRY); -extern HRESULT WINAPI IDirectDrawPaletteImpl_GetCaps(LPDIRECTDRAWPALETTE,LPDWORD); -extern HRESULT WINAPI IDirectDrawPaletteImpl_QueryInterface(LPDIRECTDRAWPALETTE,REFIID,LPVOID *); - -extern HRESULT WINAPI common_IDirectDraw2Impl_CreatePalette( - IDirectDraw2Impl* This,DWORD dwFlags,LPPALETTEENTRY palent, - IDirectDrawPaletteImpl **lpddpal,LPUNKNOWN lpunk,int *psize -); /***************************************************************************** * IDirectDrawClipper implementation structure @@ -232,145 +157,114 @@ extern HRESULT WINAPI common_IDirectDraw2Impl_CreatePalette( struct IDirectDrawClipperImpl { /* IUnknown fields */ - ICOM_VFIELD(IDirectDrawClipper); - DWORD ref; + ICOM_VFIELD_MULTI(IDirectDrawClipper); + DWORD ref; /* IDirectDrawClipper fields */ HWND hWnd; + + IDirectDrawImpl* ddraw_owner; + IDirectDrawClipperImpl* prev_ddraw; + IDirectDrawClipperImpl* next_ddraw; }; /***************************************************************************** * IDirectDrawSurface implementation structure */ -struct IDirect3DTexture2Impl; -struct _common_directdrawsurface -{ - IDirectDrawPaletteImpl* palette; - IDirectDraw2Impl* ddraw; - - struct _surface_chain *chain; - - DDSURFACEDESC surface_desc; - - /* For Get / Release DC methods */ - HBITMAP DIBsection; - void *bitmap_data; - HDC hdc; - HGDIOBJ holdbitmap; - LPDIRECTDRAWCLIPPER lpClipper; - - /* Callback for loaded textures */ - struct IDirect3DTexture2Impl* texture; - HRESULT WINAPI (*SetColorKey_cb)(struct IDirect3DTexture2Impl *texture, DWORD dwFlags, LPDDCOLORKEY ckey ) ; -}; -extern IDirectDrawSurface4Impl* _common_find_flipto(IDirectDrawSurface4Impl* This,IDirectDrawSurface4Impl* flipto); struct IDirectDrawSurfaceImpl { /* IUnknown fields */ - ICOM_VFIELD(IDirectDrawSurface); - DWORD ref; + ICOM_VFIELD_MULTI(IDirectDrawSurface7); + ICOM_VFIELD_MULTI(IDirectDrawSurface3); + DWORD ref; + + struct IDirectDrawSurfaceImpl* attached; /* attached surfaces */ + + struct IDirectDrawSurfaceImpl* next_ddraw; /* ddraw surface chain */ + struct IDirectDrawSurfaceImpl* prev_ddraw; + struct IDirectDrawSurfaceImpl* next_attached; /* attached surface chain */ + struct IDirectDrawSurfaceImpl* prev_attached; + + IDirectDrawImpl* ddraw_owner; + IDirectDrawSurfaceImpl* surface_owner; + + IDirectDrawPaletteImpl* palette; /* strong ref */ + IDirectDrawClipperImpl* clipper; /* strong ref */ + + DDSURFACEDESC2 surface_desc; + + HDC hDC; + BOOL dc_in_use; + + HRESULT (*duplicate_surface)(IDirectDrawSurfaceImpl* src, + LPDIRECTDRAWSURFACE7* dst); + void (*final_release)(IDirectDrawSurfaceImpl *This); + BOOL (*attach)(IDirectDrawSurfaceImpl *This, IDirectDrawSurfaceImpl *to); + BOOL (*detach)(IDirectDrawSurfaceImpl *This); + void (*lock_update)(IDirectDrawSurfaceImpl* This, LPCRECT pRect); + void (*unlock_update)(IDirectDrawSurfaceImpl* This, LPCRECT pRect); + void (*lose_surface)(IDirectDrawSurfaceImpl* This); + void (*flip_data)(IDirectDrawSurfaceImpl* front, + IDirectDrawSurfaceImpl* back); + void (*flip_update)(IDirectDrawSurfaceImpl* front); + HRESULT (*get_dc)(IDirectDrawSurfaceImpl* This, HDC* phDC); + HRESULT (*release_dc)(IDirectDrawSurfaceImpl* This, HDC hDC); + void (*set_palette)(IDirectDrawSurfaceImpl* This, IDirectDrawPaletteImpl* pal); + void (*update_palette)(IDirectDrawSurfaceImpl* This, IDirectDrawPaletteImpl* pal, + DWORD dwStart, DWORD dwCount, LPPALETTEENTRY palent); + HWND (*get_display_window)(IDirectDrawSurfaceImpl *This); + + struct PrivateData* private_data; + + DWORD max_lod; + DWORD priority; + + BOOL lost; + + DWORD uniqueness_value; - /* IDirectDrawSurface fields */ - struct _common_directdrawsurface s; LPVOID private; + + /* Everything below here is dodgy. */ + /* For Direct3D use */ + LPVOID aux_ctx, aux_data; + void (*aux_release)(LPVOID ctx, LPVOID data); + BOOL (*aux_flip)(LPVOID ctx, LPVOID data); + void (*aux_unlock)(LPVOID ctx, LPVOID data, LPRECT lpRect); + struct IDirect3DTexture2Impl* texture; + HRESULT WINAPI (*SetColorKey_cb)(struct IDirect3DTexture2Impl *texture, DWORD dwFlags, LPDDCOLORKEY ckey ) ; }; /***************************************************************************** - * IDirectDrawSurface2 implementation structure + * Driver initialisation functions. */ -struct IDirectDrawSurface2Impl -{ - /* IUnknown fields */ - ICOM_VFIELD(IDirectDrawSurface2); - DWORD ref; - /* IDirectDrawSurface2 fields */ - struct _common_directdrawsurface s; - LPVOID private; -}; +BOOL DDRAW_User_Init(HINSTANCE, DWORD, LPVOID); -/***************************************************************************** - * IDirectDrawSurface3 implementation structure +typedef struct { + const DDDEVICEIDENTIFIER2* info; + int preference; /* how good we are. dga might get 100, xlib 50*/ + HRESULT (*create)(const GUID*, LPDIRECTDRAW7*, LPUNKNOWN, BOOL ex); + + /* For IDirectDraw7::Initialize. */ + HRESULT (*init)(IDirectDrawImpl *, const GUID*); +} ddraw_driver; + +void DDRAW_register_driver(const ddraw_driver*); + +const ddraw_driver* DDRAW_FindDriver(const GUID* guid); + +/****************************************************************************** + * Random utilities */ -struct IDirectDrawSurface3Impl -{ - /* IUnknown fields */ - ICOM_VFIELD(IDirectDrawSurface3); - DWORD ref; - /* IDirectDrawSurface3 fields */ - struct _common_directdrawsurface s; - LPVOID private; -}; - -/***************************************************************************** - * IDirectDrawSurface4 implementation structure - */ -struct IDirectDrawSurface4Impl -{ - /* IUnknown fields */ - ICOM_VFIELD(IDirectDrawSurface4); - DWORD ref; - - /* IDirectDrawSurface4 fields */ - struct _common_directdrawsurface s; - LPVOID private; -} ; - -struct _surface_chain { - IDirectDrawSurface4Impl **surfaces; - int nrofsurfaces; -}; -extern HRESULT common_off_screen_CreateSurface(IDirectDraw2Impl* This,IDirectDrawSurfaceImpl* lpdsf); -extern HRESULT WINAPI IDirectDrawSurface4Impl_Lock(LPDIRECTDRAWSURFACE4 iface,LPRECT lprect,LPDDSURFACEDESC lpddsd,DWORD flags, HANDLE hnd); -extern HRESULT WINAPI IDirectDrawSurface4Impl_Unlock( LPDIRECTDRAWSURFACE4 iface,LPVOID surface); -extern HRESULT WINAPI IDirectDrawSurface4Impl_Blt(LPDIRECTDRAWSURFACE4 iface,LPRECT rdst,LPDIRECTDRAWSURFACE4 src,LPRECT rsrc,DWORD dwFlags,LPDDBLTFX lpbltfx); -extern HRESULT WINAPI IDirectDrawSurface4Impl_BltFast(LPDIRECTDRAWSURFACE4 iface,DWORD dstx,DWORD dsty,LPDIRECTDRAWSURFACE4 src,LPRECT rsrc,DWORD trans); -extern HRESULT WINAPI IDirectDrawSurface4Impl_BltBatch(LPDIRECTDRAWSURFACE4 iface,LPDDBLTBATCH ddbltbatch,DWORD x,DWORD y); -extern HRESULT WINAPI IDirectDrawSurface4Impl_GetCaps(LPDIRECTDRAWSURFACE4 iface,LPDDSCAPS caps); -extern HRESULT WINAPI IDirectDrawSurface4Impl_GetSurfaceDesc(LPDIRECTDRAWSURFACE4 iface,LPDDSURFACEDESC ddsd); -extern ULONG WINAPI IDirectDrawSurface4Impl_AddRef(LPDIRECTDRAWSURFACE4 iface); -extern HRESULT WINAPI IDirectDrawSurface4Impl_GetAttachedSurface(LPDIRECTDRAWSURFACE4 iface,LPDDSCAPS lpddsd,LPDIRECTDRAWSURFACE4 *lpdsf); -extern HRESULT WINAPI IDirectDrawSurface4Impl_Initialize(LPDIRECTDRAWSURFACE4 iface,LPDIRECTDRAW ddraw,LPDDSURFACEDESC lpdsfd); -extern HRESULT WINAPI IDirectDrawSurface4Impl_GetPixelFormat(LPDIRECTDRAWSURFACE4 iface,LPDDPIXELFORMAT pf); -extern HRESULT WINAPI IDirectDrawSurface4Impl_GetBltStatus(LPDIRECTDRAWSURFACE4 iface,DWORD dwFlags); -extern HRESULT WINAPI IDirectDrawSurface4Impl_GetOverlayPosition(LPDIRECTDRAWSURFACE4 iface,LPLONG x1,LPLONG x2); -extern HRESULT WINAPI IDirectDrawSurface4Impl_SetClipper(LPDIRECTDRAWSURFACE4 iface,LPDIRECTDRAWCLIPPER lpClipper); -extern HRESULT WINAPI IDirectDrawSurface4Impl_AddAttachedSurface(LPDIRECTDRAWSURFACE4 iface,LPDIRECTDRAWSURFACE4 surf); -extern HRESULT WINAPI IDirectDrawSurface4Impl_GetDC(LPDIRECTDRAWSURFACE4 iface,HDC* lphdc); -extern HRESULT WINAPI IDirectDrawSurface4Impl_ReleaseDC(LPDIRECTDRAWSURFACE4 iface,HDC hdc); -extern HRESULT WINAPI IDirectDrawSurface4Impl_QueryInterface(LPDIRECTDRAWSURFACE4 iface,REFIID refiid,LPVOID *obj); -extern HRESULT WINAPI IDirectDrawSurface4Impl_IsLost(LPDIRECTDRAWSURFACE4 iface); -extern HRESULT WINAPI IDirectDrawSurface4Impl_EnumAttachedSurfaces(LPDIRECTDRAWSURFACE4 iface,LPVOID context,LPDDENUMSURFACESCALLBACK esfcb); -extern HRESULT WINAPI IDirectDrawSurface4Impl_Restore(LPDIRECTDRAWSURFACE4 iface); -extern HRESULT WINAPI IDirectDrawSurface4Impl_SetColorKey(LPDIRECTDRAWSURFACE4 iface, DWORD dwFlags, LPDDCOLORKEY ckey); -extern HRESULT WINAPI IDirectDrawSurface4Impl_AddOverlayDirtyRect(LPDIRECTDRAWSURFACE4 iface,LPRECT lpRect); -extern HRESULT WINAPI IDirectDrawSurface4Impl_DeleteAttachedSurface(LPDIRECTDRAWSURFACE4 iface,DWORD dwFlags,LPDIRECTDRAWSURFACE4 lpDDSAttachedSurface); -extern HRESULT WINAPI IDirectDrawSurface4Impl_EnumOverlayZOrders(LPDIRECTDRAWSURFACE4 iface,DWORD dwFlags,LPVOID lpContext,LPDDENUMSURFACESCALLBACK lpfnCallback); -extern HRESULT WINAPI IDirectDrawSurface4Impl_GetClipper(LPDIRECTDRAWSURFACE4 iface,LPDIRECTDRAWCLIPPER* lplpDDClipper); -extern HRESULT WINAPI IDirectDrawSurface4Impl_GetColorKey(LPDIRECTDRAWSURFACE4 iface,DWORD dwFlags,LPDDCOLORKEY lpDDColorKey); -extern HRESULT WINAPI IDirectDrawSurface4Impl_GetFlipStatus(LPDIRECTDRAWSURFACE4 iface,DWORD dwFlags); -extern HRESULT WINAPI IDirectDrawSurface4Impl_GetPalette(LPDIRECTDRAWSURFACE4 iface,LPDIRECTDRAWPALETTE* lplpDDPalette); -extern HRESULT WINAPI IDirectDrawSurface4Impl_SetOverlayPosition(LPDIRECTDRAWSURFACE4 iface,LONG lX,LONG lY); -extern HRESULT WINAPI IDirectDrawSurface4Impl_UpdateOverlay(LPDIRECTDRAWSURFACE4 iface,LPRECT lpSrcRect,LPDIRECTDRAWSURFACE4 lpDDDestSurface,LPRECT lpDestRect,DWORD dwFlags,LPDDOVERLAYFX lpDDOverlayFx); -extern HRESULT WINAPI IDirectDrawSurface4Impl_UpdateOverlayDisplay(LPDIRECTDRAWSURFACE4 iface,DWORD dwFlags); -extern HRESULT WINAPI IDirectDrawSurface4Impl_UpdateOverlayZOrder(LPDIRECTDRAWSURFACE4 iface,DWORD dwFlags,LPDIRECTDRAWSURFACE4 lpDDSReference); -extern HRESULT WINAPI IDirectDrawSurface4Impl_GetDDInterface(LPDIRECTDRAWSURFACE4 iface,LPVOID* lplpDD); -extern HRESULT WINAPI IDirectDrawSurface4Impl_PageLock(LPDIRECTDRAWSURFACE4 iface,DWORD dwFlags); -extern HRESULT WINAPI IDirectDrawSurface4Impl_PageUnlock(LPDIRECTDRAWSURFACE4 iface,DWORD dwFlags); -extern HRESULT WINAPI IDirectDrawSurface4Impl_SetSurfaceDesc(LPDIRECTDRAWSURFACE4 iface,LPDDSURFACEDESC lpDDSD,DWORD dwFlags); -extern HRESULT WINAPI IDirectDrawSurface4Impl_SetPrivateData(LPDIRECTDRAWSURFACE4 iface,REFGUID guidTag,LPVOID lpData,DWORD cbSize,DWORD dwFlags); -extern HRESULT WINAPI IDirectDrawSurface4Impl_GetPrivateData(LPDIRECTDRAWSURFACE4 iface,REFGUID guidTag,LPVOID lpBuffer,LPDWORD lpcbBufferSize); -extern HRESULT WINAPI IDirectDrawSurface4Impl_FreePrivateData(LPDIRECTDRAWSURFACE4 iface,REFGUID guidTag); -extern HRESULT WINAPI IDirectDrawSurface4Impl_GetUniquenessValue(LPDIRECTDRAWSURFACE4 iface,LPDWORD lpValue); -extern HRESULT WINAPI IDirectDrawSurface4Impl_ChangeUniquenessValue(LPDIRECTDRAWSURFACE4 iface); - -extern void _common_IDirectDrawImpl_SetDisplayMode(IDirectDrawImpl* This); /* Get DDSCAPS of surface (shortcutmacro) */ #define SDDSCAPS(iface) ((iface)->s.surface_desc.ddsCaps.dwCaps) /* Get the number of bytes per pixel for a given surface */ -#define PFGET_BPP(pf) (pf.dwFlags&DDPF_PALETTEINDEXED8?1:((pf.u.dwRGBBitCount+7)/8)) -#define GET_BPP(desc) PFGET_BPP(desc.ddpfPixelFormat) +#define PFGET_BPP(pf) (pf.dwFlags&DDPF_PALETTEINDEXED8?1:((pf.u1.dwRGBBitCount+7)/8)) +#define GET_BPP(desc) PFGET_BPP(desc.u4.ddpfPixelFormat) + +LONG DDRAW_width_bpp_to_pitch(DWORD width, DWORD bpp); typedef struct { unsigned short bpp,depth; @@ -387,27 +281,33 @@ typedef struct { ConvertFuncs funcs; } Convert; -extern Convert ModeEmulations[7]; +extern Convert ModeEmulations[8]; extern int _common_depth_to_pixelformat(DWORD depth,LPDIRECTDRAW ddraw); -extern HRESULT create_direct3d(LPVOID *obj,IDirectDraw2Impl*); -extern HRESULT create_direct3d2(LPVOID *obj,IDirectDraw2Impl*); -extern HRESULT create_direct3d3(LPVOID *obj,IDirectDraw2Impl*); +extern HRESULT create_direct3d(LPVOID *obj,IDirectDrawImpl*); +extern HRESULT create_direct3d2(LPVOID *obj,IDirectDrawImpl*); +extern HRESULT create_direct3d3(LPVOID *obj,IDirectDrawImpl*); +extern HRESULT create_direct3d7(LPVOID *obj,IDirectDrawImpl*); + +/****************************************************************************** + * Structure conversion (for thunks) + */ +void DDRAW_Convert_DDSCAPS_1_To_2(const DDSCAPS* pIn, DDSCAPS2* pOut); +void DDRAW_Convert_DDDEVICEIDENTIFIER_2_To_1(const DDDEVICEIDENTIFIER* pIn, + DDDEVICEIDENTIFIER2* pOut); /****************************************************************************** * Debugging / Flags output functions */ -extern void _dump_DDBLTFX(DWORD flagmask); -extern void _dump_DDBLTFAST(DWORD flagmask); -extern void _dump_DDBLT(DWORD flagmask); -extern void _dump_DDSCAPS(void *in); -extern void _dump_pixelformat_flag(DWORD flagmask); -extern void _dump_paletteformat(DWORD dwFlags); -extern void _dump_pixelformat(void *in); -extern void _dump_colorkeyflag(DWORD ck); -extern void _dump_surface_desc(DDSURFACEDESC *lpddsd); -extern void _dump_cooperativelevel(DWORD cooplevel); -extern void _dump_surface_desc(DDSURFACEDESC *lpddsd); -extern void _dump_DDCOLORKEY(void *in); -extern void _dump_DDOVERLAY(DWORD flagmask) ; +extern void DDRAW_dump_DDBLTFX(DWORD flagmask); +extern void DDRAW_dump_DDBLTFAST(DWORD flagmask); +extern void DDRAW_dump_DDBLT(DWORD flagmask); +extern void DDRAW_dump_DDSCAPS(const DDSCAPS2 *in); +extern void DDRAW_dump_pixelformat_flag(DWORD flagmask); +extern void DDRAW_dump_paletteformat(DWORD dwFlags); +extern void DDRAW_dump_pixelformat(const DDPIXELFORMAT *in); +extern void DDRAW_dump_colorkeyflag(DWORD ck); +extern void DDRAW_dump_surface_desc(const DDSURFACEDESC2 *lpddsd); +extern void DDRAW_dump_cooperativelevel(DWORD cooplevel); +extern void DDRAW_dump_DDCOLORKEY(const DDCOLORKEY *in); #endif /* __WINE_DLLS_DDRAW_DDRAW_PRIVATE_H */ diff --git a/dlls/ddraw/direct3d/mesa.c b/dlls/ddraw/direct3d/mesa.c index 709fdef1d01..d7fa735af48 100644 --- a/dlls/ddraw/direct3d/mesa.c +++ b/dlls/ddraw/direct3d/mesa.c @@ -342,7 +342,7 @@ ICOM_VTABLE(IDirect3D3) mesa_d3d3vt = #undef XCAST #endif -HRESULT create_direct3d(LPVOID *obj,IDirectDraw2Impl* ddraw) { +HRESULT create_direct3d(LPVOID *obj,IDirectDrawImpl* ddraw) { IDirect3DImpl* d3d; d3d = HeapAlloc(GetProcessHeap(),0,sizeof(*d3d)); @@ -357,7 +357,7 @@ HRESULT create_direct3d(LPVOID *obj,IDirectDraw2Impl* ddraw) { return S_OK; } -HRESULT create_direct3d2(LPVOID *obj,IDirectDraw2Impl* ddraw) { +HRESULT create_direct3d2(LPVOID *obj,IDirectDrawImpl* ddraw) { IDirect3D2Impl* d3d; d3d = HeapAlloc(GetProcessHeap(),0,sizeof(*d3d)); @@ -372,7 +372,7 @@ HRESULT create_direct3d2(LPVOID *obj,IDirectDraw2Impl* ddraw) { return S_OK; } -HRESULT create_direct3d3(LPVOID *obj,IDirectDraw2Impl* ddraw) { +HRESULT create_direct3d3(LPVOID *obj,IDirectDrawImpl* ddraw) { IDirect3D3Impl* d3d; d3d = HeapAlloc(GetProcessHeap(),0,sizeof(*d3d)); diff --git a/dlls/ddraw/dpalette/dga.c b/dlls/ddraw/dpalette/dga.c deleted file mode 100644 index 02747c8dfbd..00000000000 --- a/dlls/ddraw/dpalette/dga.c +++ /dev/null @@ -1,65 +0,0 @@ -/* DirectDrawPalette XF86DGA implementation - * - * Copyright 1997-2000 Marcus Meissner - * Copyright 1998 Lionel Ulmer (most of Direct3D stuff) - */ - -#include "config.h" -#include "winerror.h" - -#include -#include -#include -#include - -#include "debugtools.h" - -#include "dga_private.h" - -DEFAULT_DEBUG_CHANNEL(ddraw); - -#define DPPRIVATE(x) dga_dp_private *dppriv = ((dga_dp_private*)(x)->private) -#define DDPRIVATE(x) dga_dd_private *ddpriv = ((dga_dd_private*)(x)->d->private) - -HRESULT WINAPI DGA_IDirectDrawPaletteImpl_SetEntries( - LPDIRECTDRAWPALETTE iface,DWORD x,DWORD start,DWORD count,LPPALETTEENTRY palent -) { - ICOM_THIS(IDirectDrawPaletteImpl,iface); - DPPRIVATE(This); - XColor xc; - int i; - - TRACE("(%p)->SetEntries(%08lx,%ld,%ld,%p)\n",This,x,start,count,palent); - if (!dppriv->cm) /* should not happen */ { - TRACE("app tried to set colormap in non-palettized mode\n"); - } - for (i=0;icm) - TSXStoreColor(display,dppriv->cm,&xc); - - This->palents[start+i].peRed = palent[i].peRed; - This->palents[start+i].peBlue = palent[i].peBlue; - This->palents[start+i].peGreen = palent[i].peGreen; - This->palents[start+i].peFlags = palent[i].peFlags; - } - /* Flush the display queue so that palette updates are visible directly */ - TSXFlush(display); - return DD_OK; -} -ICOM_VTABLE(IDirectDrawPalette) dga_ddpalvt = -{ - ICOM_MSVTABLE_COMPAT_DummyRTTIVALUE - IDirectDrawPaletteImpl_QueryInterface, - IDirectDrawPaletteImpl_AddRef, - Xlib_IDirectDrawPaletteImpl_Release, - IDirectDrawPaletteImpl_GetCaps, - IDirectDrawPaletteImpl_GetEntries, - IDirectDrawPaletteImpl_Initialize, - DGA_IDirectDrawPaletteImpl_SetEntries -}; diff --git a/dlls/ddraw/dpalette/main.c b/dlls/ddraw/dpalette/main.c index 12b2dba9cf1..95bfca4be87 100644 --- a/dlls/ddraw/dpalette/main.c +++ b/dlls/ddraw/dpalette/main.c @@ -1,110 +1,259 @@ /* DirectDraw - IDirectPalette base interface * * Copyright 1997-2000 Marcus Meissner + * Copyright 2000 TransGaming Technologies Inc. */ #include "config.h" #include "winerror.h" - -#include -#include -#include -#include - -#include "ddraw_private.h" #include "debugtools.h" +#include +#include + +#include "ddraw_private.h" +#include "dpalette/main.h" +#include "ddraw/main.h" + DEFAULT_DEBUG_CHANNEL(ddraw); +#define SIZE_BITS (DDPCAPS_1BIT | DDPCAPS_2BIT | DDPCAPS_4BIT | DDPCAPS_8BIT) + +/* For unsigned x. 0 is not a power of 2. */ +#define IS_POW_2(x) (((x) & ((x) - 1)) == 0) + +static ICOM_VTABLE(IDirectDrawPalette) DDRAW_Main_Palette_VTable; + /****************************************************************************** * IDirectDrawPalette */ -HRESULT WINAPI IDirectDrawPaletteImpl_GetEntries( - LPDIRECTDRAWPALETTE iface,DWORD x,DWORD start,DWORD count,LPPALETTEENTRY palent -) { - ICOM_THIS(IDirectDrawPaletteImpl,iface); - int i; +HRESULT Main_DirectDrawPalette_Construct(IDirectDrawPaletteImpl* This, + IDirectDrawImpl* pDD, DWORD dwFlags) +{ + if (!IS_POW_2(dwFlags & SIZE_BITS)) return DDERR_INVALIDPARAMS; - TRACE("(%p)->GetEntries(%08lx,%ld,%ld,%p)\n",This,x,start,count,palent); + if (dwFlags & DDPCAPS_8BITENTRIES) + WARN("creating palette with 8 bit entries\n"); + + This->flags = dwFlags; + This->palNumEntries = Main_DirectDrawPalette_Size(dwFlags); + This->ref = 1; + This->final_release = Main_DirectDrawPalette_final_release; + ICOM_INIT_INTERFACE(This, IDirectDrawPalette, DDRAW_Main_Palette_VTable); + + /* we could defer hpal creation until we need it, + * but does anyone have a case where it would be useful? */ + This->hpal = CreatePalette((const LOGPALETTE*)&(This->palVersion)); + + Main_DirectDraw_AddPalette(pDD, This); - for (i=0;ipalents[start+i].peRed; - palent[i].peBlue = This->palents[start+i].peBlue; - palent[i].peGreen = This->palents[start+i].peGreen; - palent[i].peFlags = This->palents[start+i].peFlags; - } return DD_OK; } -HRESULT WINAPI IDirectDrawPaletteImpl_SetEntries( - LPDIRECTDRAWPALETTE iface,DWORD x,DWORD start,DWORD count,LPPALETTEENTRY palent -) { - ICOM_THIS(IDirectDrawPaletteImpl,iface); - int i; +HRESULT +Main_DirectDrawPalette_Create(IDirectDrawImpl* pDD, DWORD dwFlags, + LPDIRECTDRAWPALETTE* ppPalette, + LPUNKNOWN pUnkOuter) +{ + IDirectDrawPaletteImpl* This; + HRESULT hr; - TRACE("(%p)->SetEntries(%08lx,%ld,%ld,%p)\n", This,x,start,count,palent); - for (i=0;ipalents[start+i].peRed = palent[i].peRed; - This->palents[start+i].peBlue = palent[i].peBlue; - This->palents[start+i].peGreen = palent[i].peGreen; - This->palents[start+i].peFlags = palent[i].peFlags; + if (pUnkOuter != NULL) + return CLASS_E_NOAGGREGATION; /* unchecked */ + + This = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(*This)); + if (This == NULL) return E_OUTOFMEMORY; + + hr = Main_DirectDrawPalette_Construct(This, pDD, dwFlags); + if (FAILED(hr)) + HeapFree(GetProcessHeap(), 0, This); + else + *ppPalette = ICOM_INTERFACE(This, IDirectDrawPalette); + + return hr; +} + +DWORD Main_DirectDrawPalette_Size(DWORD dwFlags) +{ + switch (dwFlags & SIZE_BITS) + { + case DDPCAPS_1BIT: return 2; + case DDPCAPS_2BIT: return 4; + case DDPCAPS_4BIT: return 16; + case DDPCAPS_8BIT: return 256; + default: assert(0); return 256; + } +} + +HRESULT WINAPI +Main_DirectDrawPalette_GetEntries(LPDIRECTDRAWPALETTE iface, DWORD dwFlags, + DWORD dwStart, DWORD dwCount, + LPPALETTEENTRY palent) +{ + ICOM_THIS(IDirectDrawPaletteImpl,iface); + + TRACE("(%p)->GetEntries(%08lx,%ld,%ld,%p)\n",This,dwFlags,dwStart,dwCount, + palent); + + if (dwFlags != 0) return DDERR_INVALIDPARAMS; /* unchecked */ + if (dwStart + dwCount > Main_DirectDrawPalette_Size(This->flags)) + return DDERR_INVALIDPARAMS; + + if (This->flags & DDPCAPS_8BITENTRIES) + { + int i; + LPBYTE entry = (LPBYTE)palent; + + for (i=dwStart; i < dwCount+dwStart; i++) + *entry++ = This->palents[i].peRed; + } + else + memcpy(palent, This->palents+dwStart, dwCount * sizeof(PALETTEENTRY)); + + return DD_OK; +} + +HRESULT WINAPI +Main_DirectDrawPalette_SetEntries(LPDIRECTDRAWPALETTE iface, DWORD dwFlags, + DWORD dwStart, DWORD dwCount, + LPPALETTEENTRY palent) +{ + ICOM_THIS(IDirectDrawPaletteImpl,iface); + + TRACE("(%p)->SetEntries(%08lx,%ld,%ld,%p)\n",This,dwFlags,dwStart,dwCount, + palent); + + if (This->flags & DDPCAPS_8BITENTRIES) + { + int i; + const BYTE* entry = (const BYTE*)palent; + + for (i=dwStart; i < dwCount+dwStart; i++) + This->palents[i].peRed = *entry++; + } + else { + memcpy(This->palents+dwStart, palent, dwCount * sizeof(PALETTEENTRY)); + + if (This->hpal) + SetPaletteEntries(This->hpal, dwStart, dwCount, This->palents+dwStart); + + if (This->flags & DDPCAPS_PRIMARYSURFACE) { + /* update physical palette */ + LPDIRECTDRAWSURFACE7 psurf = NULL; + IDirectDraw7_GetGDISurface(ICOM_INTERFACE(This->ddraw_owner,IDirectDraw7), &psurf); + if (psurf) { + IDirectDrawSurfaceImpl *surf = ICOM_OBJECT(IDirectDrawSurfaceImpl, + IDirectDrawSurface7, psurf); + surf->update_palette(surf, This, dwStart, dwCount, palent); + IDirectDrawSurface7_Release(psurf); + } + else ERR("can't find GDI surface!!\n"); + } } +#if 0 /* Now, if we are in 'depth conversion mode', update the screen palette */ /* FIXME: we need to update the image or we won't get palette fading. */ if (This->ddraw->d->palette_convert != NULL) This->ddraw->d->palette_convert(palent,This->screen_palents,start,count); +#endif + return DD_OK; } -ULONG WINAPI IDirectDrawPaletteImpl_Release(LPDIRECTDRAWPALETTE iface) { +void Main_DirectDrawPalette_final_release(IDirectDrawPaletteImpl* This) +{ + Main_DirectDraw_RemovePalette(This->ddraw_owner, This); + + if (This->hpal) DeleteObject(This->hpal); +} + +static void Main_DirectDrawPalette_Destroy(IDirectDrawPaletteImpl* This) +{ + This->final_release(This); + + if (This->private != This+1) + HeapFree(GetProcessHeap(), 0, This->private); + + HeapFree(GetProcessHeap(),0,This); +} + +void Main_DirectDrawPalette_ForceDestroy(IDirectDrawPaletteImpl* This) +{ + WARN("deleting palette %p with refcnt %lu\n", This, This->ref); + Main_DirectDrawPalette_Destroy(This); +} + +ULONG WINAPI +Main_DirectDrawPalette_Release(LPDIRECTDRAWPALETTE iface) +{ ICOM_THIS(IDirectDrawPaletteImpl,iface); TRACE("(%p)->() decrementing from %lu.\n", This, This->ref ); - if (!--(This->ref)) { - HeapFree(GetProcessHeap(),0,This); - return S_OK; + + if (!--This->ref) + { + Main_DirectDrawPalette_Destroy(This); + return 0; } + return This->ref; } -ULONG WINAPI IDirectDrawPaletteImpl_AddRef(LPDIRECTDRAWPALETTE iface) { +ULONG WINAPI Main_DirectDrawPalette_AddRef(LPDIRECTDRAWPALETTE iface) { ICOM_THIS(IDirectDrawPaletteImpl,iface); TRACE("(%p)->() incrementing from %lu.\n", This, This->ref ); - return ++(This->ref); + return ++This->ref; } -HRESULT WINAPI IDirectDrawPaletteImpl_Initialize( - LPDIRECTDRAWPALETTE iface,LPDIRECTDRAW ddraw,DWORD x,LPPALETTEENTRY palent -) { +HRESULT WINAPI +Main_DirectDrawPalette_Initialize(LPDIRECTDRAWPALETTE iface, + LPDIRECTDRAW ddraw, DWORD dwFlags, + LPPALETTEENTRY palent) +{ ICOM_THIS(IDirectDrawPaletteImpl,iface); - TRACE("(%p)->(%p,%ld,%p)\n", This, ddraw, x, palent); + TRACE("(%p)->(%p,%ld,%p)\n", This, ddraw, dwFlags, palent); return DDERR_ALREADYINITIALIZED; } -HRESULT WINAPI IDirectDrawPaletteImpl_GetCaps( - LPDIRECTDRAWPALETTE iface, LPDWORD lpdwCaps ) +HRESULT WINAPI +Main_DirectDrawPalette_GetCaps(LPDIRECTDRAWPALETTE iface, LPDWORD lpdwCaps) { ICOM_THIS(IDirectDrawPaletteImpl,iface); - FIXME("(%p)->(%p) stub.\n", This, lpdwCaps ); + TRACE("(%p)->(%p)\n",This,lpdwCaps); + + *lpdwCaps = This->flags; + return DD_OK; } -HRESULT WINAPI IDirectDrawPaletteImpl_QueryInterface( - LPDIRECTDRAWPALETTE iface,REFIID refiid,LPVOID *obj ) +HRESULT WINAPI +Main_DirectDrawPalette_QueryInterface(LPDIRECTDRAWPALETTE iface, + REFIID refiid, LPVOID *obj) { ICOM_THIS(IDirectDrawPaletteImpl,iface); - FIXME("(%p)->(%s,%p) stub.\n",This,debugstr_guid(refiid),obj); - return S_OK; + TRACE("(%p)->(%s,%p)\n",This,debugstr_guid(refiid),obj); + + if (IsEqualGUID(refiid, &IID_IUnknown) + || IsEqualGUID(refiid, &IID_IDirectDrawPalette)) + { + *obj = iface; + IDirectDrawPalette_AddRef(iface); + return S_OK; + } + else + { + return E_NOINTERFACE; + } } -ICOM_VTABLE(IDirectDrawPalette) ddraw_ddpalvt = +static ICOM_VTABLE(IDirectDrawPalette) DDRAW_Main_Palette_VTable = { ICOM_MSVTABLE_COMPAT_DummyRTTIVALUE - IDirectDrawPaletteImpl_QueryInterface, - IDirectDrawPaletteImpl_AddRef, - IDirectDrawPaletteImpl_Release, - IDirectDrawPaletteImpl_GetCaps, - IDirectDrawPaletteImpl_GetEntries, - IDirectDrawPaletteImpl_Initialize, - IDirectDrawPaletteImpl_SetEntries + Main_DirectDrawPalette_QueryInterface, + Main_DirectDrawPalette_AddRef, + Main_DirectDrawPalette_Release, + Main_DirectDrawPalette_GetCaps, + Main_DirectDrawPalette_GetEntries, + Main_DirectDrawPalette_Initialize, + Main_DirectDrawPalette_SetEntries }; diff --git a/dlls/ddraw/dpalette/main.h b/dlls/ddraw/dpalette/main.h new file mode 100644 index 00000000000..7edefea26f2 --- /dev/null +++ b/dlls/ddraw/dpalette/main.h @@ -0,0 +1,44 @@ +/* Copyright 2000 TransGaming Technologies Inc. */ + +#ifndef WINE_DDRAW_DPALETTE_MAIN_H_INCLUDED +#define WINE_DDRAW_DPALETTE_MAIN_H_INCLUDED + +HRESULT Main_DirectDrawPalette_Construct(IDirectDrawPaletteImpl* This, + IDirectDrawImpl* pDD, DWORD dwFlags); +void Main_DirectDrawPalette_final_release(IDirectDrawPaletteImpl* This); + + +HRESULT +Main_DirectDrawPalette_Create(IDirectDrawImpl* pDD, DWORD dwFlags, + LPDIRECTDRAWPALETTE* ppPalette, + LPUNKNOWN pUnkOuter); +void Main_DirectDrawPalette_ForceDestroy(IDirectDrawPaletteImpl* This); + + +DWORD Main_DirectDrawPalette_Size(DWORD dwFlags); + + + +HRESULT WINAPI +Main_DirectDrawPalette_GetEntries(LPDIRECTDRAWPALETTE iface, DWORD dwFlags, + DWORD dwStart, DWORD dwCount, + LPPALETTEENTRY palent); +HRESULT WINAPI +Main_DirectDrawPalette_SetEntries(LPDIRECTDRAWPALETTE iface, DWORD dwFlags, + DWORD dwStart, DWORD dwCount, + LPPALETTEENTRY palent); +ULONG WINAPI +Main_DirectDrawPalette_Release(LPDIRECTDRAWPALETTE iface); +ULONG WINAPI Main_DirectDrawPalette_AddRef(LPDIRECTDRAWPALETTE iface); +HRESULT WINAPI +Main_DirectDrawPalette_Initialize(LPDIRECTDRAWPALETTE iface, + LPDIRECTDRAW ddraw, DWORD dwFlags, + LPPALETTEENTRY palent); +HRESULT WINAPI +Main_DirectDrawPalette_GetCaps(LPDIRECTDRAWPALETTE iface, LPDWORD lpdwCaps); +HRESULT WINAPI +Main_DirectDrawPalette_QueryInterface(LPDIRECTDRAWPALETTE iface, + REFIID refiid, LPVOID *obj); + + +#endif diff --git a/dlls/ddraw/dpalette/x11.c b/dlls/ddraw/dpalette/x11.c deleted file mode 100644 index bebe6986790..00000000000 --- a/dlls/ddraw/dpalette/x11.c +++ /dev/null @@ -1,85 +0,0 @@ -/* DirectDraw IDirectDrawPalette X11 implementation - * - * Copyright 1997-2000 Marcus Meissner - */ - -#include "config.h" -#include "winerror.h" - - -#include -#include -#include -#include - -#include "debugtools.h" - -#include "x11_private.h" - -DEFAULT_DEBUG_CHANNEL(ddraw); - -#define DPPRIVATE(x) x11_dp_private *dppriv = ((x11_dp_private*)x->private) - -/****************************************************************************** - * IDirectDrawPalette - */ - -HRESULT WINAPI Xlib_IDirectDrawPaletteImpl_SetEntries( - LPDIRECTDRAWPALETTE iface,DWORD x,DWORD start,DWORD count,LPPALETTEENTRY palent -) { - ICOM_THIS(IDirectDrawPaletteImpl,iface); - XColor xc; - int i; - DPPRIVATE(This); - - TRACE("(%p)->SetEntries(%08lx,%ld,%ld,%p)\n",This,x,start,count,palent); - for (i=0;icm) - TSXStoreColor(display,dppriv->cm,&xc); - - This->palents[start+i].peRed = palent[i].peRed; - This->palents[start+i].peBlue = palent[i].peBlue; - This->palents[start+i].peGreen = palent[i].peGreen; - This->palents[start+i].peFlags = palent[i].peFlags; - } - - /* Now, if we are in 'depth conversion mode', update the screen palette */ - /* FIXME: we need to update the image or we won't get palette fading. */ - if (This->ddraw->d->palette_convert != NULL) { - This->ddraw->d->palette_convert(palent,This->screen_palents,start,count); - } - return DD_OK; -} - -ULONG WINAPI Xlib_IDirectDrawPaletteImpl_Release(LPDIRECTDRAWPALETTE iface) { - ICOM_THIS(IDirectDrawPaletteImpl,iface); - DPPRIVATE(This); - TRACE("(%p)->() decrementing from %lu.\n", This, This->ref ); - if (!--(This->ref)) { - if (dppriv->cm) { - TSXFreeColormap(display,dppriv->cm); - dppriv->cm = 0; - } - HeapFree(GetProcessHeap(),0,This); - return S_OK; - } - return This->ref; -} - -ICOM_VTABLE(IDirectDrawPalette) xlib_ddpalvt = -{ - ICOM_MSVTABLE_COMPAT_DummyRTTIVALUE - IDirectDrawPaletteImpl_QueryInterface, - IDirectDrawPaletteImpl_AddRef, - Xlib_IDirectDrawPaletteImpl_Release, - IDirectDrawPaletteImpl_GetCaps, - IDirectDrawPaletteImpl_GetEntries, - IDirectDrawPaletteImpl_Initialize, - Xlib_IDirectDrawPaletteImpl_SetEntries -}; diff --git a/dlls/ddraw/dsurface/dga.c b/dlls/ddraw/dsurface/dga.c deleted file mode 100644 index 6a192053714..00000000000 --- a/dlls/ddraw/dsurface/dga.c +++ /dev/null @@ -1,249 +0,0 @@ -/* DirectDrawSurface XF86DGA implementation - * - * Copyright 1997-2000 Marcus Meissner - * Copyright 1998-2000 Lionel Ulmer (most of Direct3D stuff) - */ -#include "config.h" -#include "winerror.h" - -#include -#include -#include -#include -#include -#include - -#include "debugtools.h" -#include "dga_private.h" -#include "bitmap.h" - -DEFAULT_DEBUG_CHANNEL(ddraw); - -#define DDPRIVATE(x) dga_dd_private *ddpriv = ((dga_dd_private*)(x)->d->private) -#define DPPRIVATE(x) dga_dp_private *dppriv = ((dga_dp_private*)(x)->private) -#define DSPRIVATE(x) dga_ds_private *dspriv = ((dga_ds_private*)(x)->private) - -static BYTE DGA_TouchSurface(LPDIRECTDRAWSURFACE4 iface) -{ - ICOM_THIS(IDirectDrawSurface4Impl,iface); - /* if the DIB section is in GdiMod state, we must - * touch the surface to get any updates from the DIB */ - return *(BYTE*)(This->s.surface_desc.u1.lpSurface); -} - -/****************************************************************************** - * IDirectDrawSurface methods - * - * Since DDS3 and DDS2 are supersets of DDS, we implement DDS3 and let - * DDS and DDS2 use those functions. (Function calls did not change (except - * using different DirectDrawSurfaceX version), just added flags and functions) - */ - -HRESULT WINAPI DGA_IDirectDrawSurface4Impl_Flip( - LPDIRECTDRAWSURFACE4 iface,LPDIRECTDRAWSURFACE4 flipto,DWORD dwFlags -) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); - DSPRIVATE(This); - dga_ds_private *fspriv; - IDirectDrawSurface4Impl* iflipto=(IDirectDrawSurface4Impl*)flipto; - DWORD xheight; - LPBYTE surf; - - TRACE("(%p)->Flip(%p,%08lx)\n",This,iflipto,dwFlags); - - DGA_TouchSurface(iface); - iflipto = _common_find_flipto(This,iflipto); - - /* and flip! */ - fspriv = (dga_ds_private*)iflipto->private; - TSXF86DGASetViewPort(display,DefaultScreen(display),0,fspriv->fb_height); - if (iflipto->s.palette) { - DPPRIVATE(iflipto); - - if (dppriv->cm) - TSXF86DGAInstallColormap(display,DefaultScreen(display),dppriv->cm); - } - while (!TSXF86DGAViewPortChanged(display,DefaultScreen(display),2)) { - /* EMPTY */ - } - /* We need to switch the lowlevel surfaces, for DGA this is: */ - - /* The height within the framebuffer */ - xheight = dspriv->fb_height; - dspriv->fb_height = fspriv->fb_height; - fspriv->fb_height = xheight; - - /* And the assciated surface pointer */ - surf = This->s.surface_desc.u1.lpSurface; - This->s.surface_desc.u1.lpSurface = iflipto->s.surface_desc.u1.lpSurface; - iflipto->s.surface_desc.u1.lpSurface= surf; - return DD_OK; -} - -HRESULT WINAPI DGA_IDirectDrawSurface4Impl_SetPalette( - LPDIRECTDRAWSURFACE4 iface,LPDIRECTDRAWPALETTE pal -) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); - IDirectDrawPaletteImpl* ipal=(IDirectDrawPaletteImpl*)pal; - - TRACE("(%p)->(%p)\n",This,ipal); - - /* According to spec, we are only supposed to - * AddRef if this is not the same palette. - */ - if( This->s.palette != ipal ) { - dga_dp_private *fppriv; - if( ipal != NULL ) - IDirectDrawPalette_AddRef( (IDirectDrawPalette*)ipal ); - if( This->s.palette != NULL ) - IDirectDrawPalette_Release( (IDirectDrawPalette*)This->s.palette ); - This->s.palette = ipal; - fppriv = (dga_dp_private*)This->s.palette->private; - - if (!fppriv->cm && - (This->s.ddraw->d->screen_pixelformat.u.dwRGBBitCount<=8) ) { - int i; - - /* Delayed palette creation */ - fppriv->cm = TSXCreateColormap(display,DefaultRootWindow(display), - DefaultVisualOfScreen(X11DRV_GetXScreen()),AllocAll); - - for (i=0;i<256;i++) { - XColor xc; - - xc.red = ipal->palents[i].peRed<<8; - xc.blue = ipal->palents[i].peBlue<<8; - xc.green = ipal->palents[i].peGreen<<8; - xc.flags = DoRed|DoBlue|DoGreen; - xc.pixel = i; - TSXStoreColor(display,fppriv->cm,&xc); - } - } - - TSXF86DGAInstallColormap(display,DefaultScreen(display),fppriv->cm); - - if (This->s.hdc != 0) { - /* hack: set the DIBsection color map */ - BITMAPOBJ *bmp = (BITMAPOBJ *) GDI_GetObjPtr(This->s.DIBsection, BITMAP_MAGIC); - X11DRV_DIBSECTION *dib = (X11DRV_DIBSECTION *)bmp->dib; - dib->colorMap = This->s.palette ? This->s.palette->screen_palents : NULL; - GDI_ReleaseObj(This->s.DIBsection); - } - TSXFlush(display); - } - return DD_OK; -} - -ULONG WINAPI DGA_IDirectDrawSurface4Impl_Release(LPDIRECTDRAWSURFACE4 iface) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); - DDPRIVATE(This->s.ddraw); - DSPRIVATE(This); - - TRACE("(%p)->() decrementing from %lu.\n", This, This->ref ); - - if (--(This->ref)) - return This->ref; - - IDirectDraw2_Release((IDirectDraw2*)This->s.ddraw); - /* clear out of surface list */ - if (ddpriv->fb_height == -1) - VirtualFree(This->s.surface_desc.u1.lpSurface, 0, MEM_RELEASE); - else - ddpriv->vpmask &= ~(1<<(dspriv->fb_height/ddpriv->fb_height)); - - /* Free the DIBSection (if any) */ - if (This->s.hdc != 0) { - /* hack: restore the original DIBsection color map */ - BITMAPOBJ *bmp = (BITMAPOBJ *) GDI_GetObjPtr(This->s.DIBsection, BITMAP_MAGIC); - X11DRV_DIBSECTION *dib = (X11DRV_DIBSECTION *)bmp->dib; - dib->colorMap = dspriv->oldDIBmap; - GDI_ReleaseObj(This->s.DIBsection); - - SelectObject(This->s.hdc, This->s.holdbitmap); - DeleteDC(This->s.hdc); - DeleteObject(This->s.DIBsection); - } - /* Free the clipper if attached to this surface */ - if( This->s.lpClipper ) - IDirectDrawClipper_Release(This->s.lpClipper); - HeapFree(GetProcessHeap(),0,This); - return S_OK; -} - -HRESULT WINAPI DGA_IDirectDrawSurface4Impl_Unlock( - LPDIRECTDRAWSURFACE4 iface,LPVOID surface -) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); - TRACE("(%p)->Unlock(%p)\n",This,surface); - - /* in case this was called from ReleaseDC */ - DGA_TouchSurface(iface); - - return DD_OK; -} - -HRESULT WINAPI DGA_IDirectDrawSurface4Impl_GetDC(LPDIRECTDRAWSURFACE4 iface,HDC* lphdc) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); - DSPRIVATE(This); - int was_ok = This->s.hdc != 0; - HRESULT result = IDirectDrawSurface4Impl_GetDC(iface,lphdc); - if (This->s.hdc && !was_ok) { - /* hack: take over the DIBsection color map */ - BITMAPOBJ *bmp = (BITMAPOBJ *) GDI_GetObjPtr(This->s.DIBsection, BITMAP_MAGIC); - X11DRV_DIBSECTION *dib = (X11DRV_DIBSECTION *)bmp->dib; - dspriv->oldDIBmap = dib->colorMap; - dib->colorMap = This->s.palette ? This->s.palette->screen_palents : NULL; - GDI_ReleaseObj(This->s.DIBsection); - } - return result; -} - -ICOM_VTABLE(IDirectDrawSurface4) dga_dds4vt = -{ - ICOM_MSVTABLE_COMPAT_DummyRTTIVALUE - IDirectDrawSurface4Impl_QueryInterface, - IDirectDrawSurface4Impl_AddRef, - DGA_IDirectDrawSurface4Impl_Release, - IDirectDrawSurface4Impl_AddAttachedSurface, - IDirectDrawSurface4Impl_AddOverlayDirtyRect, - IDirectDrawSurface4Impl_Blt, - IDirectDrawSurface4Impl_BltBatch, - IDirectDrawSurface4Impl_BltFast, - IDirectDrawSurface4Impl_DeleteAttachedSurface, - IDirectDrawSurface4Impl_EnumAttachedSurfaces, - IDirectDrawSurface4Impl_EnumOverlayZOrders, - DGA_IDirectDrawSurface4Impl_Flip, - IDirectDrawSurface4Impl_GetAttachedSurface, - IDirectDrawSurface4Impl_GetBltStatus, - IDirectDrawSurface4Impl_GetCaps, - IDirectDrawSurface4Impl_GetClipper, - IDirectDrawSurface4Impl_GetColorKey, - DGA_IDirectDrawSurface4Impl_GetDC, - IDirectDrawSurface4Impl_GetFlipStatus, - IDirectDrawSurface4Impl_GetOverlayPosition, - IDirectDrawSurface4Impl_GetPalette, - IDirectDrawSurface4Impl_GetPixelFormat, - IDirectDrawSurface4Impl_GetSurfaceDesc, - IDirectDrawSurface4Impl_Initialize, - IDirectDrawSurface4Impl_IsLost, - IDirectDrawSurface4Impl_Lock, - IDirectDrawSurface4Impl_ReleaseDC, - IDirectDrawSurface4Impl_Restore, - IDirectDrawSurface4Impl_SetClipper, - IDirectDrawSurface4Impl_SetColorKey, - IDirectDrawSurface4Impl_SetOverlayPosition, - DGA_IDirectDrawSurface4Impl_SetPalette, - DGA_IDirectDrawSurface4Impl_Unlock, - IDirectDrawSurface4Impl_UpdateOverlay, - IDirectDrawSurface4Impl_UpdateOverlayDisplay, - IDirectDrawSurface4Impl_UpdateOverlayZOrder, - IDirectDrawSurface4Impl_GetDDInterface, - IDirectDrawSurface4Impl_PageLock, - IDirectDrawSurface4Impl_PageUnlock, - IDirectDrawSurface4Impl_SetSurfaceDesc, - IDirectDrawSurface4Impl_SetPrivateData, - IDirectDrawSurface4Impl_GetPrivateData, - IDirectDrawSurface4Impl_FreePrivateData, - IDirectDrawSurface4Impl_GetUniquenessValue, - IDirectDrawSurface4Impl_ChangeUniquenessValue -}; diff --git a/dlls/ddraw/dsurface/dga2.c b/dlls/ddraw/dsurface/dga2.c index b253fa02cb0..53bcc2d7991 100644 --- a/dlls/ddraw/dsurface/dga2.c +++ b/dlls/ddraw/dsurface/dga2.c @@ -1,176 +1,253 @@ -/* DirectDrawSurface XF86DGA implementation +/* XF86DGA2 primary surface driver * - * DGA2's specific DirectDrawSurface routines + * Copyright 2000 TransGaming Technologies Inc. */ + #include "config.h" + +#ifdef HAVE_LIBXXF86DGA2 + +#include "ts_xlib.h" +#include "ts_xf86dga2.h" +#include "x11drv.h" #include "winerror.h" -#include #include -#include -#include #include -#include #include "debugtools.h" -#include "dga2_private.h" -#include "bitmap.h" +#include "ddraw_private.h" +#include "ddraw/user.h" +#include "ddraw/dga2.h" +#include "dsurface/main.h" +#include "dsurface/dib.h" +#include "dsurface/dga2.h" DEFAULT_DEBUG_CHANNEL(ddraw); -#define DDPRIVATE(x) dga2_dd_private *ddpriv = ((dga2_dd_private*)(x)->d->private) -#define DPPRIVATE(x) dga2_dp_private *dppriv = ((dga2_dp_private*)(x)->private) -#define DSPRIVATE(x) dga2_ds_private *dspriv = ((dga2_ds_private*)(x)->private) +static ICOM_VTABLE(IDirectDrawSurface7) XF86DGA2_IDirectDrawSurface7_VTable; -static BYTE DGA2_TouchSurface(LPDIRECTDRAWSURFACE4 iface) -{ - ICOM_THIS(IDirectDrawSurface4Impl,iface); - /* if the DIB section is in GdiMod state, we must - * touch the surface to get any updates from the DIB */ - return *(BYTE*)(This->s.surface_desc.u1.lpSurface); -} +HRESULT +XF86DGA2_DirectDrawSurface_Construct(IDirectDrawSurfaceImpl* This, + IDirectDrawImpl* pDD, + const DDSURFACEDESC2* pDDSD) +{ + XF86DGA2_PRIV_VAR(priv, This); + XF86DGA2_DDRAW_PRIV_VAR(ddpriv, pDD); + HRESULT hr; + XDGADevice* mode; -HRESULT WINAPI DGA2_IDirectDrawSurface4Impl_Flip( - LPDIRECTDRAWSURFACE4 iface,LPDIRECTDRAWSURFACE4 flipto,DWORD dwFlags -) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); - IDirectDrawSurface4Impl* iflipto=(IDirectDrawSurface4Impl*)flipto; - DWORD xheight; - DSPRIVATE(This); - dga_ds_private *fspriv; - LPBYTE surf; - - TRACE("(%p)->Flip(%p,%08lx)\n",This,iflipto,dwFlags); - - DGA2_TouchSurface(iface); - iflipto = _common_find_flipto(This,iflipto); - - /* and flip! */ - fspriv = (dga_ds_private*)iflipto->private; - TSXDGASetViewport(display,DefaultScreen(display),0,fspriv->fb_height, XDGAFlipRetrace); - TSXDGASync(display,DefaultScreen(display)); - TSXFlush(display); - if (iflipto->s.palette) { - DPPRIVATE(iflipto->s.palette); - if (dppriv->cm) - TSXDGAInstallColormap(display,DefaultScreen(display),dppriv->cm); + TRACE("(%p,%p,%p)\n",This,pDD,pDDSD); + if (!ddpriv->xf86dga2.current_mode) { + /* we need a mode! */ + hr = XF86DGA2_DirectDraw_SetDisplayMode(ICOM_INTERFACE(pDD, IDirectDraw7), + pDD->width, pDD->height, + pDD->pixelformat.u1.dwRGBBitCount, + 0, 0); + if (FAILED(hr)) return hr; } - /* We need to switch the lowlevel surfaces, for DGA this is: */ - /* The height within the framebuffer */ - xheight = dspriv->fb_height; - dspriv->fb_height = fspriv->fb_height; - fspriv->fb_height = xheight; + /* grab framebuffer data from current_mode */ + mode = ddpriv->xf86dga2.current_mode; + priv->xf86dga2.fb_pitch = mode->mode.bytesPerScanline; + priv->xf86dga2.fb_vofs = ddpriv->xf86dga2.next_vofs; + priv->xf86dga2.fb_addr = mode->data + + priv->xf86dga2.fb_pitch * priv->xf86dga2.fb_vofs; + TRACE("vofs=%ld, addr=%p\n", priv->xf86dga2.fb_vofs, priv->xf86dga2.fb_addr); - /* And the assciated surface pointer */ - surf = This->s.surface_desc.u1.lpSurface; - This->s.surface_desc.u1.lpSurface = iflipto->s.surface_desc.u1.lpSurface; - iflipto->s.surface_desc.u1.lpSurface = surf; + /* fill in surface_desc before we construct DIB from it */ + This->surface_desc = *pDDSD; + This->surface_desc.lpSurface = priv->xf86dga2.fb_addr; + This->surface_desc.u1.lPitch = priv->xf86dga2.fb_pitch; + This->surface_desc.dwFlags |= DDSD_LPSURFACE | DDSD_PITCH; + + hr = DIB_DirectDrawSurface_Construct(This, pDD, &This->surface_desc); + if (FAILED(hr)) return hr; + + if (This->surface_desc.u4.ddpfPixelFormat.dwFlags & DDPF_PALETTEINDEXED8) { + priv->xf86dga2.pal = TSXDGACreateColormap(display, DefaultScreen(display), mode, AllocAll); + TSXDGAInstallColormap(display, DefaultScreen(display), priv->xf86dga2.pal); + } + + ddpriv->xf86dga2.next_vofs += pDDSD->dwHeight; + + ICOM_INIT_INTERFACE(This, IDirectDrawSurface7, + XF86DGA2_IDirectDrawSurface7_VTable); + + This->final_release = XF86DGA2_DirectDrawSurface_final_release; + This->duplicate_surface = XF86DGA2_DirectDrawSurface_duplicate_surface; + + This->flip_data = XF86DGA2_DirectDrawSurface_flip_data; + This->flip_update = XF86DGA2_DirectDrawSurface_flip_update; + + This->set_palette = XF86DGA2_DirectDrawSurface_set_palette; + This->update_palette = XF86DGA2_DirectDrawSurface_update_palette; + + This->get_display_window = XF86DGA2_DirectDrawSurface_get_display_window; return DD_OK; } -HRESULT WINAPI DGA2_IDirectDrawSurface4Impl_SetPalette( - LPDIRECTDRAWSURFACE4 iface,LPDIRECTDRAWPALETTE pal -) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); - DDPRIVATE(This->s.ddraw); - IDirectDrawPaletteImpl* ipal=(IDirectDrawPaletteImpl*)pal; +HRESULT +XF86DGA2_DirectDrawSurface_Create(IDirectDrawImpl *pDD, + const DDSURFACEDESC2 *pDDSD, + LPDIRECTDRAWSURFACE7 *ppSurf, + IUnknown *pUnkOuter) +{ + IDirectDrawSurfaceImpl* This; + HRESULT hr; + assert(pUnkOuter == NULL); - TRACE("(%p)->(%p)\n",This,ipal); + This = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, + sizeof(*This) + sizeof(XF86DGA2_DirectDrawSurfaceImpl)); + if (This == NULL) return E_OUTOFMEMORY; - /* According to spec, we are only supposed to - * AddRef if this is not the same palette. - */ - if( This->s.palette != ipal ) { - dga_dp_private *fppriv; - if( ipal != NULL ) - IDirectDrawPalette_AddRef( (IDirectDrawPalette*)ipal ); - if( This->s.palette != NULL ) - IDirectDrawPalette_Release( (IDirectDrawPalette*)This->s.palette ); - This->s.palette = ipal; - fppriv = (dga_dp_private*)This->s.palette->private; + This->private = (XF86DGA2_DirectDrawSurfaceImpl*)(This+1); - if (!fppriv->cm && - (This->s.ddraw->d->screen_pixelformat.u.dwRGBBitCount<=8) ) { - int i; - - /* Delayed palette creation */ - fppriv->cm = TSXDGACreateColormap(display,DefaultScreen(display), ddpriv->dev, AllocAll); - - for (i=0;i<256;i++) { - XColor xc; - - xc.red = ipal->palents[i].peRed<<8; - xc.blue = ipal->palents[i].peBlue<<8; - xc.green = ipal->palents[i].peGreen<<8; - xc.flags = DoRed|DoBlue|DoGreen; - xc.pixel = i; - TSXStoreColor(display,fppriv->cm,&xc); - } - } + hr = XF86DGA2_DirectDrawSurface_Construct(This, pDD, pDDSD); + if (FAILED(hr)) + HeapFree(GetProcessHeap(), 0, This); + else + *ppSurf = ICOM_INTERFACE(This, IDirectDrawSurface7); - TSXDGAInstallColormap(display,DefaultScreen(display),fppriv->cm); + return hr; +} - if (This->s.hdc != 0) { - /* hack: set the DIBsection color map */ - BITMAPOBJ *bmp = (BITMAPOBJ *) GDI_GetObjPtr(This->s.DIBsection, BITMAP_MAGIC); - X11DRV_DIBSECTION *dib = (X11DRV_DIBSECTION *)bmp->dib; - dib->colorMap = This->s.palette ? This->s.palette->screen_palents : NULL; - GDI_ReleaseObj(This->s.DIBsection); +void XF86DGA2_DirectDrawSurface_final_release(IDirectDrawSurfaceImpl* This) +{ + XF86DGA2_PRIV_VAR(priv, This); + + DIB_DirectDrawSurface_final_release(This); + if (priv->xf86dga2.pal) + TSXFreeColormap(display, priv->xf86dga2.pal); +} + +void XF86DGA2_DirectDrawSurface_set_palette(IDirectDrawSurfaceImpl* This, + IDirectDrawPaletteImpl* pal) +{ + DIB_DirectDrawSurface_set_palette(This, pal); +} + +void XF86DGA2_DirectDrawSurface_update_palette(IDirectDrawSurfaceImpl* This, + IDirectDrawPaletteImpl* pal, + DWORD dwStart, DWORD dwCount, + LPPALETTEENTRY palent) +{ + XF86DGA2_PRIV_VAR(priv, This); + + if (This->surface_desc.ddsCaps.dwCaps & DDSCAPS_PRIMARYSURFACE) + { + XColor c; + int n; + + c.flags = DoRed|DoGreen|DoBlue; + c.pixel = dwStart; + for (n=0; nxf86dga2.pal, &c); } TSXFlush(display); } - return DD_OK; } - -ICOM_VTABLE(IDirectDrawSurface4) dga2_dds4vt = +HRESULT XF86DGA2_DirectDrawSurface_duplicate_surface(IDirectDrawSurfaceImpl* This, + LPDIRECTDRAWSURFACE7* ppDup) { - ICOM_MSVTABLE_COMPAT_DummyRTTIVALUE - IDirectDrawSurface4Impl_QueryInterface, - IDirectDrawSurface4Impl_AddRef, - DGA_IDirectDrawSurface4Impl_Release, - IDirectDrawSurface4Impl_AddAttachedSurface, - IDirectDrawSurface4Impl_AddOverlayDirtyRect, - IDirectDrawSurface4Impl_Blt, - IDirectDrawSurface4Impl_BltBatch, - IDirectDrawSurface4Impl_BltFast, - IDirectDrawSurface4Impl_DeleteAttachedSurface, - IDirectDrawSurface4Impl_EnumAttachedSurfaces, - IDirectDrawSurface4Impl_EnumOverlayZOrders, - DGA2_IDirectDrawSurface4Impl_Flip, - IDirectDrawSurface4Impl_GetAttachedSurface, - IDirectDrawSurface4Impl_GetBltStatus, - IDirectDrawSurface4Impl_GetCaps, - IDirectDrawSurface4Impl_GetClipper, - IDirectDrawSurface4Impl_GetColorKey, - DGA_IDirectDrawSurface4Impl_GetDC, - IDirectDrawSurface4Impl_GetFlipStatus, - IDirectDrawSurface4Impl_GetOverlayPosition, - IDirectDrawSurface4Impl_GetPalette, - IDirectDrawSurface4Impl_GetPixelFormat, - IDirectDrawSurface4Impl_GetSurfaceDesc, - IDirectDrawSurface4Impl_Initialize, - IDirectDrawSurface4Impl_IsLost, - IDirectDrawSurface4Impl_Lock, - IDirectDrawSurface4Impl_ReleaseDC, - IDirectDrawSurface4Impl_Restore, - IDirectDrawSurface4Impl_SetClipper, - IDirectDrawSurface4Impl_SetColorKey, - IDirectDrawSurface4Impl_SetOverlayPosition, - DGA2_IDirectDrawSurface4Impl_SetPalette, - DGA_IDirectDrawSurface4Impl_Unlock, - IDirectDrawSurface4Impl_UpdateOverlay, - IDirectDrawSurface4Impl_UpdateOverlayDisplay, - IDirectDrawSurface4Impl_UpdateOverlayZOrder, - IDirectDrawSurface4Impl_GetDDInterface, - IDirectDrawSurface4Impl_PageLock, - IDirectDrawSurface4Impl_PageUnlock, - IDirectDrawSurface4Impl_SetSurfaceDesc, - IDirectDrawSurface4Impl_SetPrivateData, - IDirectDrawSurface4Impl_GetPrivateData, - IDirectDrawSurface4Impl_FreePrivateData, - IDirectDrawSurface4Impl_GetUniquenessValue, - IDirectDrawSurface4Impl_ChangeUniquenessValue + return XF86DGA2_DirectDrawSurface_Create(This->ddraw_owner, + &This->surface_desc, ppDup, NULL); +} + +void XF86DGA2_DirectDrawSurface_flip_data(IDirectDrawSurfaceImpl* front, + IDirectDrawSurfaceImpl* back) +{ + XF86DGA2_PRIV_VAR(front_priv, front); + XF86DGA2_PRIV_VAR(back_priv, back); + + { + DWORD tmp; + tmp = front_priv->xf86dga2.fb_vofs; + front_priv->xf86dga2.fb_vofs = back_priv->xf86dga2.fb_vofs; + back_priv->xf86dga2.fb_vofs = tmp; + } + { + LPVOID tmp; + tmp = front_priv->xf86dga2.fb_addr; + front_priv->xf86dga2.fb_addr = back_priv->xf86dga2.fb_addr; + back_priv->xf86dga2.fb_addr = tmp; + } + + DIB_DirectDrawSurface_flip_data(front, back); +} + +void XF86DGA2_DirectDrawSurface_flip_update(IDirectDrawSurfaceImpl* This) +{ + XF86DGA2_PRIV_VAR(priv, This); + + /* XXX having the Flip's dwFlags would be nice here */ + TSXDGASetViewport(display, DefaultScreen(display), + 0, priv->xf86dga2.fb_vofs, XDGAFlipImmediate); +} + +HWND XF86DGA2_DirectDrawSurface_get_display_window(IDirectDrawSurfaceImpl* This) +{ + /* there's a potential drawable in the ddraw object's current_mode->pixmap... + * perhaps it's possible to use it for the Direct3D rendering as well? */ + return 0; +} + +static ICOM_VTABLE(IDirectDrawSurface7) XF86DGA2_IDirectDrawSurface7_VTable = +{ + Main_DirectDrawSurface_QueryInterface, + Main_DirectDrawSurface_AddRef, + Main_DirectDrawSurface_Release, + Main_DirectDrawSurface_AddAttachedSurface, + Main_DirectDrawSurface_AddOverlayDirtyRect, + DIB_DirectDrawSurface_Blt, + Main_DirectDrawSurface_BltBatch, + DIB_DirectDrawSurface_BltFast, + Main_DirectDrawSurface_DeleteAttachedSurface, + Main_DirectDrawSurface_EnumAttachedSurfaces, + Main_DirectDrawSurface_EnumOverlayZOrders, + Main_DirectDrawSurface_Flip, + Main_DirectDrawSurface_GetAttachedSurface, + Main_DirectDrawSurface_GetBltStatus, + Main_DirectDrawSurface_GetCaps, + Main_DirectDrawSurface_GetClipper, + Main_DirectDrawSurface_GetColorKey, + Main_DirectDrawSurface_GetDC, + Main_DirectDrawSurface_GetFlipStatus, + Main_DirectDrawSurface_GetOverlayPosition, + Main_DirectDrawSurface_GetPalette, + Main_DirectDrawSurface_GetPixelFormat, + Main_DirectDrawSurface_GetSurfaceDesc, + Main_DirectDrawSurface_Initialize, + Main_DirectDrawSurface_IsLost, + Main_DirectDrawSurface_Lock, + Main_DirectDrawSurface_ReleaseDC, + DIB_DirectDrawSurface_Restore, + Main_DirectDrawSurface_SetClipper, + Main_DirectDrawSurface_SetColorKey, + Main_DirectDrawSurface_SetOverlayPosition, + Main_DirectDrawSurface_SetPalette, + Main_DirectDrawSurface_Unlock, + Main_DirectDrawSurface_UpdateOverlay, + Main_DirectDrawSurface_UpdateOverlayDisplay, + Main_DirectDrawSurface_UpdateOverlayZOrder, + Main_DirectDrawSurface_GetDDInterface, + Main_DirectDrawSurface_PageLock, + Main_DirectDrawSurface_PageUnlock, + DIB_DirectDrawSurface_SetSurfaceDesc, + Main_DirectDrawSurface_SetPrivateData, + Main_DirectDrawSurface_GetPrivateData, + Main_DirectDrawSurface_FreePrivateData, + Main_DirectDrawSurface_GetUniquenessValue, + Main_DirectDrawSurface_ChangeUniquenessValue, + Main_DirectDrawSurface_SetPriority, + Main_DirectDrawSurface_GetPriority, + Main_DirectDrawSurface_SetLOD, + Main_DirectDrawSurface_GetLOD }; + +#endif /* HAVE_LIBXXF86DGA2 */ diff --git a/dlls/ddraw/dsurface/dga2.h b/dlls/ddraw/dsurface/dga2.h new file mode 100644 index 00000000000..23f8f0d2da6 --- /dev/null +++ b/dlls/ddraw/dsurface/dga2.h @@ -0,0 +1,50 @@ +/* Copyright 2000 TransGaming Technologies Inc. */ + +#ifndef DDRAW_DSURFACE_DGA2_H_INCLUDED +#define DDRAW_DSURFACE_DGA2_H_INCLUDED + +#define XF86DGA2_PRIV(surf) ((XF86DGA2_DirectDrawSurfaceImpl*)((surf)->private)) + +#define XF86DGA2_PRIV_VAR(name,surf) \ + XF86DGA2_DirectDrawSurfaceImpl* name = XF86DGA2_PRIV(surf) + +struct XF86DGA2_DirectDrawSurfaceImpl_Part +{ + LPVOID fb_addr; + DWORD fb_pitch, fb_vofs; + Colormap pal; +}; + +typedef struct +{ + struct DIB_DirectDrawSurfaceImpl_Part dib; + struct XF86DGA2_DirectDrawSurfaceImpl_Part xf86dga2; +} XF86DGA2_DirectDrawSurfaceImpl; + +HRESULT +XF86DGA2_DirectDrawSurface_Construct(IDirectDrawSurfaceImpl* This, + IDirectDrawImpl* pDD, + const DDSURFACEDESC2* pDDSD); + +HRESULT +XF86DGA2_DirectDrawSurface_Create(IDirectDrawImpl *pDD, + const DDSURFACEDESC2 *pDDSD, + LPDIRECTDRAWSURFACE7 *ppSurf, + IUnknown *pUnkOuter); + +void XF86DGA2_DirectDrawSurface_final_release(IDirectDrawSurfaceImpl* This); + +void XF86DGA2_DirectDrawSurface_set_palette(IDirectDrawSurfaceImpl* This, + IDirectDrawPaletteImpl* pal); +void XF86DGA2_DirectDrawSurface_update_palette(IDirectDrawSurfaceImpl* This, + IDirectDrawPaletteImpl* pal, + DWORD dwStart, DWORD dwCount, + LPPALETTEENTRY palent); +HRESULT XF86DGA2_DirectDrawSurface_duplicate_surface(IDirectDrawSurfaceImpl* This, + LPDIRECTDRAWSURFACE7* ppDup); +void XF86DGA2_DirectDrawSurface_flip_data(IDirectDrawSurfaceImpl* front, + IDirectDrawSurfaceImpl* back); +void XF86DGA2_DirectDrawSurface_flip_update(IDirectDrawSurfaceImpl* This); +HWND XF86DGA2_DirectDrawSurface_get_display_window(IDirectDrawSurfaceImpl* This); + +#endif diff --git a/dlls/ddraw/dsurface/dib.c b/dlls/ddraw/dsurface/dib.c new file mode 100644 index 00000000000..285f66d1d6d --- /dev/null +++ b/dlls/ddraw/dsurface/dib.c @@ -0,0 +1,879 @@ +/* DIBSection DirectDrawSurface driver + * + * Copyright 1997-2000 Marcus Meissner + * Copyright 1998-2000 Lionel Ulmer + * Copyright 2000 TransGaming Technologies Inc. + */ + +#include "config.h" +#include "winerror.h" +#include "bitmap.h" + +#include +#include + +#include "debugtools.h" +#include "ddraw_private.h" +#include "dsurface/main.h" +#include "dsurface/dib.h" + +DEFAULT_DEBUG_CHANNEL(ddraw); + +static ICOM_VTABLE(IDirectDrawSurface7) DIB_IDirectDrawSurface7_VTable; + +static HRESULT create_dib(IDirectDrawSurfaceImpl* This) +{ + BITMAPINFO* b_info; + UINT usage; + HDC ddc; + DIB_DirectDrawSurfaceImpl* priv = This->private; + + assert(This->surface_desc.lpSurface != NULL); + + switch (This->surface_desc.u4.ddpfPixelFormat.u1.dwRGBBitCount) + { + case 16: + case 32: + /* Allocate extra space to store the RGB bit masks. */ + b_info = (BITMAPINFO*)HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, + sizeof(BITMAPINFOHEADER) + + 3 * sizeof(DWORD)); + break; + + case 24: + b_info = (BITMAPINFO*)HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, + sizeof(BITMAPINFOHEADER)); + break; + + default: + /* Allocate extra space for a palette. */ + b_info = (BITMAPINFO*)HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, + sizeof(BITMAPINFOHEADER) + + sizeof(RGBQUAD) + * (1 << This->surface_desc.u4.ddpfPixelFormat.u1.dwRGBBitCount)); + break; + } + + b_info->bmiHeader.biSize = sizeof(BITMAPINFOHEADER); + b_info->bmiHeader.biWidth = This->surface_desc.dwWidth; + b_info->bmiHeader.biHeight = -This->surface_desc.dwHeight; + b_info->bmiHeader.biPlanes = 1; + b_info->bmiHeader.biBitCount = This->surface_desc.u4.ddpfPixelFormat.u1.dwRGBBitCount; + + if ((This->surface_desc.u4.ddpfPixelFormat.u1.dwRGBBitCount != 16) + && (This->surface_desc.u4.ddpfPixelFormat.u1.dwRGBBitCount != 32)) + b_info->bmiHeader.biCompression = BI_RGB; + else + b_info->bmiHeader.biCompression = BI_BITFIELDS; + + b_info->bmiHeader.biSizeImage + = (This->surface_desc.u4.ddpfPixelFormat.u1.dwRGBBitCount / 8) + * This->surface_desc.dwWidth * This->surface_desc.dwHeight; + + b_info->bmiHeader.biXPelsPerMeter = 0; + b_info->bmiHeader.biYPelsPerMeter = 0; + b_info->bmiHeader.biClrUsed = 0; + b_info->bmiHeader.biClrImportant = 0; + + switch (This->surface_desc.u4.ddpfPixelFormat.u1.dwRGBBitCount) + { + case 16: + case 32: + { + DWORD *masks = (DWORD *) &(b_info->bmiColors); + + usage = 0; + masks[0] = This->surface_desc.u4.ddpfPixelFormat.u2.dwRBitMask; + masks[1] = This->surface_desc.u4.ddpfPixelFormat.u3.dwGBitMask; + masks[2] = This->surface_desc.u4.ddpfPixelFormat.u4.dwBBitMask; + } + break; + + case 24: + /* Nothing to do */ + usage = DIB_RGB_COLORS; + break; + + default: + /* Don't know palette */ + usage = 0; + break; + } + + ddc = CreateDCA("DISPLAY", NULL, NULL, NULL); + if (ddc == 0) + { + HeapFree(GetProcessHeap(), 0, b_info); + return HRESULT_FROM_WIN32(GetLastError()); + } + + priv->dib.DIBsection + = DIB_CreateDIBSection(ddc, b_info, usage, &(priv->dib.bitmap_data), 0, + (DWORD)This->surface_desc.lpSurface, + This->surface_desc.u1.lPitch); + DeleteDC(ddc); + if (!priv->dib.DIBsection) { + ERR("CreateDIBSection failed!\n"); + HeapFree(GetProcessHeap(), 0, b_info); + return HRESULT_FROM_WIN32(GetLastError()); + } + + TRACE("DIBSection at : %p\n", priv->dib.bitmap_data); + if (!This->surface_desc.u1.lPitch) { + /* This can't happen, right? */ + /* or use GDI_GetObj to get it from the created DIB? */ + This->surface_desc.u1.lPitch = DIB_GetDIBWidthBytes(b_info->bmiHeader.biWidth, b_info->bmiHeader.biBitCount); + This->surface_desc.dwFlags |= DDSD_PITCH; + } + + if (!This->surface_desc.lpSurface) { + This->surface_desc.lpSurface = priv->dib.bitmap_data; + This->surface_desc.dwFlags |= DDSD_LPSURFACE; + } + + HeapFree(GetProcessHeap(), 0, b_info); + + /* I don't think it's worth checking for this. */ + if (priv->dib.bitmap_data != This->surface_desc.lpSurface) + ERR("unexpected error creating DirectDrawSurface DIB section\n"); + + return S_OK; +} + +void DIB_DirectDrawSurface_final_release(IDirectDrawSurfaceImpl* This) +{ + DIB_DirectDrawSurfaceImpl* priv = This->private; + + DeleteObject(priv->dib.DIBsection); + + if (!priv->dib.client_memory) + VirtualFree(This->surface_desc.lpSurface, 0, MEM_RELEASE); + + Main_DirectDrawSurface_final_release(This); +} + +HRESULT DIB_DirectDrawSurface_duplicate_surface(IDirectDrawSurfaceImpl* This, + LPDIRECTDRAWSURFACE7* ppDup) +{ + return DIB_DirectDrawSurface_Create(This->ddraw_owner, + &This->surface_desc, ppDup, NULL); +} + +HRESULT DIB_DirectDrawSurface_Construct(IDirectDrawSurfaceImpl *This, + IDirectDrawImpl *pDD, + const DDSURFACEDESC2 *pDDSD) +{ + HRESULT hr; + DIB_DirectDrawSurfaceImpl* priv = This->private; + + TRACE("(%p)->(%p,%p)\n",This,pDD,pDDSD); + hr = Main_DirectDrawSurface_Construct(This, pDD, pDDSD); + if (FAILED(hr)) return hr; + + ICOM_INIT_INTERFACE(This, IDirectDrawSurface7, + DIB_IDirectDrawSurface7_VTable); + + This->final_release = DIB_DirectDrawSurface_final_release; + This->duplicate_surface = DIB_DirectDrawSurface_duplicate_surface; + This->flip_data = DIB_DirectDrawSurface_flip_data; + + This->get_dc = DIB_DirectDrawSurface_get_dc; + This->release_dc = DIB_DirectDrawSurface_release_dc; + This->hDC = (HDC)NULL; + + This->set_palette = DIB_DirectDrawSurface_set_palette; + This->update_palette = DIB_DirectDrawSurface_update_palette; + + TRACE("(%ldx%ld, pitch=%ld)\n", + This->surface_desc.dwWidth, This->surface_desc.dwHeight, + This->surface_desc.u1.lPitch); + /* XXX load dwWidth and dwHeight from pDD if they are not specified? */ + + if (This->surface_desc.dwFlags & DDSD_LPSURFACE) + { + /* "Client memory": it is managed by the application. */ + /* XXX What if lPitch is not set? Use dwWidth or fail? */ + + priv->dib.client_memory = TRUE; + } + else + { + if (!(This->surface_desc.dwFlags & DDSD_PITCH)) + { + int pitch = This->surface_desc.u1.lPitch; + if (pitch % 8 != 0) + pitch += 8 - (pitch % 8); + } + /* XXX else: how should lPitch be verified? */ + + This->surface_desc.dwFlags |= DDSD_PITCH|DDSD_LPSURFACE; + + This->surface_desc.lpSurface + = VirtualAlloc(NULL, This->surface_desc.u1.lPitch + * This->surface_desc.dwHeight, + MEM_RESERVE | MEM_COMMIT, PAGE_READWRITE); + + if (This->surface_desc.lpSurface == NULL) + { + Main_DirectDrawSurface_final_release(This); + return HRESULT_FROM_WIN32(GetLastError()); + } + + priv->dib.client_memory = FALSE; + } + + hr = create_dib(This); + if (FAILED(hr)) + { + if (!priv->dib.client_memory) + VirtualFree(This->surface_desc.lpSurface, 0, MEM_RELEASE); + + Main_DirectDrawSurface_final_release(This); + + return hr; + } + + return DD_OK; +} + +/* Not an API */ +HRESULT DIB_DirectDrawSurface_Create(IDirectDrawImpl *pDD, + const DDSURFACEDESC2 *pDDSD, + LPDIRECTDRAWSURFACE7 *ppSurf, + IUnknown *pUnkOuter) +{ + IDirectDrawSurfaceImpl* This; + HRESULT hr; + assert(pUnkOuter == NULL); + + This = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, + sizeof(*This) + sizeof(DIB_DirectDrawSurfaceImpl)); + if (This == NULL) return E_OUTOFMEMORY; + + This->private = (DIB_DirectDrawSurfaceImpl*)(This+1); + + hr = DIB_DirectDrawSurface_Construct(This, pDD, pDDSD); + if (FAILED(hr)) + HeapFree(GetProcessHeap(), 0, This); + else + *ppSurf = ICOM_INTERFACE(This, IDirectDrawSurface7); + + return hr; + +} + +/* AddAttachedSurface: generic */ +/* AddOverlayDirtyRect: generic, unimplemented */ + +static HRESULT _Blt_ColorFill( + LPBYTE buf, int width, int height, int bpp, LONG lPitch, DWORD color +) { + int x, y; + LPBYTE first; + + /* Do first row */ + +#define COLORFILL_ROW(type) { \ + type *d = (type *) buf; \ + for (x = 0; x < width; x++) \ + d[x] = (type) color; \ + break; \ +} + + switch(bpp) { + case 1: COLORFILL_ROW(BYTE) + case 2: COLORFILL_ROW(WORD) + case 4: COLORFILL_ROW(DWORD) + default: + FIXME("Color fill not implemented for bpp %d!\n", bpp*8); + return DDERR_UNSUPPORTED; + } + +#undef COLORFILL_ROW + + /* Now copy first row */ + first = buf; + for (y = 1; y < height; y++) { + buf += lPitch; + memcpy(buf, first, width * bpp); + } + return DD_OK; +} + +HRESULT WINAPI +DIB_DirectDrawSurface_Blt(LPDIRECTDRAWSURFACE7 iface, LPRECT rdst, + LPDIRECTDRAWSURFACE7 src, LPRECT rsrc, + DWORD dwFlags, LPDDBLTFX lpbltfx) +{ + ICOM_THIS(IDirectDrawSurfaceImpl,iface); + RECT xdst,xsrc; + DDSURFACEDESC2 ddesc,sdesc; + HRESULT ret = DD_OK; + int bpp, srcheight, srcwidth, dstheight, dstwidth, width; + int x, y; + LPBYTE dbuf, sbuf; + + TRACE("(%p)->(%p,%p,%p,%08lx,%p)\n", This,rdst,src,rsrc,dwFlags,lpbltfx); + + DD_STRUCT_INIT(&ddesc); + DD_STRUCT_INIT(&sdesc); + + sdesc.dwSize = sizeof(sdesc); + if (src) IDirectDrawSurface7_Lock(src, NULL, &sdesc, 0, 0); + ddesc.dwSize = sizeof(ddesc); + IDirectDrawSurface7_Lock(iface,NULL,&ddesc,0,0); + + if (TRACE_ON(ddraw)) { + if (rdst) TRACE("\tdestrect :%dx%d-%dx%d\n",rdst->left,rdst->top,rdst->right,rdst->bottom); + if (rsrc) TRACE("\tsrcrect :%dx%d-%dx%d\n",rsrc->left,rsrc->top,rsrc->right,rsrc->bottom); + TRACE("\tflags: "); + DDRAW_dump_DDBLT(dwFlags); + if (dwFlags & DDBLT_DDFX) { + TRACE("\tblitfx: "); + DDRAW_dump_DDBLTFX(lpbltfx->dwDDFX); + } + } + + if (rdst) { + if ((rdst->top < 0) || + (rdst->left < 0) || + (rdst->bottom < 0) || + (rdst->right < 0)) { + ERR(" Negative values in LPRECT !!!\n"); + goto release; + } + memcpy(&xdst,rdst,sizeof(xdst)); + } else { + xdst.top = 0; + xdst.bottom = ddesc.dwHeight; + xdst.left = 0; + xdst.right = ddesc.dwWidth; + } + + if (rsrc) { + if ((rsrc->top < 0) || + (rsrc->left < 0) || + (rsrc->bottom < 0) || + (rsrc->right < 0)) { + ERR(" Negative values in LPRECT !!!\n"); + goto release; + } + memcpy(&xsrc,rsrc,sizeof(xsrc)); + } else { + if (src) { + xsrc.top = 0; + xsrc.bottom = sdesc.dwHeight; + xsrc.left = 0; + xsrc.right = sdesc.dwWidth; + } else { + memset(&xsrc,0,sizeof(xsrc)); + } + } + if (src) assert((xsrc.bottom-xsrc.top) <= sdesc.dwHeight); + assert((xdst.bottom-xdst.top) <= ddesc.dwHeight); + + bpp = GET_BPP(ddesc); + srcheight = xsrc.bottom - xsrc.top; + srcwidth = xsrc.right - xsrc.left; + dstheight = xdst.bottom - xdst.top; + dstwidth = xdst.right - xdst.left; + width = (xdst.right - xdst.left) * bpp; + + assert(width <= ddesc.u1.lPitch); + + dbuf = (BYTE*)ddesc.lpSurface+(xdst.top*ddesc.u1.lPitch)+(xdst.left*bpp); + + dwFlags &= ~(DDBLT_WAIT|DDBLT_ASYNC);/* FIXME: can't handle right now */ + + /* First, all the 'source-less' blits */ + if (dwFlags & DDBLT_COLORFILL) { + ret = _Blt_ColorFill(dbuf, dstwidth, dstheight, bpp, + ddesc.u1.lPitch, lpbltfx->u5.dwFillColor); + dwFlags &= ~DDBLT_COLORFILL; + } + + if (dwFlags & DDBLT_DEPTHFILL) + FIXME("DDBLT_DEPTHFILL needs to be implemented!\n"); + if (dwFlags & DDBLT_ROP) { + /* Catch some degenerate cases here */ + switch(lpbltfx->dwROP) { + case BLACKNESS: + ret = _Blt_ColorFill(dbuf,dstwidth,dstheight,bpp,ddesc.u1.lPitch,0); + break; + case 0xAA0029: /* No-op */ + break; + case WHITENESS: + ret = _Blt_ColorFill(dbuf,dstwidth,dstheight,bpp,ddesc.u1.lPitch,~0); + break; + case SRCCOPY: /* well, we do that below ? */ + break; + default: + FIXME("Unsupported raster op: %08lx Pattern: %p\n", lpbltfx->dwROP, lpbltfx->u5.lpDDSPattern); + goto error; + } + dwFlags &= ~DDBLT_ROP; + } + if (dwFlags & DDBLT_DDROPS) { + FIXME("\tDdraw Raster Ops: %08lx Pattern: %p\n", lpbltfx->dwDDROP, lpbltfx->u5.lpDDSPattern); + } + /* Now the 'with source' blits */ + if (src) { + LPBYTE sbase; + int sx, xinc, sy, yinc; + + if (!dstwidth || !dstheight) /* hmm... stupid program ? */ + goto release; + sbase = (BYTE*)sdesc.lpSurface+(xsrc.top*sdesc.u1.lPitch)+xsrc.left*bpp; + xinc = (srcwidth << 16) / dstwidth; + yinc = (srcheight << 16) / dstheight; + + if (!dwFlags) { + /* No effects, we can cheat here */ + if (dstwidth == srcwidth) { + if (dstheight == srcheight) { + /* No stretching in either direction. This needs to be as + * fast as possible */ + sbuf = sbase; + for (y = 0; y < dstheight; y++) { + memcpy(dbuf, sbuf, width); + sbuf += sdesc.u1.lPitch; + dbuf += ddesc.u1.lPitch; + } + } else { + /* Stretching in Y direction only */ + for (y = sy = 0; y < dstheight; y++, sy += yinc) { + sbuf = sbase + (sy >> 16) * sdesc.u1.lPitch; + memcpy(dbuf, sbuf, width); + dbuf += ddesc.u1.lPitch; + } + } + } else { + /* Stretching in X direction */ + int last_sy = -1; + for (y = sy = 0; y < dstheight; y++, sy += yinc) { + sbuf = sbase + (sy >> 16) * sdesc.u1.lPitch; + + if ((sy >> 16) == (last_sy >> 16)) { + /* this sourcerow is the same as last sourcerow - + * copy already stretched row + */ + memcpy(dbuf, dbuf - ddesc.u1.lPitch, width); + } else { +#define STRETCH_ROW(type) { \ + type *s = (type *) sbuf, *d = (type *) dbuf; \ + for (x = sx = 0; x < dstwidth; x++, sx += xinc) \ + d[x] = s[sx >> 16]; \ + break; } + + switch(bpp) { + case 1: STRETCH_ROW(BYTE) + case 2: STRETCH_ROW(WORD) + case 4: STRETCH_ROW(DWORD) + case 3: { + LPBYTE s,d = dbuf; + for (x = sx = 0; x < dstwidth; x++, sx+= xinc) { + DWORD pixel; + + s = sbuf+3*(sx>>16); + pixel = (s[0]<<16)|(s[1]<<8)|s[2]; + d[0] = (pixel>>16)&0xff; + d[1] = (pixel>> 8)&0xff; + d[2] = (pixel )&0xff; + d+=3; + } + break; + } + default: + FIXME("Stretched blit not implemented for bpp %d!\n", bpp*8); + ret = DDERR_UNSUPPORTED; + goto error; + } +#undef STRETCH_ROW + } + dbuf += ddesc.u1.lPitch; + last_sy = sy; + } + } + } else if (dwFlags & (DDBLT_KEYSRC | DDBLT_KEYDEST)) { + DWORD keylow, keyhigh; + + if (dwFlags & DDBLT_KEYSRC) { + keylow = sdesc.ddckCKSrcBlt.dwColorSpaceLowValue; + keyhigh = sdesc.ddckCKSrcBlt.dwColorSpaceHighValue; + } else { + /* I'm not sure if this is correct */ + FIXME("DDBLT_KEYDEST not fully supported yet.\n"); + keylow = ddesc.ddckCKDestBlt.dwColorSpaceLowValue; + keyhigh = ddesc.ddckCKDestBlt.dwColorSpaceHighValue; + } + + + for (y = sy = 0; y < dstheight; y++, sy += yinc) { + sbuf = sbase + (sy >> 16) * sdesc.u1.lPitch; + +#define COPYROW_COLORKEY(type) { \ + type *s = (type *) sbuf, *d = (type *) dbuf, tmp; \ + for (x = sx = 0; x < dstwidth; x++, sx += xinc) { \ + tmp = s[sx >> 16]; \ + if (tmp < keylow || tmp > keyhigh) d[x] = tmp; \ + } \ + break; } + + switch (bpp) { + case 1: COPYROW_COLORKEY(BYTE) + case 2: COPYROW_COLORKEY(WORD) + case 4: COPYROW_COLORKEY(DWORD) + default: + FIXME("%s color-keyed blit not implemented for bpp %d!\n", + (dwFlags & DDBLT_KEYSRC) ? "Source" : "Destination", bpp*8); + ret = DDERR_UNSUPPORTED; + goto error; + } + dbuf += ddesc.u1.lPitch; + } +#undef COPYROW_COLORKEY + dwFlags &= ~(DDBLT_KEYSRC | DDBLT_KEYDEST); + } + } + +error: + if (dwFlags && FIXME_ON(ddraw)) { + FIXME("\tUnsupported flags: "); + DDRAW_dump_DDBLT(dwFlags); + } + +release: + IDirectDrawSurface7_Unlock(iface,NULL); + if (src) IDirectDrawSurface7_Unlock(src,NULL); + return DD_OK; +} + +/* BltBatch: generic, unimplemented */ + +HRESULT WINAPI +DIB_DirectDrawSurface_BltFast(LPDIRECTDRAWSURFACE7 iface, DWORD dstx, + DWORD dsty, LPDIRECTDRAWSURFACE7 src, + LPRECT rsrc, DWORD trans) +{ + ICOM_THIS(IDirectDrawSurfaceImpl,iface); + int bpp, w, h, x, y; + DDSURFACEDESC2 ddesc,sdesc; + HRESULT ret = DD_OK; + LPBYTE sbuf, dbuf; + RECT rsrc2; + + + if (TRACE_ON(ddraw)) { + FIXME("(%p)->(%ld,%ld,%p,%p,%08lx)\n", + This,dstx,dsty,src,rsrc,trans + ); + FIXME(" trans:"); + if (FIXME_ON(ddraw)) + DDRAW_dump_DDBLTFAST(trans); + if (rsrc) + FIXME("\tsrcrect: %dx%d-%dx%d\n",rsrc->left,rsrc->top,rsrc->right,rsrc->bottom); + else + FIXME(" srcrect: NULL\n"); + } + + /* We need to lock the surfaces, or we won't get refreshes when done. */ + sdesc.dwSize = sizeof(sdesc); + IDirectDrawSurface7_Lock(src, NULL,&sdesc,DDLOCK_READONLY, 0); + ddesc.dwSize = sizeof(ddesc); + IDirectDrawSurface7_Lock(iface,NULL,&ddesc,DDLOCK_WRITEONLY,0); + + if (!rsrc) { + WARN("rsrc is NULL!\n"); + rsrc = &rsrc2; + rsrc->left = rsrc->top = 0; + rsrc->right = sdesc.dwWidth; + rsrc->bottom = sdesc.dwHeight; + } + + bpp = GET_BPP(This->surface_desc); + sbuf = (BYTE *)sdesc.lpSurface+(rsrc->top*sdesc.u1.lPitch)+rsrc->left*bpp; + dbuf = (BYTE *)ddesc.lpSurface+(dsty*ddesc.u1.lPitch)+dstx* bpp; + + + h=rsrc->bottom-rsrc->top; + if (h>ddesc.dwHeight-dsty) h=ddesc.dwHeight-dsty; + if (h>sdesc.dwHeight-rsrc->top) h=sdesc.dwHeight-rsrc->top; + if (h<0) h=0; + + w=rsrc->right-rsrc->left; + if (w>ddesc.dwWidth-dstx) w=ddesc.dwWidth-dstx; + if (w>sdesc.dwWidth-rsrc->left) w=sdesc.dwWidth-rsrc->left; + if (w<0) w=0; + + if (trans & (DDBLTFAST_SRCCOLORKEY | DDBLTFAST_DESTCOLORKEY)) { + DWORD keylow, keyhigh; + if (trans & DDBLTFAST_SRCCOLORKEY) { + keylow = sdesc.ddckCKSrcBlt.dwColorSpaceLowValue; + keyhigh = sdesc.ddckCKSrcBlt.dwColorSpaceHighValue; + } else { + /* I'm not sure if this is correct */ + FIXME("DDBLTFAST_DESTCOLORKEY not fully supported yet.\n"); + keylow = ddesc.ddckCKDestBlt.dwColorSpaceLowValue; + keyhigh = ddesc.ddckCKDestBlt.dwColorSpaceHighValue; + } + +#define COPYBOX_COLORKEY(type) { \ + type *d = (type *)dbuf, *s = (type *)sbuf, tmp; \ + s = (type *) ((BYTE *) sdesc.lpSurface + (rsrc->top * sdesc.u1.lPitch) + rsrc->left * bpp); \ + d = (type *) ((BYTE *) ddesc.lpSurface + (dsty * ddesc.u1.lPitch) + dstx * bpp); \ + for (y = 0; y < h; y++) { \ + for (x = 0; x < w; x++) { \ + tmp = s[x]; \ + if (tmp < keylow || tmp > keyhigh) d[x] = tmp; \ + } \ + (LPBYTE)s += sdesc.u1.lPitch; \ + (LPBYTE)d += ddesc.u1.lPitch; \ + } \ + break; \ +} + + switch (bpp) { + case 1: COPYBOX_COLORKEY(BYTE) + case 2: COPYBOX_COLORKEY(WORD) + case 4: COPYBOX_COLORKEY(DWORD) + default: + FIXME("Source color key blitting not supported for bpp %d\n",bpp*8); + ret = DDERR_UNSUPPORTED; + goto error; + } +#undef COPYBOX_COLORKEY + } else { + int width = w * bpp; + + for (y = 0; y < h; y++) { + memcpy(dbuf, sbuf, width); + sbuf += sdesc.u1.lPitch; + dbuf += ddesc.u1.lPitch; + } + } +error: + IDirectDrawSurface7_Unlock(iface, NULL); + IDirectDrawSurface7_Unlock(src, NULL); + return ret; +} + +/* ChangeUniquenessValue: generic */ +/* DeleteAttachedSurface: generic */ +/* EnumAttachedSurfaces: generic */ +/* EnumOverlayZOrders: generic, unimplemented */ + +void DIB_DirectDrawSurface_flip_data(IDirectDrawSurfaceImpl* front, + IDirectDrawSurfaceImpl* back) +{ + DIB_DirectDrawSurfaceImpl* front_priv = front->private; + DIB_DirectDrawSurfaceImpl* back_priv = back->private; + + TRACE("(%p,%p)\n",front,back); + Main_DirectDrawSurface_flip_data(front, back); + + { + HBITMAP tmp; + tmp = front_priv->dib.DIBsection; + front_priv->dib.DIBsection = back_priv->dib.DIBsection; + back_priv->dib.DIBsection = tmp; + } + + { + void* tmp; + tmp = front_priv->dib.bitmap_data; + front_priv->dib.bitmap_data = back_priv->dib.bitmap_data; + back_priv->dib.bitmap_data = tmp; + + tmp = front->surface_desc.lpSurface; + front->surface_desc.lpSurface = back->surface_desc.lpSurface; + back->surface_desc.lpSurface = tmp; + } + + /* client_memory should not be different, but just in case */ + { + BOOL tmp; + tmp = front_priv->dib.client_memory; + front_priv->dib.client_memory = back_priv->dib.client_memory; + back_priv->dib.client_memory = tmp; + } +} + +/* Flip: generic */ +/* FreePrivateData: generic */ +/* GetAttachedSurface: generic */ +/* GetBltStatus: generic */ +/* GetCaps: generic (Returns the caps from This->surface_desc.) */ +/* GetClipper: generic */ +/* GetColorKey: generic */ + +HRESULT DIB_DirectDrawSurface_alloc_dc(IDirectDrawSurfaceImpl* This, HDC* phDC) +{ + DIB_PRIV_VAR(priv, This); + HDC hDC; + + TRACE("Grabbing a DC for surface: %p\n", This); + + hDC = CreateCompatibleDC(0); + priv->dib.holdbitmap = SelectObject(hDC, priv->dib.DIBsection); + if (This->palette) + SelectPalette(hDC, This->palette->hpal, FALSE); + + *phDC = hDC; + + return S_OK; +} + +HRESULT DIB_DirectDrawSurface_free_dc(IDirectDrawSurfaceImpl* This, HDC hDC) +{ + DIB_PRIV_VAR(priv, This); + + TRACE("Releasing DC for surface: %p\n", This); + + SelectObject(hDC, priv->dib.holdbitmap); + DeleteDC(hDC); + + return S_OK; +} + +HRESULT DIB_DirectDrawSurface_get_dc(IDirectDrawSurfaceImpl* This, HDC* phDC) +{ + return DIB_DirectDrawSurface_alloc_dc(This, phDC); +} + +HRESULT DIB_DirectDrawSurface_release_dc(IDirectDrawSurfaceImpl* This, HDC hDC) +{ + return DIB_DirectDrawSurface_free_dc(This, hDC); +} + +/* GetDDInterface: generic */ +/* GetFlipStatus: generic */ +/* GetLOD: generic */ +/* GetOverlayPosition: generic */ +/* GetPalette: generic */ +/* GetPixelFormat: generic */ +/* GetPriority: generic */ +/* GetPrivateData: generic */ +/* GetSurfaceDesc: generic */ +/* GetUniquenessValue: generic */ +/* Initialize: generic */ +/* IsLost: generic */ +/* Lock: generic with callback? */ +/* PageLock: generic */ +/* PageUnlock: generic */ + +HRESULT WINAPI +DIB_DirectDrawSurface_Restore(LPDIRECTDRAWSURFACE7 iface) +{ + TRACE("(%p)\n",iface); + return DD_OK; /* ??? */ +} + +/* SetClipper: generic */ +/* SetColorKey: generic */ +/* SetLOD: generic */ +/* SetOverlayPosition: generic */ + +void DIB_DirectDrawSurface_set_palette(IDirectDrawSurfaceImpl* This, + IDirectDrawPaletteImpl* pal) +{ + if (!pal) return; + if (This->surface_desc.ddsCaps.dwCaps & DDSCAPS_PRIMARYSURFACE) + This->update_palette(This, pal, + 0, pal->palNumEntries, + pal->palents); +} + +void DIB_DirectDrawSurface_update_palette(IDirectDrawSurfaceImpl* This, + IDirectDrawPaletteImpl* pal, + DWORD dwStart, DWORD dwCount, + LPPALETTEENTRY palent) +{ + RGBQUAD col[256]; + int n; + HDC dc; + + TRACE("updating primary palette\n"); + for (n=0; nget_dc(This, &dc); + SetDIBColorTable(dc, dwStart, dwCount, col); + This->release_dc(This, dc); + /* FIXME: propagate change to backbuffers */ +} + + +/* SetPalette: generic */ +/* SetPriority: generic */ +/* SetPrivateData: generic */ + +HRESULT WINAPI +DIB_DirectDrawSurface_SetSurfaceDesc(LPDIRECTDRAWSURFACE7 iface, + LPDDSURFACEDESC2 pDDSD, DWORD dwFlags) +{ + /* XXX */ + FIXME("(%p)->(%p,%08lx)\n",iface,pDDSD,dwFlags); + abort(); + return E_FAIL; +} + +/* Unlock: ???, need callback */ +/* UpdateOverlay: generic */ +/* UpdateOverlayDisplay: generic */ +/* UpdateOverlayZOrder: generic */ + +static ICOM_VTABLE(IDirectDrawSurface7) DIB_IDirectDrawSurface7_VTable = +{ + Main_DirectDrawSurface_QueryInterface, + Main_DirectDrawSurface_AddRef, + Main_DirectDrawSurface_Release, + Main_DirectDrawSurface_AddAttachedSurface, + Main_DirectDrawSurface_AddOverlayDirtyRect, + DIB_DirectDrawSurface_Blt, + Main_DirectDrawSurface_BltBatch, + DIB_DirectDrawSurface_BltFast, + Main_DirectDrawSurface_DeleteAttachedSurface, + Main_DirectDrawSurface_EnumAttachedSurfaces, + Main_DirectDrawSurface_EnumOverlayZOrders, + Main_DirectDrawSurface_Flip, + Main_DirectDrawSurface_GetAttachedSurface, + Main_DirectDrawSurface_GetBltStatus, + Main_DirectDrawSurface_GetCaps, + Main_DirectDrawSurface_GetClipper, + Main_DirectDrawSurface_GetColorKey, + Main_DirectDrawSurface_GetDC, + Main_DirectDrawSurface_GetFlipStatus, + Main_DirectDrawSurface_GetOverlayPosition, + Main_DirectDrawSurface_GetPalette, + Main_DirectDrawSurface_GetPixelFormat, + Main_DirectDrawSurface_GetSurfaceDesc, + Main_DirectDrawSurface_Initialize, + Main_DirectDrawSurface_IsLost, + Main_DirectDrawSurface_Lock, + Main_DirectDrawSurface_ReleaseDC, + DIB_DirectDrawSurface_Restore, + Main_DirectDrawSurface_SetClipper, + Main_DirectDrawSurface_SetColorKey, + Main_DirectDrawSurface_SetOverlayPosition, + Main_DirectDrawSurface_SetPalette, + Main_DirectDrawSurface_Unlock, + Main_DirectDrawSurface_UpdateOverlay, + Main_DirectDrawSurface_UpdateOverlayDisplay, + Main_DirectDrawSurface_UpdateOverlayZOrder, + Main_DirectDrawSurface_GetDDInterface, + Main_DirectDrawSurface_PageLock, + Main_DirectDrawSurface_PageUnlock, + DIB_DirectDrawSurface_SetSurfaceDesc, + Main_DirectDrawSurface_SetPrivateData, + Main_DirectDrawSurface_GetPrivateData, + Main_DirectDrawSurface_FreePrivateData, + Main_DirectDrawSurface_GetUniquenessValue, + Main_DirectDrawSurface_ChangeUniquenessValue, + Main_DirectDrawSurface_SetPriority, + Main_DirectDrawSurface_GetPriority, + Main_DirectDrawSurface_SetLOD, + Main_DirectDrawSurface_GetLOD +}; diff --git a/dlls/ddraw/dsurface/dib.h b/dlls/ddraw/dsurface/dib.h new file mode 100644 index 00000000000..bfbad79b4bd --- /dev/null +++ b/dlls/ddraw/dsurface/dib.h @@ -0,0 +1,67 @@ +/* Copyright 2000 TransGaming Technologies Inc. */ + +#ifndef DDRAW_DSURFACE_DIB_H_INCLUDED +#define DDRAW_DSURFACE_DIB_H_INCLUDED + +#define DIB_PRIV(surf) ((DIB_DirectDrawSurfaceImpl*)((surf)->private)) + +#define DIB_PRIV_VAR(name, surf) \ + DIB_DirectDrawSurfaceImpl* name = DIB_PRIV(surf) + + +struct DIB_DirectDrawSurfaceImpl_Part +{ + HBITMAP DIBsection; + void* bitmap_data; + HGDIOBJ holdbitmap; + BOOL client_memory; + DWORD d3d_data[4]; /* room for Direct3D driver data */ +}; + +typedef struct +{ + struct DIB_DirectDrawSurfaceImpl_Part dib; +} DIB_DirectDrawSurfaceImpl; + +HRESULT +DIB_DirectDrawSurface_Construct(IDirectDrawSurfaceImpl *This, + IDirectDrawImpl *pDD, + const DDSURFACEDESC2 *pDDSD); +HRESULT +DIB_DirectDrawSurface_Create(IDirectDrawImpl *pDD, + const DDSURFACEDESC2 *pDDSD, + LPDIRECTDRAWSURFACE7 *ppSurf, + IUnknown *pUnkOuter); + +void DIB_DirectDrawSurface_final_release(IDirectDrawSurfaceImpl* This); +void DIB_DirectDrawSurface_flip_data(IDirectDrawSurfaceImpl* front, + IDirectDrawSurfaceImpl* back); + +void DIB_DirectDrawSurface_set_palette(IDirectDrawSurfaceImpl* This, + IDirectDrawPaletteImpl* pal); +void DIB_DirectDrawSurface_update_palette(IDirectDrawSurfaceImpl* This, + IDirectDrawPaletteImpl* pal, + DWORD dwStart, DWORD dwCount, + LPPALETTEENTRY palent); + +HRESULT DIB_DirectDrawSurface_get_dc(IDirectDrawSurfaceImpl* This, HDC* phDC); +HRESULT DIB_DirectDrawSurface_release_dc(IDirectDrawSurfaceImpl* This,HDC hDC); + +HRESULT DIB_DirectDrawSurface_alloc_dc(IDirectDrawSurfaceImpl* This,HDC* phDC); +HRESULT DIB_DirectDrawSurface_free_dc(IDirectDrawSurfaceImpl* This, HDC hDC); + + +HRESULT WINAPI +DIB_DirectDrawSurface_Blt(LPDIRECTDRAWSURFACE7 iface, LPRECT prcDest, + LPDIRECTDRAWSURFACE7 pSrcSurf, LPRECT prcSrc, + DWORD dwFlags, LPDDBLTFX pBltFx); +HRESULT WINAPI +DIB_DirectDrawSurface_BltFast(LPDIRECTDRAWSURFACE7 iface, DWORD dwX, + DWORD dwY, LPDIRECTDRAWSURFACE7 pSrcSurf, + LPRECT prcSrc, DWORD dwTrans); +HRESULT WINAPI +DIB_DirectDrawSurface_Restore(LPDIRECTDRAWSURFACE7 iface); +HRESULT WINAPI +DIB_DirectDrawSurface_SetSurfaceDesc(LPDIRECTDRAWSURFACE7 iface, + LPDDSURFACEDESC2 pDDSD, DWORD dwFlags); +#endif diff --git a/dlls/ddraw/dsurface/dibtexture.c b/dlls/ddraw/dsurface/dibtexture.c new file mode 100644 index 00000000000..011ea5f1a9a --- /dev/null +++ b/dlls/ddraw/dsurface/dibtexture.c @@ -0,0 +1,133 @@ +/* DIB Section Texture DirectDrawSurface Driver + * + * Copyright 2000 TransGaming Technologies Inc. + */ + +#include "config.h" +#include "winerror.h" + +#include +#include + +#include "debugtools.h" +#include "ddraw_private.h" +#include "dsurface/main.h" +#include "dsurface/dib.h" +#include "dsurface/dibtexture.h" + +DEFAULT_DEBUG_CHANNEL(ddraw); + +static ICOM_VTABLE(IDirectDrawSurface7) DIBTexture_IDirectDrawSurface7_VTable; + +HRESULT +DIBTexture_DirectDrawSurface_Construct(IDirectDrawSurfaceImpl* This, + IDirectDrawImpl* pDD, + const DDSURFACEDESC2* pDDSD) +{ + HRESULT hr; + + hr = DIB_DirectDrawSurface_Construct(This, pDD, pDDSD); + if (FAILED(hr)) return hr; + + ICOM_INIT_INTERFACE(This, IDirectDrawSurface7, + DIBTexture_IDirectDrawSurface7_VTable); + + This->final_release = DIBTexture_DirectDrawSurface_final_release; + This->duplicate_surface = DIBTexture_DirectDrawSurface_duplicate_surface; + + return S_OK; +} + +HRESULT +DIBTexture_DirectDrawSurface_Create(IDirectDrawImpl *pDD, + const DDSURFACEDESC2 *pDDSD, + LPDIRECTDRAWSURFACE7 *ppSurf, + IUnknown *pUnkOuter) +{ + IDirectDrawSurfaceImpl* This; + HRESULT hr; + + assert(pUnkOuter == NULL); + assert(pDDSD->ddsCaps.dwCaps & DDSCAPS_TEXTURE); + + This = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, + sizeof(*This) + sizeof(DIBTexture_DirectDrawSurfaceImpl)); + if (This == NULL) return E_OUTOFMEMORY; + + This->private = (DIBTexture_DirectDrawSurfaceImpl*)(This+1); + + hr = DIBTexture_DirectDrawSurface_Construct(This, pDD, pDDSD); + if (FAILED(hr)) + HeapFree(GetProcessHeap(), 0, This); + else + *ppSurf = ICOM_INTERFACE(This, IDirectDrawSurface7); + + return hr; +} + +void DIBTexture_DirectDrawSurface_final_release(IDirectDrawSurfaceImpl* This) +{ + DIB_DirectDrawSurface_final_release(This); +} + +HRESULT +DIBTexture_DirectDrawSurface_duplicate_surface(IDirectDrawSurfaceImpl* This, + LPDIRECTDRAWSURFACE7* ppDup) +{ + return DIBTexture_DirectDrawSurface_Create(This->ddraw_owner, + &This->surface_desc, ppDup, + NULL); +} + +static ICOM_VTABLE(IDirectDrawSurface7) DIBTexture_IDirectDrawSurface7_VTable = +{ + Main_DirectDrawSurface_QueryInterface, + Main_DirectDrawSurface_AddRef, + Main_DirectDrawSurface_Release, + Main_DirectDrawSurface_AddAttachedSurface, + Main_DirectDrawSurface_AddOverlayDirtyRect, + DIB_DirectDrawSurface_Blt, + Main_DirectDrawSurface_BltBatch, + DIB_DirectDrawSurface_BltFast, + Main_DirectDrawSurface_DeleteAttachedSurface, + Main_DirectDrawSurface_EnumAttachedSurfaces, + Main_DirectDrawSurface_EnumOverlayZOrders, + Main_DirectDrawSurface_Flip, + Main_DirectDrawSurface_GetAttachedSurface, + Main_DirectDrawSurface_GetBltStatus, + Main_DirectDrawSurface_GetCaps, + Main_DirectDrawSurface_GetClipper, + Main_DirectDrawSurface_GetColorKey, + Main_DirectDrawSurface_GetDC, + Main_DirectDrawSurface_GetFlipStatus, + Main_DirectDrawSurface_GetOverlayPosition, + Main_DirectDrawSurface_GetPalette, + Main_DirectDrawSurface_GetPixelFormat, + Main_DirectDrawSurface_GetSurfaceDesc, + Main_DirectDrawSurface_Initialize, + Main_DirectDrawSurface_IsLost, + Main_DirectDrawSurface_Lock, + Main_DirectDrawSurface_ReleaseDC, + DIB_DirectDrawSurface_Restore, + Main_DirectDrawSurface_SetClipper, + Main_DirectDrawSurface_SetColorKey, + Main_DirectDrawSurface_SetOverlayPosition, + Main_DirectDrawSurface_SetPalette, + Main_DirectDrawSurface_Unlock, + Main_DirectDrawSurface_UpdateOverlay, + Main_DirectDrawSurface_UpdateOverlayDisplay, + Main_DirectDrawSurface_UpdateOverlayZOrder, + Main_DirectDrawSurface_GetDDInterface, + Main_DirectDrawSurface_PageLock, + Main_DirectDrawSurface_PageUnlock, + DIB_DirectDrawSurface_SetSurfaceDesc, + Main_DirectDrawSurface_SetPrivateData, + Main_DirectDrawSurface_GetPrivateData, + Main_DirectDrawSurface_FreePrivateData, + Main_DirectDrawSurface_GetUniquenessValue, + Main_DirectDrawSurface_ChangeUniquenessValue, + Main_DirectDrawSurface_SetPriority, + Main_DirectDrawSurface_GetPriority, + Main_DirectDrawSurface_SetLOD, + Main_DirectDrawSurface_GetLOD +}; diff --git a/dlls/ddraw/dsurface/dibtexture.h b/dlls/ddraw/dsurface/dibtexture.h new file mode 100644 index 00000000000..ac539c36756 --- /dev/null +++ b/dlls/ddraw/dsurface/dibtexture.h @@ -0,0 +1,48 @@ +/* Copyright 2000 TransGaming Technologies Inc. */ + +#ifndef DDRAW_DSURFACE_DIBTEXTURE_H_INCLUDED +#define DDRAW_DSURFACE_DIBTEXTURE_H_INCLUDED + +#define DIBTEXTURE_PRIV(surf) \ + ((DIBTexture_DirectDrawSurfaceImpl*)(surf->private)) + +#define DIBTEXTURE_PRIV_VAR(name,surf) \ + DIBTexture_DirectDrawSurfaceImpl* name = DIBTEXTURE_PRIV(surf) + +/* We add a spot for 3D drivers to store some private data. A cleaner + * solution would be to use SetPrivateData, but it's much too slow. */ +union DIBTexture_data +{ + int i; + void* p; +}; + +struct DIBTexture_DirectDrawSurfaceImpl_Part +{ + union DIBTexture_data data; +}; + +typedef struct +{ + struct DIB_DirectDrawSurfaceImpl_Part dib; + struct DIBTexture_DirectDrawSurfaceImpl_Part dibtexture; +} DIBTexture_DirectDrawSurfaceImpl; + +HRESULT +DIBTexture_DirectDrawSurface_Construct(IDirectDrawSurfaceImpl* This, + IDirectDrawImpl* pDD, + const DDSURFACEDESC2* pDDSD); + +HRESULT +DIBTexture_DirectDrawSurface_Create(IDirectDrawImpl *pDD, + const DDSURFACEDESC2 *pDDSD, + LPDIRECTDRAWSURFACE7 *ppSurf, + IUnknown *pUnkOuter); + +void DIBTexture_DirectDrawSurface_final_release(IDirectDrawSurfaceImpl* This); + +HRESULT +DIBTexture_DirectDrawSurface_duplicate_surface(IDirectDrawSurfaceImpl* This, + LPDIRECTDRAWSURFACE7* ppDup); + +#endif diff --git a/dlls/ddraw/dsurface/fakezbuffer.c b/dlls/ddraw/dsurface/fakezbuffer.c new file mode 100644 index 00000000000..dc2ebdeb3de --- /dev/null +++ b/dlls/ddraw/dsurface/fakezbuffer.c @@ -0,0 +1,194 @@ +/* DirectDraw/Direct3D Z-Buffer stand in + * + * Copyright 2000 TransGaming Technologies Inc. + * + * This class provides a DirectDrawSurface implementation that represents + * a Z-Buffer surface. However it does not store an image and does not + * support Lock/Unlock or GetDC. It is merely a placeholder required by the + * Direct3D architecture. + */ + +#include "config.h" + +#include +#include + +#include +#include + +#include "debugtools.h" + +#include "ddcomimpl.h" +#include "ddraw_private.h" +#include "dsurface/main.h" +#include "dsurface/fakezbuffer.h" + +DEFAULT_DEBUG_CHANNEL(ddraw); + +static ICOM_VTABLE(IDirectDrawSurface7) FakeZBuffer_IDirectDrawSurface7_VTable; + +HRESULT FakeZBuffer_DirectDrawSurface_Construct(IDirectDrawSurfaceImpl *This, + IDirectDrawImpl *pDD, + const DDSURFACEDESC2 *pDDSD) +{ + HRESULT hr; + + assert(pDDSD->ddsCaps.dwCaps & DDSCAPS_ZBUFFER); + + hr = Main_DirectDrawSurface_Construct(This, pDD, pDDSD); + if (FAILED(hr)) return hr; + + ICOM_INIT_INTERFACE(This, IDirectDrawSurface7, + FakeZBuffer_IDirectDrawSurface7_VTable); + + This->final_release = FakeZBuffer_DirectDrawSurface_final_release; + This->duplicate_surface = FakeZBuffer_DirectDrawSurface_duplicate_surface; + + return DD_OK; +} + +/* Not an API */ +HRESULT FakeZBuffer_DirectDrawSurface_Create(IDirectDrawImpl* pDD, + const DDSURFACEDESC2* pDDSD, + LPDIRECTDRAWSURFACE7* ppSurf, + IUnknown* pUnkOuter) +{ + IDirectDrawSurfaceImpl* This; + HRESULT hr; + assert(pUnkOuter == NULL); + + This = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, + sizeof(*This) + + sizeof(FakeZBuffer_DirectDrawSurfaceImpl)); + if (This == NULL) return E_OUTOFMEMORY; + + This->private = (FakeZBuffer_DirectDrawSurfaceImpl*)(This+1); + + hr = FakeZBuffer_DirectDrawSurface_Construct(This, pDD, pDDSD); + if (FAILED(hr)) + HeapFree(GetProcessHeap(), 0, This); + else + *ppSurf = ICOM_INTERFACE(This, IDirectDrawSurface7); + + return hr; +} + +void +FakeZBuffer_DirectDrawSurface_final_release(IDirectDrawSurfaceImpl* This) +{ + return Main_DirectDrawSurface_final_release(This); +} + +HRESULT +FakeZBuffer_DirectDrawSurface_duplicate_surface(IDirectDrawSurfaceImpl* This, + LPDIRECTDRAWSURFACE7* ppDup) +{ + return FakeZBuffer_DirectDrawSurface_Create(This->ddraw_owner, + &This->surface_desc, ppDup, + NULL); +} + +/* put your breakpoint/abort call here */ +static HRESULT cant_do_that(const char *s) +{ + FIXME("attempt to %s fake z-buffer\n", s); + return DDERR_UNSUPPORTED; +} + +HRESULT WINAPI +FakeZBuffer_DirectDrawSurface_Blt(LPDIRECTDRAWSURFACE7 iface, LPRECT rdst, + LPDIRECTDRAWSURFACE7 src, LPRECT rsrc, + DWORD dwFlags, LPDDBLTFX lpbltfx) +{ + return cant_do_that("blt to a"); +} + +HRESULT WINAPI +FakeZBuffer_DirectDrawSurface_BltFast(LPDIRECTDRAWSURFACE7 iface, DWORD dstx, + DWORD dsty, LPDIRECTDRAWSURFACE7 src, + LPRECT rsrc, DWORD trans) +{ + return cant_do_that("bltfast to a"); +} + +HRESULT WINAPI +FakeZBuffer_DirectDrawSurface_GetDC(LPDIRECTDRAWSURFACE7 iface, HDC *phDC) +{ + return cant_do_that("get a DC for a"); +} + +HRESULT WINAPI +FakeZBuffer_DirectDrawSurface_ReleaseDC(LPDIRECTDRAWSURFACE7 iface, HDC hDC) +{ + return cant_do_that("release a DC for a"); +} + +HRESULT WINAPI +FakeZBuffer_DirectDrawSurface_Restore(LPDIRECTDRAWSURFACE7 iface) +{ + return DD_OK; +} + +HRESULT WINAPI +FakeZBuffer_DirectDrawSurface_SetSurfaceDesc(LPDIRECTDRAWSURFACE7 iface, + LPDDSURFACEDESC2 pDDSD, + DWORD dwFlags) +{ + /* XXX */ + abort(); + return E_FAIL; +} + + +static ICOM_VTABLE(IDirectDrawSurface7) FakeZBuffer_IDirectDrawSurface7_VTable= +{ + Main_DirectDrawSurface_QueryInterface, + Main_DirectDrawSurface_AddRef, + Main_DirectDrawSurface_Release, + Main_DirectDrawSurface_AddAttachedSurface, + Main_DirectDrawSurface_AddOverlayDirtyRect, + FakeZBuffer_DirectDrawSurface_Blt, + Main_DirectDrawSurface_BltBatch, + FakeZBuffer_DirectDrawSurface_BltFast, + Main_DirectDrawSurface_DeleteAttachedSurface, + Main_DirectDrawSurface_EnumAttachedSurfaces, + Main_DirectDrawSurface_EnumOverlayZOrders, + Main_DirectDrawSurface_Flip, + Main_DirectDrawSurface_GetAttachedSurface, + Main_DirectDrawSurface_GetBltStatus, + Main_DirectDrawSurface_GetCaps, + Main_DirectDrawSurface_GetClipper, + Main_DirectDrawSurface_GetColorKey, + FakeZBuffer_DirectDrawSurface_GetDC, + Main_DirectDrawSurface_GetFlipStatus, + Main_DirectDrawSurface_GetOverlayPosition, + Main_DirectDrawSurface_GetPalette, + Main_DirectDrawSurface_GetPixelFormat, + Main_DirectDrawSurface_GetSurfaceDesc, + Main_DirectDrawSurface_Initialize, + Main_DirectDrawSurface_IsLost, + Main_DirectDrawSurface_Lock, + FakeZBuffer_DirectDrawSurface_ReleaseDC, + FakeZBuffer_DirectDrawSurface_Restore, + Main_DirectDrawSurface_SetClipper, + Main_DirectDrawSurface_SetColorKey, + Main_DirectDrawSurface_SetOverlayPosition, + Main_DirectDrawSurface_SetPalette, + Main_DirectDrawSurface_Unlock, + Main_DirectDrawSurface_UpdateOverlay, + Main_DirectDrawSurface_UpdateOverlayDisplay, + Main_DirectDrawSurface_UpdateOverlayZOrder, + Main_DirectDrawSurface_GetDDInterface, + Main_DirectDrawSurface_PageLock, + Main_DirectDrawSurface_PageUnlock, + FakeZBuffer_DirectDrawSurface_SetSurfaceDesc, + Main_DirectDrawSurface_SetPrivateData, + Main_DirectDrawSurface_GetPrivateData, + Main_DirectDrawSurface_FreePrivateData, + Main_DirectDrawSurface_GetUniquenessValue, + Main_DirectDrawSurface_ChangeUniquenessValue, + Main_DirectDrawSurface_SetPriority, + Main_DirectDrawSurface_GetPriority, + Main_DirectDrawSurface_SetLOD, + Main_DirectDrawSurface_GetLOD +}; diff --git a/dlls/ddraw/dsurface/fakezbuffer.h b/dlls/ddraw/dsurface/fakezbuffer.h new file mode 100644 index 00000000000..9d419f46d3f --- /dev/null +++ b/dlls/ddraw/dsurface/fakezbuffer.h @@ -0,0 +1,33 @@ +/* Copyright 200 TransGaming Technologies Inc. */ + +#ifndef DDRAW_DSURFACE_FAKEZBUFFER_H_INCLUDED +#define DDRAW_DSURFACE_FAKEZBUFFER_H_INCLUDED + +struct FakeZBuffer_DirectDrawSurfaceImpl_Part +{ +}; + +typedef struct +{ + struct FakeZBuffer_DirectDrawSurfaceImpl_Part fakezbuffer; +} FakeZBuffer_DirectDrawSurfaceImpl; + +HRESULT +FakeZBuffer_DirectDrawSurface_Construct(IDirectDrawSurfaceImpl* This, + IDirectDrawImpl* pDD, + const DDSURFACEDESC2* pDDSD); + +HRESULT FakeZBuffer_DirectDrawSurface_Create(IDirectDrawImpl* pDD, + const DDSURFACEDESC2* pDDSD, + LPDIRECTDRAWSURFACE7* ppSurf, + IUnknown* pUnkOuter); + +void +FakeZBuffer_DirectDrawSurface_final_release(IDirectDrawSurfaceImpl* This); + +HRESULT +FakeZBuffer_DirectDrawSurface_duplicate_surface(IDirectDrawSurfaceImpl* This, + LPDIRECTDRAWSURFACE7* ppDup); + + +#endif diff --git a/dlls/ddraw/dsurface/main.c b/dlls/ddraw/dsurface/main.c index c6243a4803a..5ecad335666 100644 --- a/dlls/ddraw/dsurface/main.c +++ b/dlls/ddraw/dsurface/main.c @@ -2,1180 +2,1075 @@ * * Copyright 1997-2000 Marcus Meissner * Copyright 1998-2000 Lionel Ulmer (most of Direct3D stuff) + * Copyright 2000 TransGaming Technologies Inc. */ #include "config.h" #include "winerror.h" - -#include #include -#include #include -#include -#include #include "debugtools.h" -#include "bitmap.h" #include "ddraw_private.h" +#include "dsurface/main.h" +#include "ddraw/main.h" +#include "dsurface/thunks.h" DEFAULT_DEBUG_CHANNEL(ddraw); -/****************************************************************************** - * IDirectDrawSurface methods - * - * Since DDS3 and DDS2 are supersets of DDS, we implement DDS3 and let - * DDS and DDS2 use those functions. (Function calls did not change (except - * using different DirectDrawSurfaceX version), just added flags and functions) - */ +/** Creation/Destruction functions */ -HRESULT WINAPI IDirectDrawSurface4Impl_Lock( - LPDIRECTDRAWSURFACE4 iface,LPRECT lprect,LPDDSURFACEDESC lpddsd,DWORD flags, HANDLE hnd -) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); +HRESULT +Main_DirectDrawSurface_Construct(IDirectDrawSurfaceImpl *This, + IDirectDrawImpl *pDD, + const DDSURFACEDESC2 *pDDSD) +{ + if (pDDSD != &This->surface_desc) + This->surface_desc = *pDDSD; + This->uniqueness_value = 1; /* unchecked */ + This->ref = 1; - TRACE("(%p)->Lock(%p,%p,%08lx,%08lx)\n", - This,lprect,lpddsd,flags,(DWORD)hnd); + This->final_release = Main_DirectDrawSurface_final_release; + This->attach = Main_DirectDrawSurface_attach; + This->detach = Main_DirectDrawSurface_detach; + This->lock_update = Main_DirectDrawSurface_lock_update; + This->unlock_update = Main_DirectDrawSurface_unlock_update; + This->lose_surface = Main_DirectDrawSurface_lose_surface; + This->set_palette = Main_DirectDrawSurface_set_palette; + This->update_palette = Main_DirectDrawSurface_update_palette; + This->get_display_window = Main_DirectDrawSurface_get_display_window; - /* DO NOT AddRef the surface! Lock/Unlock must not come in matched pairs - * -Marcus Meissner 20000509 - */ - if (flags & ~(DDLOCK_WAIT|DDLOCK_READONLY|DDLOCK_WRITEONLY)) - WARN("(%p)->Lock(%p,%p,%08lx,%08lx)\n", - This,lprect,lpddsd,flags,(DWORD)hnd); + ICOM_INIT_INTERFACE(This, IDirectDrawSurface3, + DDRAW_IDDS3_Thunk_VTable); + /* There is no generic implementation of IDDS7 */ - /* First, copy the Surface description */ - *lpddsd = This->s.surface_desc; - TRACE("locked surface: height=%ld, width=%ld, pitch=%ld\n", - lpddsd->dwHeight,lpddsd->dwWidth,lpddsd->lPitch); - - /* If asked only for a part, change the surface pointer */ - if (lprect) { - TRACE(" lprect: %dx%d-%dx%d\n", - lprect->top,lprect->left,lprect->bottom,lprect->right - ); - if ((lprect->top < 0) || - (lprect->left < 0) || - (lprect->bottom < 0) || - (lprect->right < 0)) { - ERR(" Negative values in LPRECT !!!\n"); - return DDERR_INVALIDPARAMS; - } - - lpddsd->u1.lpSurface = (LPVOID) ((char *) This->s.surface_desc.u1.lpSurface + - (lprect->top*This->s.surface_desc.lPitch) + - lprect->left*GET_BPP(This->s.surface_desc)); - } else { - assert(This->s.surface_desc.u1.lpSurface); - } + Main_DirectDraw_AddSurface(pDD, This); return DD_OK; } -HRESULT WINAPI IDirectDrawSurface4Impl_Unlock( - LPDIRECTDRAWSURFACE4 iface,LPVOID surface -) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); +void Main_DirectDrawSurface_final_release(IDirectDrawSurfaceImpl* This) +{ + Main_DirectDraw_RemoveSurface(This->ddraw_owner, This); +} + +static void Main_DirectDrawSurface_Destroy(IDirectDrawSurfaceImpl* This) +{ + This->final_release(This); + if (This->private != This+1) HeapFree(GetProcessHeap(), 0, This->private); + HeapFree(GetProcessHeap(), 0, This); +} + +void Main_DirectDrawSurface_ForceDestroy(IDirectDrawSurfaceImpl* This) +{ + WARN("destroying surface %p with refcnt %lu\n", This, This->ref); + Main_DirectDrawSurface_Destroy(This); +} + +ULONG WINAPI Main_DirectDrawSurface_Release(LPDIRECTDRAWSURFACE7 iface) +{ + ICOM_THIS(IDirectDrawSurfaceImpl, iface); + + if (--This->ref == 0) + { + if (This->aux_release) + This->aux_release(This->aux_ctx, This->aux_data); + Main_DirectDrawSurface_Destroy(This); + return 0; + } + + return This->ref; +} + +ULONG WINAPI Main_DirectDrawSurface_AddRef(LPDIRECTDRAWSURFACE7 iface) +{ + ICOM_THIS(IDirectDrawSurfaceImpl, iface); + + return ++This->ref; +} + +HRESULT WINAPI +Main_DirectDrawSurface_QueryInterface(LPDIRECTDRAWSURFACE7 iface, REFIID riid, + LPVOID* ppObj) +{ + ICOM_THIS(IDirectDrawSurfaceImpl, iface); + TRACE("(%p)->(%s,%p)\n", This, debugstr_guid(riid), ppObj); + + if (IsEqualGUID(&IID_IUnknown, riid) + || IsEqualGUID(&IID_IDirectDrawSurface7, riid) + || IsEqualGUID(&IID_IDirectDrawSurface4, riid)) + { + This->ref++; + *ppObj = ICOM_INTERFACE(This, IDirectDrawSurface7); + return S_OK; + } + else if (IsEqualGUID(&IID_IDirectDrawSurface, riid) + || IsEqualGUID(&IID_IDirectDrawSurface2, riid) + || IsEqualGUID(&IID_IDirectDrawSurface3, riid)) + { + This->ref++; + *ppObj = ICOM_INTERFACE(This, IDirectDrawSurface3); + return S_OK; + } + else + return E_NOINTERFACE; +} + +/*** Callbacks */ + +BOOL +Main_DirectDrawSurface_attach(IDirectDrawSurfaceImpl *This, + IDirectDrawSurfaceImpl *to) +{ + return TRUE; +} + +BOOL Main_DirectDrawSurface_detach(IDirectDrawSurfaceImpl *This) +{ + return TRUE; +} + +void +Main_DirectDrawSurface_lock_update(IDirectDrawSurfaceImpl* This, LPCRECT pRect) +{ +} + +void +Main_DirectDrawSurface_unlock_update(IDirectDrawSurfaceImpl* This, + LPCRECT pRect) +{ +} + +void +Main_DirectDrawSurface_lose_surface(IDirectDrawSurfaceImpl* This) +{ +} + +void +Main_DirectDrawSurface_set_palette(IDirectDrawSurfaceImpl* This, + IDirectDrawPaletteImpl* pal) +{ +} + +void +Main_DirectDrawSurface_update_palette(IDirectDrawSurfaceImpl* This, + IDirectDrawPaletteImpl* pal, + DWORD dwStart, DWORD dwCount, + LPPALETTEENTRY palent) +{ +} + +HWND +Main_DirectDrawSurface_get_display_window(IDirectDrawSurfaceImpl* This) +{ + return 0; +} + + +/*** Interface functions */ + +HRESULT WINAPI +Main_DirectDrawSurface_AddAttachedSurface(LPDIRECTDRAWSURFACE7 iface, + LPDIRECTDRAWSURFACE7 pAttach) +{ + ICOM_THIS(IDirectDrawSurfaceImpl, iface); + IDirectDrawSurfaceImpl* surf = ICOM_OBJECT(IDirectDrawSurfaceImpl, + IDirectDrawSurface7, pAttach); + + TRACE("(%p)->(%p)\n",This,pAttach); + + /* Does windows check this? */ + if (surf == This) + return DDERR_CANNOTATTACHSURFACE; /* unchecked */ + + /* Does windows check this? */ + if (surf->ddraw_owner != This->ddraw_owner) + return DDERR_CANNOTATTACHSURFACE; /* unchecked */ + + if (surf->surface_owner != NULL) + return DDERR_SURFACEALREADYATTACHED; /* unchecked */ + + /* TODO MSDN: "You can attach only z-buffer surfaces with this method." + * But apparently backbuffers and mipmaps can be attached too. */ + + /* Callback to allow the surface to do something special now that it is + * attached. (e.g. maybe the Z-buffer tells the renderer to use it.) */ + if (!surf->attach(surf, This)) + return DDERR_CANNOTATTACHSURFACE; + + /* check: Where should it go in the chain? This puts it on the head. */ + if (This->attached) + This->attached->prev_attached = surf; + surf->next_attached = This->attached; + surf->prev_attached = NULL; + This->attached = surf; + surf->surface_owner = This; + + IDirectDrawSurface7_AddRef(pAttach); - /* DO NOT Release the surface! Lock/Unlock MUST NOT come in matched pairs - * Marcus Meissner 20000509 - */ - TRACE("(%p)->Unlock(%p)\n",This,surface); return DD_OK; } -IDirectDrawSurface4Impl* _common_find_flipto( - IDirectDrawSurface4Impl* This,IDirectDrawSurface4Impl* flipto -) { - int i,j,flipable=0; - struct _surface_chain *chain = This->s.chain; +/* MSDN: "not currently implemented." */ +HRESULT WINAPI +Main_DirectDrawSurface_AddOverlayDirtyRect(LPDIRECTDRAWSURFACE7 iface, + LPRECT pRect) +{ + TRACE("(%p)->(%p)\n",iface,pRect); + return DDERR_UNSUPPORTED; /* unchecked */ +} - if (!chain) { - ERR("No flip chain? -> returning This.\n"); - return This; +/* MSDN: "not currently implemented." */ +HRESULT WINAPI +Main_DirectDrawSurface_BltBatch(LPDIRECTDRAWSURFACE7 iface, + LPDDBLTBATCH pBatch, DWORD dwCount, + DWORD dwFlags) +{ + TRACE("(%p)->(%p,%ld,%08lx)\n",iface,pBatch,dwCount,dwFlags); + return DDERR_UNSUPPORTED; /* unchecked */ +} + +HRESULT WINAPI +Main_DirectDrawSurface_ChangeUniquenessValue(LPDIRECTDRAWSURFACE7 iface) +{ + ICOM_THIS(IDirectDrawSurfaceImpl, iface); + volatile IDirectDrawSurfaceImpl* vThis = This; + + TRACE("(%p)\n",This); + /* A uniquness value of 0 is apparently special. + * This needs to be checked. */ + while (1) + { + DWORD old_uniqueness_value = vThis->uniqueness_value; + DWORD new_uniqueness_value = old_uniqueness_value+1; + + if (old_uniqueness_value == 0) break; + if (new_uniqueness_value == 0) new_uniqueness_value = 1; + + if (InterlockedCompareExchange(&vThis->uniqueness_value, + old_uniqueness_value, + new_uniqueness_value) + == old_uniqueness_value) + break; } - /* if there was no override flipto, look for current backbuffer */ - if (!flipto) { - /* walk the flip chain looking for backbuffer */ - for (i=0;inrofsurfaces;i++) { - if (SDDSCAPS(chain->surfaces[i]) & DDSCAPS_FLIP) - flipable++; - if (SDDSCAPS(chain->surfaces[i]) & DDSCAPS_BACKBUFFER) - flipto = chain->surfaces[i]; - } - /* sanity checks ... */ - if (!flipto) { - if (flipable>1) { - for (i=0;inrofsurfaces;i++) - if (SDDSCAPS(chain->surfaces[i]) & DDSCAPS_FRONTBUFFER) - break; - if (i==chain->nrofsurfaces) { - /* we do not have a frontbuffer either */ - for (i=0;inrofsurfaces;i++) - if (SDDSCAPS(chain->surfaces[i]) & DDSCAPS_FLIP) { - SDDSCAPS(chain->surfaces[i])|=DDSCAPS_FRONTBUFFER; - break; - } - for (j=i+1;jnrofsurfaces+1;j++) { - int k = j % chain->nrofsurfaces; - if (SDDSCAPS(chain->surfaces[k]) & DDSCAPS_FLIP) { - SDDSCAPS(chain->surfaces[k])|=DDSCAPS_BACKBUFFER; - flipto = chain->surfaces[k]; - break; - } - } - } + return DD_OK; +} + +HRESULT WINAPI +Main_DirectDrawSurface_DeleteAttachedSurface(LPDIRECTDRAWSURFACE7 iface, + DWORD dwFlags, + LPDIRECTDRAWSURFACE7 pAttach) +{ + ICOM_THIS(IDirectDrawSurfaceImpl, iface); + IDirectDrawSurfaceImpl* surf = ICOM_OBJECT(IDirectDrawSurfaceImpl, + IDirectDrawSurface7, pAttach); + + TRACE("(%p)->(%08lx,%p)\n",This,dwFlags,pAttach); + + if (!surf || (surf->surface_owner != This)) + return DDERR_SURFACENOTATTACHED; /* unchecked */ + + surf->detach(surf); + + if (surf->next_attached) + surf->next_attached->prev_attached = surf->prev_attached; + if (surf->prev_attached) + surf->prev_attached->next_attached = surf->next_attached; + if (This->attached == surf) + This->attached = surf->next_attached; + + IDirectDrawSurface7_Release(pAttach); + + return DD_OK; +} + +HRESULT WINAPI +Main_DirectDrawSurface_EnumAttachedSurfaces(LPDIRECTDRAWSURFACE7 iface, + LPVOID context, + LPDDENUMSURFACESCALLBACK7 cb) +{ + ICOM_THIS(IDirectDrawSurfaceImpl, iface); + IDirectDrawSurfaceImpl* surf; + + TRACE("(%p)->(%p,%p)\n",This,context,cb); + + for (surf = This->attached; surf != NULL; surf = surf->next_attached) + { + /* check: != DDENUMRET_OK or == DDENUMRET_CANCEL? */ + if (cb(ICOM_INTERFACE(surf, IDirectDrawSurface7), &surf->surface_desc, + context) == DDENUMRET_CANCEL) + break; + } + + return DD_OK; +} + +HRESULT WINAPI +Main_DirectDrawSurface_EnumOverlayZOrders(LPDIRECTDRAWSURFACE7 iface, + DWORD dwFlags, LPVOID context, + LPDDENUMSURFACESCALLBACK7 cb) +{ + TRACE("(%p)->(%08lx,%p,%p)\n",iface,dwFlags,context,cb); + return DD_OK; +} + +void Main_DirectDrawSurface_flip_data(IDirectDrawSurfaceImpl* front, + IDirectDrawSurfaceImpl* back) +{ + /* uniqueness_value? */ + /* This is necessary. But is it safe? */ + { + HDC tmp = front->hDC; + front->hDC = back->hDC; + back->hDC = tmp; + } + + { + BOOL tmp = front->dc_in_use; + front->dc_in_use = back->dc_in_use; + back->dc_in_use = tmp; + } +} + +HRESULT WINAPI +Main_DirectDrawSurface_Flip(LPDIRECTDRAWSURFACE7 iface, + LPDIRECTDRAWSURFACE7 override, DWORD dwFlags) +{ + ICOM_THIS(IDirectDrawSurfaceImpl, iface); + IDirectDrawSurfaceImpl* target; + HRESULT hr; + + TRACE("(%p)->(%p,%08lx)\n",This,override,dwFlags); + + /* MSDN: "This method can be called only for a surface that has the + * DDSCAPS_FLIP and DDSCAPS_FRONTBUFFER capabilities." */ + if ((This->surface_desc.ddsCaps.dwCaps&(DDSCAPS_FLIP|DDSCAPS_FRONTBUFFER)) + != (DDSCAPS_FLIP|DDSCAPS_FRONTBUFFER)) + return DDERR_NOTFLIPPABLE; + + if (This->aux_flip) + if (This->aux_flip(This->aux_ctx, This->aux_data)) + return DD_OK; + + /* 1. find the flip target */ + /* XXX I don't think this algorithm works for more than 1 backbuffer. */ + if (override == NULL) + { + static const DDSCAPS2 back_caps = { DDSCAPS_BACKBUFFER }; + LPDIRECTDRAWSURFACE7 tgt; + + hr = IDirectDrawSurface7_GetAttachedSurface(iface, &back_caps, &tgt); + if (FAILED(hr)) return DDERR_NOTFLIPPABLE; /* unchecked */ + + target = ICOM_OBJECT(IDirectDrawSurfaceImpl, IDirectDrawSurface7, + tgt); + IDirectDrawSurface7_Release(tgt); + } + else + { + BOOL on_chain = FALSE; + IDirectDrawSurfaceImpl* surf; + + /* MSDN: "The method fails if the specified [override] surface is not + * a member of the flipping chain." */ + + /* Verify that override is on this flip chain. We assume that + * surf is the head of the flipping chain, because it's the front + * buffer. */ + target = ICOM_OBJECT(IDirectDrawSurfaceImpl, IDirectDrawSurface7, + override); + + /* Either target is (indirectly) attached to This or This is + * (indirectly) attached to target. */ + for (surf = target; surf != NULL; surf = surf->surface_owner) + { + if (surf == This) + { + on_chain = TRUE; + break; } - if (!flipto) - flipto = This; - } - TRACE("flipping to %p\n",flipto); - } - return flipto; -} - -static HRESULT _Blt_ColorFill( - LPBYTE buf, int width, int height, int bpp, LONG lPitch, DWORD color -) { - int x, y; - LPBYTE first; - - /* Do first row */ - -#define COLORFILL_ROW(type) { \ - type *d = (type *) buf; \ - for (x = 0; x < width; x++) \ - d[x] = (type) color; \ - break; \ -} - - switch(bpp) { - case 1: COLORFILL_ROW(BYTE) - case 2: COLORFILL_ROW(WORD) - case 4: COLORFILL_ROW(DWORD) - default: - FIXME("Color fill not implemented for bpp %d!\n", bpp*8); - return DDERR_UNSUPPORTED; - } - -#undef COLORFILL_ROW - - /* Now copy first row */ - first = buf; - for (y = 1; y < height; y++) { - buf += lPitch; - memcpy(buf, first, width * bpp); - } - return DD_OK; -} - -HRESULT WINAPI IDirectDrawSurface4Impl_Blt( - LPDIRECTDRAWSURFACE4 iface,LPRECT rdst,LPDIRECTDRAWSURFACE4 src,LPRECT rsrc, - DWORD dwFlags,LPDDBLTFX lpbltfx -) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); - RECT xdst,xsrc; - DDSURFACEDESC ddesc,sdesc; - HRESULT ret = DD_OK; - int bpp, srcheight, srcwidth, dstheight, dstwidth, width; - int x, y; - LPBYTE dbuf, sbuf; - - TRACE("(%p)->(%p,%p,%p,%08lx,%p)\n", This,rdst,src,rsrc,dwFlags,lpbltfx); - - if (src) IDirectDrawSurface4_Lock(src, NULL, &sdesc, 0, 0); - IDirectDrawSurface4_Lock(iface,NULL,&ddesc,0,0); - - if (TRACE_ON(ddraw)) { - if (rdst) TRACE("\tdestrect :%dx%d-%dx%d\n",rdst->left,rdst->top,rdst->right,rdst->bottom); - if (rsrc) TRACE("\tsrcrect :%dx%d-%dx%d\n",rsrc->left,rsrc->top,rsrc->right,rsrc->bottom); - TRACE("\tflags: "); - _dump_DDBLT(dwFlags); - if (dwFlags & DDBLT_DDFX) { - TRACE("\tblitfx: "); - _dump_DDBLTFX(lpbltfx->dwDDFX); - } - } - - if (rdst) { - if ((rdst->top < 0) || - (rdst->left < 0) || - (rdst->bottom < 0) || - (rdst->right < 0)) { - ERR(" Negative values in LPRECT !!!\n"); - goto release; - } - memcpy(&xdst,rdst,sizeof(xdst)); - } else { - xdst.top = 0; - xdst.bottom = ddesc.dwHeight; - xdst.left = 0; - xdst.right = ddesc.dwWidth; - } - - if (rsrc) { - if ((rsrc->top < 0) || - (rsrc->left < 0) || - (rsrc->bottom < 0) || - (rsrc->right < 0)) { - ERR(" Negative values in LPRECT !!!\n"); - goto release; - } - memcpy(&xsrc,rsrc,sizeof(xsrc)); - } else { - if (src) { - xsrc.top = 0; - xsrc.bottom = sdesc.dwHeight; - xsrc.left = 0; - xsrc.right = sdesc.dwWidth; - } else { - memset(&xsrc,0,sizeof(xsrc)); - } - } - if (src) assert((xsrc.bottom-xsrc.top) <= sdesc.dwHeight); - - /* truncate dst rect to dest surface. */ - if ((xdst.bottom-xdst.top) > ddesc.dwHeight) - xdst.bottom = xdst.top+ddesc.dwHeight; - if ((xdst.right-xdst.left) > ddesc.dwWidth) - xdst.right = xdst.left+ddesc.dwWidth; - - bpp = GET_BPP(ddesc); - srcheight = xsrc.bottom - xsrc.top; - srcwidth = xsrc.right - xsrc.left; - dstheight = xdst.bottom - xdst.top; - dstwidth = xdst.right - xdst.left; - width = (xdst.right - xdst.left) * bpp; - - assert(width <= ddesc.lPitch); - - dbuf = (BYTE*)ddesc.u1.lpSurface+(xdst.top*ddesc.lPitch)+(xdst.left*bpp); - - dwFlags &= ~(DDBLT_WAIT|DDBLT_ASYNC);/* FIXME: can't handle right now */ - - /* First, all the 'source-less' blits */ - if (dwFlags & DDBLT_COLORFILL) { - ret = _Blt_ColorFill(dbuf, dstwidth, dstheight, bpp, - ddesc.lPitch, lpbltfx->u4.dwFillColor); - dwFlags &= ~DDBLT_COLORFILL; - } - - if (dwFlags & DDBLT_DEPTHFILL) - FIXME("DDBLT_DEPTHFILL needs to be implemented!\n"); - if (dwFlags & DDBLT_ROP) { - /* Catch some degenerate cases here */ - switch(lpbltfx->dwROP) { - case BLACKNESS: - ret = _Blt_ColorFill(dbuf,dstwidth,dstheight,bpp,ddesc.lPitch,0); - break; - case 0xAA0029: /* No-op */ - break; - case WHITENESS: - ret = _Blt_ColorFill(dbuf,dstwidth,dstheight,bpp,ddesc.lPitch,~0); - break; - case SRCCOPY: /* well, we do that below ? */ - break; - default: - FIXME("Unsupported raster op: %08lx Pattern: %p\n", lpbltfx->dwROP, lpbltfx->u4.lpDDSPattern); - goto error; - } - dwFlags &= ~DDBLT_ROP; - } - if (dwFlags & DDBLT_DDROPS) { - FIXME("\tDdraw Raster Ops: %08lx Pattern: %p\n", lpbltfx->dwDDROP, lpbltfx->u4.lpDDSPattern); - } - /* Now the 'with source' blits */ - if (src) { - LPBYTE sbase; - int sx, xinc, sy, yinc; - - if (!dstwidth || !dstheight) /* hmm... stupid program ? */ - goto release; - sbase = (BYTE*)sdesc.u1.lpSurface+(xsrc.top*sdesc.lPitch)+xsrc.left*bpp; - xinc = (srcwidth << 16) / dstwidth; - yinc = (srcheight << 16) / dstheight; - - if (!dwFlags) { - /* No effects, we can cheat here */ - if (dstwidth == srcwidth) { - if (dstheight == srcheight) { - /* No stretching in either direction. This needs to be as - * fast as possible */ - sbuf = sbase; - for (y = 0; y < dstheight; y++) { - memcpy(dbuf, sbuf, width); - sbuf += sdesc.lPitch; - dbuf += ddesc.lPitch; - } - } else { - /* Stretching in Y direction only */ - for (y = sy = 0; y < dstheight; y++, sy += yinc) { - sbuf = sbase + (sy >> 16) * sdesc.lPitch; - memcpy(dbuf, sbuf, width); - dbuf += ddesc.lPitch; - } - } - } else { - /* Stretching in X direction */ - int last_sy = -1; - for (y = sy = 0; y < dstheight; y++, sy += yinc) { - sbuf = sbase + (sy >> 16) * sdesc.lPitch; - - if ((sy >> 16) == (last_sy >> 16)) { - /* this sourcerow is the same as last sourcerow - - * copy already stretched row - */ - memcpy(dbuf, dbuf - ddesc.lPitch, width); - } else { -#define STRETCH_ROW(type) { \ - type *s = (type *) sbuf, *d = (type *) dbuf; \ - for (x = sx = 0; x < dstwidth; x++, sx += xinc) \ - d[x] = s[sx >> 16]; \ - break; } - - switch(bpp) { - case 1: STRETCH_ROW(BYTE) - case 2: STRETCH_ROW(WORD) - case 4: STRETCH_ROW(DWORD) - case 3: { - LPBYTE s,d = dbuf; - for (x = sx = 0; x < dstwidth; x++, sx+= xinc) { - DWORD pixel; - - s = sbuf+3*(sx>>16); - pixel = (s[0]<<16)|(s[1]<<8)|s[2]; - d[0] = (pixel>>16)&0xff; - d[1] = (pixel>> 8)&0xff; - d[2] = (pixel )&0xff; - d+=3; - } - break; - } - default: - FIXME("Stretched blit not implemented for bpp %d!\n", bpp*8); - ret = DDERR_UNSUPPORTED; - goto error; - } -#undef STRETCH_ROW - } - dbuf += ddesc.lPitch; - last_sy = sy; - } - } - } else if (dwFlags & (DDBLT_KEYSRC | DDBLT_KEYDEST)) { - DWORD keylow, keyhigh; - - if (dwFlags & DDBLT_KEYSRC) { - keylow = sdesc.ddckCKSrcBlt.dwColorSpaceLowValue; - keyhigh = sdesc.ddckCKSrcBlt.dwColorSpaceHighValue; - } else { - /* I'm not sure if this is correct */ - FIXME("DDBLT_KEYDEST not fully supported yet.\n"); - keylow = ddesc.ddckCKDestBlt.dwColorSpaceLowValue; - keyhigh = ddesc.ddckCKDestBlt.dwColorSpaceHighValue; - } - - - for (y = sy = 0; y < dstheight; y++, sy += yinc) { - sbuf = sbase + (sy >> 16) * sdesc.lPitch; - -#define COPYROW_COLORKEY(type) { \ - type *s = (type *) sbuf, *d = (type *) dbuf, tmp; \ - for (x = sx = 0; x < dstwidth; x++, sx += xinc) { \ - tmp = s[sx >> 16]; \ - if (tmp < keylow || tmp > keyhigh) d[x] = tmp; \ - } \ - break; } - - switch (bpp) { - case 1: COPYROW_COLORKEY(BYTE) - case 2: COPYROW_COLORKEY(WORD) - case 4: COPYROW_COLORKEY(DWORD) - default: - FIXME("%s color-keyed blit not implemented for bpp %d!\n", - (dwFlags & DDBLT_KEYSRC) ? "Source" : "Destination", bpp*8); - ret = DDERR_UNSUPPORTED; - goto error; - } - dbuf += ddesc.lPitch; - } -#undef COPYROW_COLORKEY - dwFlags &= ~(DDBLT_KEYSRC | DDBLT_KEYDEST); - } - } - -error: - if (dwFlags && FIXME_ON(ddraw)) { - FIXME("\tUnsupported flags: "); - _dump_DDBLT(dwFlags); - } - -release: - IDirectDrawSurface4_Unlock(iface,ddesc.u1.lpSurface); - if (src) IDirectDrawSurface4_Unlock(src,sdesc.u1.lpSurface); - return DD_OK; -} - -HRESULT WINAPI IDirectDrawSurface4Impl_BltFast( - LPDIRECTDRAWSURFACE4 iface,DWORD dstx,DWORD dsty,LPDIRECTDRAWSURFACE4 src, - LPRECT rsrc,DWORD trans -) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); - int bpp, w, h, x, y; - DDSURFACEDESC ddesc,sdesc; - HRESULT ret = DD_OK; - LPBYTE sbuf, dbuf; - RECT rsrc2; - - - if (TRACE_ON(ddraw)) { - FIXME("(%p)->(%ld,%ld,%p,%p,%08lx)\n", - This,dstx,dsty,src,rsrc,trans - ); - FIXME(" trans:"); - if (FIXME_ON(ddraw)) - _dump_DDBLTFAST(trans); - if (rsrc) - FIXME("\tsrcrect: %dx%d-%dx%d\n",rsrc->left,rsrc->top,rsrc->right,rsrc->bottom); - else - FIXME(" srcrect: NULL\n"); - } - - /* We need to lock the surfaces, or we won't get refreshes when done. */ - IDirectDrawSurface4_Lock(src, NULL,&sdesc,DDLOCK_READONLY, 0); - IDirectDrawSurface4_Lock(iface,NULL,&ddesc,DDLOCK_WRITEONLY,0); - - if (!rsrc) { - WARN("rsrc is NULL!\n"); - rsrc = &rsrc2; - rsrc->left = rsrc->top = 0; - rsrc->right = sdesc.dwWidth; - rsrc->bottom = sdesc.dwHeight; - } - - bpp = GET_BPP(This->s.surface_desc); - sbuf = (BYTE *)sdesc.u1.lpSurface+(rsrc->top*sdesc.lPitch)+rsrc->left*bpp; - dbuf = (BYTE *)ddesc.u1.lpSurface+(dsty*ddesc.lPitch)+dstx* bpp; - - - h=rsrc->bottom-rsrc->top; - if (h>ddesc.dwHeight-dsty) h=ddesc.dwHeight-dsty; - if (h>sdesc.dwHeight-rsrc->top) h=sdesc.dwHeight-rsrc->top; - if (h<0) h=0; - - w=rsrc->right-rsrc->left; - if (w>ddesc.dwWidth-dstx) w=ddesc.dwWidth-dstx; - if (w>sdesc.dwWidth-rsrc->left) w=sdesc.dwWidth-rsrc->left; - if (w<0) w=0; - - if (trans & (DDBLTFAST_SRCCOLORKEY | DDBLTFAST_DESTCOLORKEY)) { - DWORD keylow, keyhigh; - if (trans & DDBLTFAST_SRCCOLORKEY) { - keylow = sdesc.ddckCKSrcBlt.dwColorSpaceLowValue; - keyhigh = sdesc.ddckCKSrcBlt.dwColorSpaceHighValue; - } else { - /* I'm not sure if this is correct */ - FIXME("DDBLTFAST_DESTCOLORKEY not fully supported yet.\n"); - keylow = ddesc.ddckCKDestBlt.dwColorSpaceLowValue; - keyhigh = ddesc.ddckCKDestBlt.dwColorSpaceHighValue; } -#define COPYBOX_COLORKEY(type) { \ - type *d = (type *)dbuf, *s = (type *)sbuf, tmp; \ - s = (type *) ((BYTE *) sdesc.u1.lpSurface + (rsrc->top * sdesc.lPitch) + rsrc->left * bpp); \ - d = (type *) ((BYTE *) ddesc.u1.lpSurface + (dsty * ddesc.lPitch) + dstx * bpp); \ - for (y = 0; y < h; y++) { \ - for (x = 0; x < w; x++) { \ - tmp = s[x]; \ - if (tmp < keylow || tmp > keyhigh) d[x] = tmp; \ - } \ - (LPBYTE)s += sdesc.lPitch; \ - (LPBYTE)d += ddesc.lPitch; \ - } \ - break; \ -} - - switch (bpp) { - case 1: COPYBOX_COLORKEY(BYTE) - case 2: COPYBOX_COLORKEY(WORD) - case 4: COPYBOX_COLORKEY(DWORD) - default: - FIXME("Source color key blitting not supported for bpp %d\n",bpp*8); - ret = DDERR_UNSUPPORTED; - goto error; - } -#undef COPYBOX_COLORKEY - } else { - int width = w * bpp; - - for (y = 0; y < h; y++) { - memcpy(dbuf, sbuf, width); - sbuf += sdesc.lPitch; - dbuf += ddesc.lPitch; - } + if (!on_chain) + return DDERR_INVALIDPARAMS; /* unchecked */ } -error: - IDirectDrawSurface4_Unlock(iface,ddesc.u1.lpSurface); - IDirectDrawSurface4_Unlock(src,sdesc.u1.lpSurface); - return ret; -} -HRESULT WINAPI IDirectDrawSurface4Impl_BltBatch( - LPDIRECTDRAWSURFACE4 iface,LPDDBLTBATCH ddbltbatch,DWORD x,DWORD y -) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); - FIXME("(%p)->BltBatch(%p,%08lx,%08lx),stub!\n",This,ddbltbatch,x,y); - return DD_OK; -} - -HRESULT WINAPI IDirectDrawSurface4Impl_GetCaps( - LPDIRECTDRAWSURFACE4 iface,LPDDSCAPS caps -) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); - TRACE("(%p)->GetCaps(%p)\n",This,caps); - caps->dwCaps = DDSCAPS_PALETTE; /* probably more */ - return DD_OK; -} - -HRESULT WINAPI IDirectDrawSurface4Impl_GetSurfaceDesc( - LPDIRECTDRAWSURFACE4 iface,LPDDSURFACEDESC ddsd -) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); - TRACE("(%p)->GetSurfaceDesc(%p)\n", This,ddsd); - - /* Simply copy the surface description stored in the object */ - *ddsd = This->s.surface_desc; - - if (TRACE_ON(ddraw)) { _dump_surface_desc(ddsd); } + TRACE("flip to backbuffer: %p\n",target); + This->flip_data(This, target); + This->flip_update(This); return DD_OK; } -ULONG WINAPI IDirectDrawSurface4Impl_AddRef(LPDIRECTDRAWSURFACE4 iface) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); - TRACE("(%p)->() incrementing from %lu.\n", This, This->ref ); - return ++(This->ref); +static PrivateData* find_private_data(IDirectDrawSurfaceImpl *This, + REFGUID tag) +{ + PrivateData* data; + for (data = This->private_data; data != NULL; data = data->next) + { + if (IsEqualGUID(&data->tag, tag)) break; + } + + return data; } +HRESULT WINAPI +Main_DirectDrawSurface_FreePrivateData(LPDIRECTDRAWSURFACE7 iface, REFGUID tag) +{ + ICOM_THIS(IDirectDrawSurfaceImpl, iface); + PrivateData *data; -HRESULT WINAPI IDirectDrawSurface4Impl_GetAttachedSurface( - LPDIRECTDRAWSURFACE4 iface,LPDDSCAPS lpddsd,LPDIRECTDRAWSURFACE4 *lpdsf -) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); - int i,found = 0,xstart; - struct _surface_chain *chain; + data = find_private_data(This, tag); + if (data == NULL) return DDERR_NOTFOUND; - TRACE("(%p)->GetAttachedSurface(%p,%p)\n", This, lpddsd, lpdsf); - if (TRACE_ON(ddraw)) { - TRACE(" caps ");_dump_DDSCAPS((void *) &(lpddsd->dwCaps)); - DPRINTF("\n"); + if (data->prev) + data->prev->next = data->next; + if (data->next) + data->next->prev = data->prev; + + if (data->flags & DDSPD_IUNKNOWNPTR) + { + if (data->ptr.object != NULL) + IUnknown_Release(data->ptr.object); } - chain = This->s.chain; - if (!chain) - return DDERR_NOTFOUND; + else + HeapFree(GetProcessHeap(), 0, data->ptr.data); - for (i=0;inrofsurfaces;i++) - if (chain->surfaces[i] == This) - break; + HeapFree(GetProcessHeap(), 0, data); - xstart = i; - for (i=0;inrofsurfaces;i++) { - if ((SDDSCAPS(chain->surfaces[(xstart+i)%chain->nrofsurfaces])&lpddsd->dwCaps) == lpddsd->dwCaps) { -#if 0 - if (found) /* may not find the same caps twice, (doc) */ - return DDERR_INVALIDPARAMS;/*FIXME: correct? */ -#endif - found = (i+1)+xstart; + return DD_OK; +} + +HRESULT WINAPI +Main_DirectDrawSurface_GetAttachedSurface(LPDIRECTDRAWSURFACE7 iface, + LPDDSCAPS2 pCaps, + LPDIRECTDRAWSURFACE7* ppSurface) +{ + ICOM_THIS(IDirectDrawSurfaceImpl, iface); + IDirectDrawSurfaceImpl* surf; + IDirectDrawSurfaceImpl* found = NULL; + + TRACE("(%p)->Looking for caps: %x,%x,%x,%x output: %p\n",This,pCaps->dwCaps, pCaps->dwCaps2, + pCaps->dwCaps3, pCaps->dwCaps4, ppSurface); + + for (surf = This->attached; surf != NULL; surf = surf->next_attached) + { + TRACE("Surface: (%p) caps: %x,%x,%x,%x \n",surf , + surf->surface_desc.ddsCaps.dwCaps, + surf->surface_desc.ddsCaps.dwCaps2, + surf->surface_desc.ddsCaps.dwCaps3, + surf->surface_desc.ddsCaps.dwCaps4); + if (((surf->surface_desc.ddsCaps.dwCaps & pCaps->dwCaps) == pCaps->dwCaps) + && ((surf->surface_desc.ddsCaps.dwCaps2 & pCaps->dwCaps2) == pCaps->dwCaps2)) + { + /* MSDN: "This method fails if more than one surface is attached + * that matches the capabilities requested." */ + if (found != NULL) + { + FIXME("More than one attached surface matches requested caps. What should we do here?\n"); + /* Previous code returned 'DDERR_NOTFOUND'. That appears not + to be correct, given what 3DMark expects from MipMapped surfaces. + We shall just continue instead. */ + } + + found = surf; } } - if (!found) + + if (found == NULL) return DDERR_NOTFOUND; - *lpdsf = (LPDIRECTDRAWSURFACE4)chain->surfaces[found-1-xstart]; - /* For EverQuest testing */ - IDirectDrawSurface4_AddRef(*lpdsf); - - TRACE("found %p\n",*lpdsf); + *ppSurface = ICOM_INTERFACE(found, IDirectDrawSurface7); + + /* XXX d3dframe.cpp sometimes AddRefs things that it gets from us. */ + IDirectDrawSurface7_AddRef(ICOM_INTERFACE(found, IDirectDrawSurface7)); return DD_OK; } -HRESULT WINAPI IDirectDrawSurface4Impl_Initialize( - LPDIRECTDRAWSURFACE4 iface,LPDIRECTDRAW ddraw,LPDDSURFACEDESC lpdsfd -) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); - TRACE("(%p)->(%p, %p)\n",This,ddraw,lpdsfd); +HRESULT WINAPI +Main_DirectDrawSurface_GetBltStatus(LPDIRECTDRAWSURFACE7 iface, DWORD dwFlags) +{ + TRACE("(%p)->(%08lx)\n",iface,dwFlags); + switch (dwFlags) + { + case DDGBS_CANBLT: + case DDGBS_ISBLTDONE: + return DD_OK; + + default: + return DDERR_INVALIDPARAMS; + } +} + +HRESULT WINAPI +Main_DirectDrawSurface_GetCaps(LPDIRECTDRAWSURFACE7 iface, LPDDSCAPS2 pCaps) +{ + ICOM_THIS(IDirectDrawSurfaceImpl, iface); + + TRACE("(%p)->(%p)\n",This,pCaps); + *pCaps = This->surface_desc.ddsCaps; + return DD_OK; +} + +HRESULT WINAPI +Main_DirectDrawSurface_GetClipper(LPDIRECTDRAWSURFACE7 iface, + LPDIRECTDRAWCLIPPER* ppClipper) +{ + ICOM_THIS(IDirectDrawSurfaceImpl, iface); + + TRACE("(%p)->(%p)\n",This,ppClipper); + if (This->clipper == NULL) + return DDERR_NOCLIPPERATTACHED; + + *ppClipper = ICOM_INTERFACE(This->clipper, IDirectDrawClipper); + IDirectDrawClipper_AddRef(ICOM_INTERFACE(This->clipper, + IDirectDrawClipper)); + return DD_OK; +} + +HRESULT WINAPI +Main_DirectDrawSurface_GetColorKey(LPDIRECTDRAWSURFACE7 iface, DWORD dwFlags, + LPDDCOLORKEY pCKey) +{ + /* There is a DDERR_NOCOLORKEY error, but how do we know if a color key + * isn't there? That's like saying that an int isn't there. (Which MS + * has done in other docs.) */ + + ICOM_THIS(IDirectDrawSurfaceImpl, iface); + + TRACE("(%p)->(%08lx,%p)\n",This,dwFlags,pCKey); + switch (dwFlags) + { + case DDCKEY_DESTBLT: + *pCKey = This->surface_desc.ddckCKDestBlt; + break; + + case DDCKEY_DESTOVERLAY: + *pCKey = This->surface_desc.u3.ddckCKDestOverlay; + break; + + case DDCKEY_SRCBLT: + *pCKey = This->surface_desc.ddckCKSrcBlt; + break; + + case DDCKEY_SRCOVERLAY: + *pCKey = This->surface_desc.ddckCKSrcOverlay; + break; + + default: + return DDERR_INVALIDPARAMS; + } + + return DD_OK; +} + +/* XXX We need to do something with the DC if the surface gets lost. */ +HRESULT WINAPI +Main_DirectDrawSurface_GetDC(LPDIRECTDRAWSURFACE7 iface, HDC *phDC) +{ + DDSURFACEDESC2 ddsd; + HRESULT hr; + ICOM_THIS(IDirectDrawSurfaceImpl, iface); + + TRACE("(%p)->(%p)\n",This,phDC); + CHECK_LOST(This); + + LOCK_OBJECT(This); + + if (This->dc_in_use) + { + UNLOCK_OBJECT(This); + return DDERR_DCALREADYCREATED; + } + + /* Lock as per MSDN. + * Strange: Lock lists DDERR_SURFACEBUSY as an error, meaning that another + * thread has it locked, but GetDC does not. */ + ddsd.dwSize = sizeof(ddsd); + hr = IDirectDrawSurface7_Lock(iface, NULL, &ddsd, 0, 0); + if (FAILED(hr)) + { + UNLOCK_OBJECT(This); + return hr; + } + + hr = This->get_dc(This, &This->hDC); + if (SUCCEEDED(hr)) + { + TRACE("returning %08x\n",This->hDC); + + *phDC = This->hDC; + This->dc_in_use = TRUE; + } + else WARN("No DC! Prepare for trouble\n"); + + UNLOCK_OBJECT(This); + return hr; +} + +HRESULT WINAPI +Main_DirectDrawSurface_GetDDInterface(LPDIRECTDRAWSURFACE7 iface, LPVOID* pDD) +{ + ICOM_THIS(IDirectDrawSurfaceImpl, iface); + + TRACE("(%p)->(%p)\n",This,pDD); + *pDD = ICOM_INTERFACE(This->ddraw_owner, IDirectDraw7); + IDirectDraw7_AddRef(ICOM_INTERFACE(This->ddraw_owner, IDirectDraw7)); + return DD_OK; +} + +HRESULT WINAPI +Main_DirectDrawSurface_GetFlipStatus(LPDIRECTDRAWSURFACE7 iface, DWORD dwFlags) +{ + /* XXX: DDERR_INVALIDSURFACETYPE */ + + TRACE("(%p)->(%08lx)\n",iface,dwFlags); + switch (dwFlags) + { + case DDGFS_CANFLIP: + case DDGFS_ISFLIPDONE: + return DD_OK; + + default: + return DDERR_INVALIDPARAMS; + } +} + +HRESULT WINAPI +Main_DirectDrawSurface_GetLOD(LPDIRECTDRAWSURFACE7 iface, LPDWORD pdwMaxLOD) +{ + ICOM_THIS(IDirectDrawSurfaceImpl, iface); + + TRACE("(%p)->(%p)\n",This,pdwMaxLOD); + CHECK_TEXTURE(This); + + *pdwMaxLOD = This->max_lod; + return DD_OK; +} + +HRESULT WINAPI +Main_DirectDrawSurface_GetOverlayPosition(LPDIRECTDRAWSURFACE7 iface, + LPLONG pX, LPLONG pY) +{ + return DDERR_NOTAOVERLAYSURFACE; +} + +HRESULT WINAPI +Main_DirectDrawSurface_GetPalette(LPDIRECTDRAWSURFACE7 iface, + LPDIRECTDRAWPALETTE* ppPalette) +{ + ICOM_THIS(IDirectDrawSurfaceImpl, iface); + + TRACE("(%p)->(%p)\n",This,ppPalette); + if (This->palette == NULL) + return DDERR_NOPALETTEATTACHED; + + *ppPalette = ICOM_INTERFACE(This->palette, IDirectDrawPalette); + IDirectDrawPalette_AddRef(ICOM_INTERFACE(This->palette, + IDirectDrawPalette)); + return DD_OK; +} + +HRESULT WINAPI +Main_DirectDrawSurface_GetPixelFormat(LPDIRECTDRAWSURFACE7 iface, + LPDDPIXELFORMAT pDDPixelFormat) +{ + /* What is DDERR_INVALIDSURFACETYPE for here? */ + ICOM_THIS(IDirectDrawSurfaceImpl, iface); + + TRACE("(%p)->(%p)\n",This,pDDPixelFormat); + *pDDPixelFormat = This->surface_desc.u4.ddpfPixelFormat; + return DD_OK; +} + +HRESULT WINAPI +Main_DirectDrawSurface_GetPriority(LPDIRECTDRAWSURFACE7 iface, + LPDWORD pdwPriority) +{ + ICOM_THIS(IDirectDrawSurfaceImpl, iface); + + TRACE("(%p)->(%p)\n",This,pdwPriority); + CHECK_TEXTURE(This); + + *pdwPriority = This->priority; + return DD_OK; +} + +HRESULT WINAPI +Main_DirectDrawSurface_GetPrivateData(LPDIRECTDRAWSURFACE7 iface, + REFGUID tag, LPVOID pBuffer, + LPDWORD pcbBufferSize) +{ + ICOM_THIS(IDirectDrawSurfaceImpl, iface); + PrivateData* data; + + data = find_private_data(This, tag); + if (data == NULL) return DDERR_NOTFOUND; + + /* This may not be right. */ + if ((data->flags & DDSPD_VOLATILE) + && data->uniqueness_value != This->uniqueness_value) + return DDERR_EXPIRED; + + if (*pcbBufferSize < data->size) + { + *pcbBufferSize = data->size; + return DDERR_MOREDATA; + } + + if (data->flags & DDSPD_IUNKNOWNPTR) + { + *(LPUNKNOWN *)pBuffer = data->ptr.object; + IUnknown_AddRef(data->ptr.object); + } + else + { + memcpy(pBuffer, data->ptr.data, data->size); + } + + return DD_OK; +} + +HRESULT WINAPI +Main_DirectDrawSurface_GetSurfaceDesc(LPDIRECTDRAWSURFACE7 iface, + LPDDSURFACEDESC2 pDDSD) +{ + ICOM_THIS(IDirectDrawSurfaceImpl, iface); + + TRACE("(%p)->(%p)\n",This,pDDSD); + *pDDSD = This->surface_desc; + return DD_OK; +} + +HRESULT WINAPI +Main_DirectDrawSurface_GetUniquenessValue(LPDIRECTDRAWSURFACE7 iface, + LPDWORD pValue) +{ + ICOM_THIS(IDirectDrawSurfaceImpl, iface); + + TRACE("(%p)->(%p)\n",This,pValue); + *pValue = This->uniqueness_value; + return DD_OK; +} + +HRESULT WINAPI +Main_DirectDrawSurface_Initialize(LPDIRECTDRAWSURFACE7 iface, + LPDIRECTDRAW pDD, LPDDSURFACEDESC2 pDDSD) +{ + TRACE("(%p)->(%p,%p)\n",iface,pDD,pDDSD); return DDERR_ALREADYINITIALIZED; } -HRESULT WINAPI IDirectDrawSurface4Impl_GetPixelFormat( - LPDIRECTDRAWSURFACE4 iface,LPDDPIXELFORMAT pf -) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); - TRACE("(%p)->(%p)\n",This,pf); - - *pf = This->s.surface_desc.ddpfPixelFormat; - if (TRACE_ON(ddraw)) { _dump_pixelformat(pf); DPRINTF("\n"); } - return DD_OK; -} - -HRESULT WINAPI IDirectDrawSurface4Impl_GetBltStatus(LPDIRECTDRAWSURFACE4 iface,DWORD dwFlags) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); - FIXME("(%p)->(0x%08lx),stub!\n",This,dwFlags); - return DD_OK; -} - -HRESULT WINAPI IDirectDrawSurface4Impl_GetOverlayPosition( - LPDIRECTDRAWSURFACE4 iface,LPLONG x1,LPLONG x2 -) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); - FIXME("(%p)->(%p,%p),stub!\n",This,x1,x2); - return DD_OK; -} - -HRESULT WINAPI IDirectDrawSurface4Impl_SetClipper( - LPDIRECTDRAWSURFACE4 iface,LPDIRECTDRAWCLIPPER lpClipper -) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); - TRACE("(%p)->(%p)!\n",This,lpClipper); - - if (This->s.lpClipper) IDirectDrawClipper_Release( This->s.lpClipper ); - This->s.lpClipper = lpClipper; - if (lpClipper) IDirectDrawClipper_AddRef( lpClipper ); - return DD_OK; -} - -HRESULT WINAPI IDirectDrawSurface4Impl_AddAttachedSurface( - LPDIRECTDRAWSURFACE4 iface,LPDIRECTDRAWSURFACE4 surf -) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); - IDirectDrawSurface4Impl*isurf = (IDirectDrawSurface4Impl*)surf; - int i; - struct _surface_chain *chain; - - FIXME("(%p)->(%p)\n",This,surf); - chain = This->s.chain; - - /* IDirectDrawSurface4_AddRef(surf); */ - - if (chain) { - for (i=0;inrofsurfaces;i++) - if (chain->surfaces[i] == isurf) - FIXME("attaching already attached surface %p to %p!\n",iface,isurf); - } else { - chain = HeapAlloc(GetProcessHeap(),0,sizeof(*chain)); - chain->nrofsurfaces = 1; - chain->surfaces = HeapAlloc(GetProcessHeap(),0,sizeof(chain->surfaces[0])); - chain->surfaces[0] = This; - This->s.chain = chain; - } - - if (chain->surfaces) - chain->surfaces = HeapReAlloc( - GetProcessHeap(), - 0, - chain->surfaces, - sizeof(chain->surfaces[0])*(chain->nrofsurfaces+1) - ); - else - chain->surfaces = HeapAlloc(GetProcessHeap(),0,sizeof(chain->surfaces[0])); - isurf->s.chain = chain; - chain->surfaces[chain->nrofsurfaces++] = isurf; - return DD_OK; -} - -HRESULT WINAPI IDirectDrawSurface4Impl_GetDC(LPDIRECTDRAWSURFACE4 iface,HDC* lphdc) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); - DDSURFACEDESC desc; - BITMAPINFO *b_info; - UINT usage; - HDC ddc; - - TRACE("(%p)->GetDC(%p)\n",This,lphdc); - - /* Creates a DIB Section of the same size / format as the surface */ - IDirectDrawSurface4_Lock(iface,NULL,&desc,0,0); - - if (This->s.hdc == 0) { - switch (desc.ddpfPixelFormat.u.dwRGBBitCount) { - case 16: - case 32: -#if 0 /* This should be filled if Wine's DIBSection did understand BI_BITFIELDS */ - b_info = (BITMAPINFO *) HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(BITMAPINFOHEADER) + 3 * sizeof(DWORD)); - break; -#endif - - case 24: - b_info = (BITMAPINFO *) HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(BITMAPINFOHEADER)); - break; - - default: - b_info = (BITMAPINFO *)HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, - sizeof(BITMAPINFOHEADER) + sizeof(RGBQUAD) * (2 << desc.ddpfPixelFormat.u.dwRGBBitCount)); - break; - } - - b_info->bmiHeader.biSize = sizeof(BITMAPINFOHEADER); - b_info->bmiHeader.biWidth = desc.dwWidth; - b_info->bmiHeader.biHeight = -desc.dwHeight; - b_info->bmiHeader.biPlanes = 1; - b_info->bmiHeader.biBitCount = desc.ddpfPixelFormat.u.dwRGBBitCount; -#if 0 - if ((desc.ddpfPixelFormat.u.dwRGBBitCount != 16) && - (desc.ddpfPixelFormat.u.dwRGBBitCount != 32)) -#endif - b_info->bmiHeader.biCompression = BI_RGB; -#if 0 - else - b_info->bmiHeader.biCompression = BI_BITFIELDS; -#endif - b_info->bmiHeader.biSizeImage = (desc.ddpfPixelFormat.u.dwRGBBitCount / 8) * desc.dwWidth * desc.dwHeight; - b_info->bmiHeader.biXPelsPerMeter = 0; - b_info->bmiHeader.biYPelsPerMeter = 0; - b_info->bmiHeader.biClrUsed = 0; - b_info->bmiHeader.biClrImportant = 0; - - switch (desc.ddpfPixelFormat.u.dwRGBBitCount) { - case 16: - case 32: -#if 0 - { - DWORD *masks = (DWORD *) &(b_info->bmiColors); - - usage = 0; - masks[0] = desc.ddpfPixelFormat.u1.dwRBitMask; - masks[1] = desc.ddpfPixelFormat.u2.dwGBitMask; - masks[2] = desc.ddpfPixelFormat.u3.dwBBitMask; - } - break; -#endif - case 24: - /* Nothing to do */ - usage = DIB_RGB_COLORS; - break; - - default: { - int i; - - /* Fill the palette */ - usage = DIB_RGB_COLORS; - - if (This->s.palette == NULL) { - ERR("Bad palette !!!\n"); - } else { - RGBQUAD *rgb = (RGBQUAD *) &(b_info->bmiColors); - PALETTEENTRY *pent = (PALETTEENTRY *)&(This->s.palette->palents); - - for (i=0;i<(1<s.DIBsection = ddc ? DIB_CreateDIBSection(ddc, - b_info, - usage, - &(This->s.bitmap_data), - 0, - (DWORD)desc.u1.lpSurface, - desc.lPitch - ) : 0; - if (!This->s.DIBsection) { - ERR("CreateDIBSection failed!\n"); - if (ddc) DeleteDC(ddc); - HeapFree(GetProcessHeap(), 0, b_info); - return E_FAIL; - } - TRACE("DIBSection at : %p\n", This->s.bitmap_data); - - /* b_info is not useful anymore */ - HeapFree(GetProcessHeap(), 0, b_info); - - /* Create the DC */ - This->s.hdc = CreateCompatibleDC(ddc); - This->s.holdbitmap = SelectObject(This->s.hdc, This->s.DIBsection); - - if (ddc) DeleteDC(ddc); - } - - if (This->s.bitmap_data != desc.u1.lpSurface) { - FIXME("DIBSection not created for frame buffer, reverting to old code\n"); - /* Copy our surface in the DIB section */ - if ((GET_BPP(desc) * desc.dwWidth) == desc.lPitch) - memcpy(This->s.bitmap_data,desc.u1.lpSurface,desc.lPitch*desc.dwHeight); - else - /* TODO */ - FIXME("This case has to be done :/\n"); - } - - if (lphdc) { - TRACE("HDC : %08lx\n", (DWORD) This->s.hdc); - *lphdc = This->s.hdc; - } - - return DD_OK; -} - -HRESULT WINAPI IDirectDrawSurface4Impl_ReleaseDC(LPDIRECTDRAWSURFACE4 iface,HDC hdc) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); - - TRACE("(%p)->(0x%08lx)\n",This,(long)hdc); - - if (This->s.bitmap_data != This->s.surface_desc.u1.lpSurface) { - TRACE( "Copying DIBSection at : %p\n", This->s.bitmap_data); - /* Copy the DIB section to our surface */ - if ((GET_BPP(This->s.surface_desc) * This->s.surface_desc.dwWidth) == This->s.surface_desc.lPitch) { - memcpy(This->s.surface_desc.u1.lpSurface, This->s.bitmap_data, This->s.surface_desc.lPitch * This->s.surface_desc.dwHeight); - } else { - /* TODO */ - FIXME("This case has to be done :/\n"); - } - } - /* Unlock the surface */ - IDirectDrawSurface4_Unlock(iface,This->s.surface_desc.u1.lpSurface); - return DD_OK; -} - -HRESULT WINAPI IDirectDrawSurface4Impl_QueryInterface( - LPDIRECTDRAWSURFACE4 iface,REFIID refiid,LPVOID *obj -) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); - - TRACE("(%p)->(%s,%p)\n",This,debugstr_guid(refiid),obj); - - /* All DirectDrawSurface versions (1, 2, 3 and 4) use - * the same interface. And IUnknown does that too of course. - */ - if ( IsEqualGUID( &IID_IDirectDrawSurface4, refiid ) || - IsEqualGUID( &IID_IDirectDrawSurface3, refiid ) || - IsEqualGUID( &IID_IDirectDrawSurface2, refiid ) || - IsEqualGUID( &IID_IDirectDrawSurface, refiid ) || - IsEqualGUID( &IID_IUnknown, refiid ) - ) { - *obj = This; - IDirectDrawSurface4_AddRef(iface); - - TRACE(" Creating IDirectDrawSurface interface (%p)\n", *obj); - return S_OK; - } - FIXME("(%p):interface for IID %s NOT found!\n",This,debugstr_guid(refiid)); - return OLE_E_ENUM_NOMORE; -} - -HRESULT WINAPI IDirectDrawSurface4Impl_IsLost(LPDIRECTDRAWSURFACE4 iface) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); - TRACE("(%p)->(), stub!\n",This); - return DD_OK; /* hmm */ -} - -HRESULT WINAPI IDirectDrawSurface4Impl_EnumAttachedSurfaces( - LPDIRECTDRAWSURFACE4 iface,LPVOID context,LPDDENUMSURFACESCALLBACK esfcb -) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); - int i; - struct _surface_chain *chain = This->s.chain; - - TRACE("(%p)->(%p,%p)\n",This,context,esfcb); - if (chain) { - for (i=0;inrofsurfaces;i++) { - TRACE( "Enumerating attached surface (%p)\n", chain->surfaces[i]); - if (esfcb((LPDIRECTDRAWSURFACE) chain->surfaces[i], &(chain->surfaces[i]->s.surface_desc), context) == DDENUMRET_CANCEL) - return DD_OK; /* FIXME: return value correct? */ - } - } - return DD_OK; -} - -HRESULT WINAPI IDirectDrawSurface4Impl_Restore(LPDIRECTDRAWSURFACE4 iface) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); - FIXME("(%p)->(),stub!\n",This); - return DD_OK; -} - -HRESULT WINAPI IDirectDrawSurface4Impl_SetColorKey( - LPDIRECTDRAWSURFACE4 iface, DWORD dwFlags, LPDDCOLORKEY ckey ) +HRESULT WINAPI +Main_DirectDrawSurface_IsLost(LPDIRECTDRAWSURFACE7 iface) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); - TRACE("(%p)->(0x%08lx,%p)\n",This,dwFlags,ckey); - if (TRACE_ON(ddraw)) { - _dump_colorkeyflag(dwFlags); - DPRINTF(" : "); - _dump_DDCOLORKEY((void *) ckey); - DPRINTF("\n"); + ICOM_THIS(IDirectDrawSurfaceImpl, iface); + + TRACE("(%p) is%s lost\n",This, (This->lost ? "" : " not")); + return This->lost ? DDERR_SURFACELOST : DD_OK; +} + + +/* XXX This doesn't actually do any locking or keep track of the locked + * rectangles. The behaviour is poorly documented. */ +HRESULT WINAPI +Main_DirectDrawSurface_Lock(LPDIRECTDRAWSURFACE7 iface, LPRECT prect, + LPDDSURFACEDESC2 pDDSD, DWORD flags, HANDLE h) +{ + ICOM_THIS(IDirectDrawSurfaceImpl, iface); + + TRACE("(%p)->Lock(%p,%p,%08lx,%08lx)\n",This,prect,pDDSD,flags,(DWORD)h); + + if (flags & ~(DDLOCK_WAIT|DDLOCK_READONLY|DDLOCK_WRITEONLY)) + WARN("(%p)->Lock(%p,%p,%08lx,%08lx)\n", + This,prect,pDDSD,flags,(DWORD)h); + + /* First, copy the Surface description */ + memcpy(pDDSD, &(This->surface_desc), pDDSD->dwSize); + TRACE("locked surface: height=%ld, width=%ld, pitch=%ld\n", + pDDSD->dwHeight,pDDSD->dwWidth,pDDSD->u1.lPitch); + + /* If asked only for a part, change the surface pointer. + * (Not documented.) */ + if (prect != NULL) { + TRACE(" lprect: %dx%d-%dx%d\n", + prect->top,prect->left,prect->bottom,prect->right + ); + if ((prect->top < 0) || + (prect->left < 0) || + (prect->bottom < 0) || + (prect->right < 0)) { + ERR(" Negative values in LPRECT !!!\n"); + return DDERR_INVALIDPARAMS; + } + + This->lock_update(This, prect); + + pDDSD->lpSurface = (char *)This->surface_desc.lpSurface + + prect->top * This->surface_desc.u1.lPitch + + prect->left * GET_BPP(This->surface_desc); } - /* If this surface was loaded as a texture, call also the texture - * SetColorKey callback. FIXME: hack approach :( - */ - if (This->s.texture) - This->s.SetColorKey_cb(This->s.texture, dwFlags, ckey); - - if( dwFlags & DDCKEY_SRCBLT ) { - dwFlags &= ~DDCKEY_SRCBLT; - This->s.surface_desc.dwFlags |= DDSD_CKSRCBLT; - memcpy( &(This->s.surface_desc.ddckCKSrcBlt), ckey, sizeof( *ckey ) ); - } - - if( dwFlags & DDCKEY_DESTBLT ) { - dwFlags &= ~DDCKEY_DESTBLT; - This->s.surface_desc.dwFlags |= DDSD_CKDESTBLT; - memcpy( &(This->s.surface_desc.ddckCKDestBlt), ckey, sizeof( *ckey ) ); - } - - if( dwFlags & DDCKEY_SRCOVERLAY ) { - dwFlags &= ~DDCKEY_SRCOVERLAY; - This->s.surface_desc.dwFlags |= DDSD_CKSRCOVERLAY; - memcpy( &(This->s.surface_desc.ddckCKSrcOverlay), ckey, sizeof( *ckey ) ); - } - - if( dwFlags & DDCKEY_DESTOVERLAY ) { - dwFlags &= ~DDCKEY_DESTOVERLAY; - This->s.surface_desc.dwFlags |= DDSD_CKDESTOVERLAY; - memcpy( &(This->s.surface_desc.ddckCKDestOverlay), ckey, sizeof( *ckey ) ); - } - if( dwFlags ) - FIXME("unhandled dwFlags: 0x%08lx\n", dwFlags ); return DD_OK; } -HRESULT WINAPI IDirectDrawSurface4Impl_AddOverlayDirtyRect( - LPDIRECTDRAWSURFACE4 iface, LPRECT lpRect -) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); - FIXME("(%p)->(%p),stub!\n",This,lpRect); - - return DD_OK; +HRESULT WINAPI +Main_DirectDrawSurface_PageLock(LPDIRECTDRAWSURFACE7 iface, DWORD dwFlags) +{ + /* Some surface types should return DDERR_CANTPAGELOCK. */ + return DD_OK; } -HRESULT WINAPI IDirectDrawSurface4Impl_DeleteAttachedSurface( - LPDIRECTDRAWSURFACE4 iface, DWORD dwFlags, - LPDIRECTDRAWSURFACE4 lpDDSAttachedSurface -) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); - int i; - struct _surface_chain *chain; +HRESULT WINAPI +Main_DirectDrawSurface_PageUnlock(LPDIRECTDRAWSURFACE7 iface, DWORD dwFlags) +{ + /* Some surface types should return DDERR_CANTPAGEUNLOCK, and we should + * keep track so we can return DDERR_NOTPAGELOCKED as appropriate. */ + return DD_OK; +} - TRACE("(%p)->(0x%08lx,%p)\n",This,dwFlags,lpDDSAttachedSurface); - chain = This->s.chain; - for (i=0;inrofsurfaces;i++) { - if ((IDirectDrawSurface4Impl*)lpDDSAttachedSurface==chain->surfaces[i]){ - /* There is no AddRef in AddAttachedSurface, so why a release here :-) - IDirectDrawSurface4_Release(lpDDSAttachedSurface); */ +HRESULT WINAPI +Main_DirectDrawSurface_ReleaseDC(LPDIRECTDRAWSURFACE7 iface, HDC hDC) +{ + HRESULT hr; + ICOM_THIS(IDirectDrawSurfaceImpl, iface); - chain->surfaces[i]->s.chain = NULL; - memcpy( chain->surfaces+i, - chain->surfaces+(i+1), - (chain->nrofsurfaces-i-1)*sizeof(chain->surfaces[i]) - ); - chain->surfaces = HeapReAlloc( - GetProcessHeap(), - 0, - chain->surfaces, - sizeof(chain->surfaces[i])*(chain->nrofsurfaces-1) - ); - chain->nrofsurfaces--; - return DD_OK; + TRACE("(%p)->(%08x)\n",This,hDC); + + if (!This->dc_in_use || This->hDC != hDC) + return DDERR_INVALIDPARAMS; + + This->release_dc(This, hDC); + + hr = IDirectDrawSurface7_Unlock(iface, NULL); + if (FAILED(hr)) return hr; + + This->dc_in_use = FALSE; + This->hDC = 0; + + return DD_OK; +} + +/* Restore */ + +HRESULT WINAPI +Main_DirectDrawSurface_SetClipper(LPDIRECTDRAWSURFACE7 iface, + LPDIRECTDRAWCLIPPER pDDClipper) +{ + ICOM_THIS(IDirectDrawSurfaceImpl, iface); + + TRACE("(%p)->(%p)\n",This,pDDClipper); + if (pDDClipper == ICOM_INTERFACE(This->clipper, IDirectDrawClipper)) + return DD_OK; + + if (This->clipper != NULL) + IDirectDrawClipper_Release(ICOM_INTERFACE(This->clipper, + IDirectDrawClipper)); + + This->clipper = ICOM_OBJECT(IDirectDrawClipperImpl, IDirectDrawClipper, + pDDClipper); + if (pDDClipper != NULL) + IDirectDrawClipper_AddRef(pDDClipper); + + return DD_OK; +} + +HRESULT WINAPI +Main_DirectDrawSurface_SetColorKey(LPDIRECTDRAWSURFACE7 iface, + DWORD dwFlags, LPDDCOLORKEY pCKey) +{ + ICOM_THIS(IDirectDrawSurfaceImpl, iface); + + TRACE("(%p)->(%08lx,%p)\n",This,dwFlags,pCKey); + if (pCKey == NULL) + { + FIXME("supposedly removing color key %lu\n", + dwFlags & ~DDCKEY_COLORSPACE); + return DD_OK; + } + + switch (dwFlags & ~DDCKEY_COLORSPACE) + { + case DDCKEY_DESTBLT: + This->surface_desc.ddckCKDestBlt = *pCKey; + break; + + case DDCKEY_DESTOVERLAY: + This->surface_desc.u3.ddckCKDestOverlay = *pCKey; + break; + + case DDCKEY_SRCOVERLAY: + This->surface_desc.ddckCKSrcOverlay = *pCKey; + break; + + case DDCKEY_SRCBLT: + This->surface_desc.ddckCKSrcBlt = *pCKey; + break; + + default: + return DDERR_INVALIDPARAMS; + } + + return DD_OK; +} + +HRESULT WINAPI +Main_DirectDrawSurface_SetLOD(LPDIRECTDRAWSURFACE7 iface, DWORD dwMaxLOD) +{ + ICOM_THIS(IDirectDrawSurfaceImpl, iface); + + TRACE("(%p)->(%08lx)\n",This,dwMaxLOD); + CHECK_TEXTURE(This); + + This->max_lod = dwMaxLOD; + return DD_OK; +} + +HRESULT WINAPI +Main_DirectDrawSurface_SetOverlayPosition(LPDIRECTDRAWSURFACE7 iface, + LONG X, LONG Y) +{ + return DDERR_NOTAOVERLAYSURFACE; +} + +HRESULT WINAPI +Main_DirectDrawSurface_SetPalette(LPDIRECTDRAWSURFACE7 iface, + LPDIRECTDRAWPALETTE pPalette) +{ + ICOM_THIS(IDirectDrawSurfaceImpl, iface); + + TRACE("(%p)->(%p)\n",This,pPalette); + if (pPalette == ICOM_INTERFACE(This->palette, IDirectDrawPalette)) + return DD_OK; + + if (This->palette != NULL) { + if (This->surface_desc.ddsCaps.dwCaps & DDSCAPS_PRIMARYSURFACE) + This->palette->flags &= ~DDPCAPS_PRIMARYSURFACE; + IDirectDrawPalette_Release(ICOM_INTERFACE(This->palette, + IDirectDrawPalette)); + } + + This->palette = ICOM_OBJECT(IDirectDrawPaletteImpl, IDirectDrawPalette, + pPalette); + if (pPalette != NULL) { + IDirectDrawPalette_AddRef(pPalette); + if (This->surface_desc.ddsCaps.dwCaps & DDSCAPS_PRIMARYSURFACE) + This->palette->flags |= DDPCAPS_PRIMARYSURFACE; + } + + This->set_palette(This, This->palette); + + return DD_OK; +} + +HRESULT WINAPI +Main_DirectDrawSurface_SetPriority(LPDIRECTDRAWSURFACE7 iface, + DWORD dwPriority) +{ + ICOM_THIS(IDirectDrawSurfaceImpl, iface); + + TRACE("(%p)->(%08lx)\n",This,dwPriority); + CHECK_TEXTURE(This); + + This->priority = dwPriority; + return DD_OK; +} + +/* Be careful when locking this: it is risky to call the object's AddRef + * or Release holding a lock. */ +HRESULT WINAPI +Main_DirectDrawSurface_SetPrivateData(LPDIRECTDRAWSURFACE7 iface, + REFGUID tag, LPVOID pData, + DWORD cbSize, DWORD dwFlags) +{ + PrivateData* data; + ICOM_THIS(IDirectDrawSurfaceImpl, iface); + + data = find_private_data(This, tag); + if (data == NULL) + { + data = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(*data)); + if (data == NULL) return DDERR_OUTOFMEMORY; + + data->tag = *tag; + data->flags = dwFlags; + data->uniqueness_value = This->uniqueness_value; + + if (dwFlags & DDSPD_IUNKNOWNPTR) + { + data->ptr.object = (LPUNKNOWN)pData; + data->size = sizeof(LPUNKNOWN); + IUnknown_AddRef(data->ptr.object); } + else + { + data->ptr.data = HeapAlloc(GetProcessHeap(), 0, cbSize); + if (data->ptr.data == NULL) + { + HeapFree(GetProcessHeap(), 0, data); + return DDERR_OUTOFMEMORY; + } + } + + /* link it in */ + data->next = This->private_data; + data->prev = NULL; + if (This->private_data) + This->private_data->prev = data; + This->private_data = data; + + return DD_OK; } - return DD_OK; -} + else + { + /* I don't actually know how windows handles this case. The only + * reason I don't just call FreePrivateData is because I want to + * guarantee SetPrivateData working when using LPUNKNOWN or data + * that is no larger than the old data. */ -HRESULT WINAPI IDirectDrawSurface4Impl_EnumOverlayZOrders( - LPDIRECTDRAWSURFACE4 iface, DWORD dwFlags, LPVOID lpContext, - LPDDENUMSURFACESCALLBACK lpfnCallback -) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); - FIXME("(%p)->(0x%08lx,%p,%p),stub!\n", This,dwFlags, - lpContext, lpfnCallback ); - - return DD_OK; -} - -HRESULT WINAPI IDirectDrawSurface4Impl_GetClipper( - LPDIRECTDRAWSURFACE4 iface, LPDIRECTDRAWCLIPPER* lplpDDClipper -) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); - FIXME("(%p)->(%p),stub!\n", This, lplpDDClipper); - - return DD_OK; -} - -HRESULT WINAPI IDirectDrawSurface4Impl_GetColorKey( - LPDIRECTDRAWSURFACE4 iface, DWORD dwFlags, LPDDCOLORKEY lpDDColorKey -) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); - TRACE("(%p)->(0x%08lx,%p)\n", This, dwFlags, lpDDColorKey); - - if( dwFlags & DDCKEY_SRCBLT ) { - dwFlags &= ~DDCKEY_SRCBLT; - memcpy( lpDDColorKey, &(This->s.surface_desc.ddckCKSrcBlt), sizeof( *lpDDColorKey ) ); + return E_FAIL; } - if( dwFlags & DDCKEY_DESTBLT ) { - dwFlags &= ~DDCKEY_DESTBLT; - memcpy( lpDDColorKey, &(This->s.surface_desc.ddckCKDestBlt), sizeof( *lpDDColorKey ) ); - } - if( dwFlags & DDCKEY_SRCOVERLAY ) { - dwFlags &= ~DDCKEY_SRCOVERLAY; - memcpy( lpDDColorKey, &(This->s.surface_desc.ddckCKSrcOverlay), sizeof( *lpDDColorKey ) ); - } - if( dwFlags & DDCKEY_DESTOVERLAY ) { - dwFlags &= ~DDCKEY_DESTOVERLAY; - memcpy( lpDDColorKey, &(This->s.surface_desc.ddckCKDestOverlay), sizeof( *lpDDColorKey ) ); - } - if( dwFlags ) - FIXME("unhandled dwFlags: 0x%08lx\n", dwFlags ); - return DD_OK; } -HRESULT WINAPI IDirectDrawSurface4Impl_GetFlipStatus( - LPDIRECTDRAWSURFACE4 iface, DWORD dwFlags -) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); - FIXME("(%p)->(0x%08lx),stub!\n", This, dwFlags); +/* SetSurfaceDesc */ + +HRESULT WINAPI +Main_DirectDrawSurface_Unlock(LPDIRECTDRAWSURFACE7 iface, LPRECT pRect) +{ + ICOM_THIS(IDirectDrawSurfaceImpl,iface); + + TRACE("(%p)->Unlock(%p)\n",This,pRect); + + This->unlock_update(This, pRect); + if (This->aux_unlock) + This->aux_unlock(This->aux_ctx, This->aux_data, pRect); return DD_OK; } -HRESULT WINAPI IDirectDrawSurface4Impl_GetPalette( - LPDIRECTDRAWSURFACE4 iface, LPDIRECTDRAWPALETTE* lplpDDPalette -) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); - TRACE("(%p)->(%p),stub!\n", This, lplpDDPalette); - - if (!This->s.palette) - return DDERR_NOPALETTEATTACHED; - - IDirectDrawPalette_AddRef( (IDirectDrawPalette*) This->s.palette ); - *lplpDDPalette = (IDirectDrawPalette*) This->s.palette; - return DD_OK; +HRESULT WINAPI +Main_DirectDrawSurface_UpdateOverlay(LPDIRECTDRAWSURFACE7 iface, + LPRECT pSrcRect, + LPDIRECTDRAWSURFACE7 pDstSurface, + LPRECT pDstRect, DWORD dwFlags, + LPDDOVERLAYFX pFX) +{ + return DDERR_UNSUPPORTED; } -HRESULT WINAPI IDirectDrawSurface4Impl_SetOverlayPosition( - LPDIRECTDRAWSURFACE4 iface, LONG lX, LONG lY -) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); - FIXME("(%p)->(%ld,%ld),stub!\n", This, lX, lY); - - return DD_OK; +/* MSDN: "not currently implemented." */ +HRESULT WINAPI +Main_DirectDrawSurface_UpdateOverlayDisplay(LPDIRECTDRAWSURFACE7 iface, + DWORD dwFlags) +{ + return DDERR_UNSUPPORTED; } -HRESULT WINAPI IDirectDrawSurface4Impl_UpdateOverlay( - LPDIRECTDRAWSURFACE4 iface, LPRECT lpSrcRect, - LPDIRECTDRAWSURFACE4 lpDDDestSurface, LPRECT lpDestRect, DWORD dwFlags, - LPDDOVERLAYFX lpDDOverlayFx -) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); - FIXME("(%p)->(%p,%p,%p,0x%08lx,%p),stub!\n", This, - lpSrcRect, lpDDDestSurface, lpDestRect, dwFlags, lpDDOverlayFx ); - - return DD_OK; -} - -HRESULT WINAPI IDirectDrawSurface4Impl_UpdateOverlayDisplay( - LPDIRECTDRAWSURFACE4 iface, DWORD dwFlags -) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); - FIXME("(%p)->(0x%08lx),stub!\n", This, dwFlags); - - return DD_OK; -} - -HRESULT WINAPI IDirectDrawSurface4Impl_UpdateOverlayZOrder( - LPDIRECTDRAWSURFACE4 iface,DWORD dwFlags,LPDIRECTDRAWSURFACE4 lpDDSReference -) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); - FIXME("(%p)->(0x%08lx,%p),stub!\n", This, dwFlags, lpDDSReference); - - return DD_OK; -} - -HRESULT WINAPI IDirectDrawSurface4Impl_GetDDInterface( - LPDIRECTDRAWSURFACE4 iface, LPVOID* lplpDD -) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); - FIXME("(%p)->(%p),stub!\n", This, lplpDD); - - /* Not sure about that... */ - - IDirectDraw_AddRef((LPDIRECTDRAW)This->s.ddraw), - *lplpDD = (void *) This->s.ddraw; - - return DD_OK; -} - -HRESULT WINAPI IDirectDrawSurface4Impl_PageLock( - LPDIRECTDRAWSURFACE4 iface, DWORD dwFlags -) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); - FIXME("(%p)->(0x%08lx),stub!\n", This, dwFlags); - - return DD_OK; -} - -HRESULT WINAPI IDirectDrawSurface4Impl_PageUnlock( - LPDIRECTDRAWSURFACE4 iface, DWORD dwFlags -) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); - FIXME("(%p)->(0x%08lx),stub!\n", This, dwFlags); - - return DD_OK; -} - -HRESULT WINAPI IDirectDrawSurface4Impl_SetSurfaceDesc( - LPDIRECTDRAWSURFACE4 iface, LPDDSURFACEDESC lpDDSD, DWORD dwFlags -) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); - FIXME("(%p)->(%p,0x%08lx),stub!\n", This, lpDDSD, dwFlags); - - return DD_OK; -} - -HRESULT WINAPI IDirectDrawSurface4Impl_SetPrivateData( - LPDIRECTDRAWSURFACE4 iface, REFGUID guidTag, LPVOID lpData, DWORD cbSize, - DWORD dwFlags -) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); - FIXME("(%p)->(%p,%p,%ld,%08lx\n", This, guidTag, lpData, cbSize, dwFlags); - - return DD_OK; -} - -HRESULT WINAPI IDirectDrawSurface4Impl_GetPrivateData( - LPDIRECTDRAWSURFACE4 iface, REFGUID guidTag, LPVOID lpBuffer, - LPDWORD lpcbBufferSize -) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); - FIXME("(%p)->(%p,%p,%p)\n", This, guidTag, lpBuffer, lpcbBufferSize); - - return DD_OK; -} - -HRESULT WINAPI IDirectDrawSurface4Impl_FreePrivateData( - LPDIRECTDRAWSURFACE4 iface, REFGUID guidTag -) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); - FIXME("(%p)->(%p)\n", This, guidTag); - - return DD_OK; -} - -HRESULT WINAPI IDirectDrawSurface4Impl_GetUniquenessValue( - LPDIRECTDRAWSURFACE4 iface, LPDWORD lpValue -) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); - FIXME("(%p)->(%p)\n", This, lpValue); - - return DD_OK; -} - -HRESULT WINAPI IDirectDrawSurface4Impl_ChangeUniquenessValue( - LPDIRECTDRAWSURFACE4 iface -) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); - FIXME("(%p)\n", This); - - return DD_OK; +HRESULT WINAPI +Main_DirectDrawSurface_UpdateOverlayZOrder(LPDIRECTDRAWSURFACE7 iface, + DWORD dwFlags, + LPDIRECTDRAWSURFACE7 pDDSRef) +{ + return DDERR_NOTAOVERLAYSURFACE; } diff --git a/dlls/ddraw/dsurface/main.h b/dlls/ddraw/dsurface/main.h new file mode 100644 index 00000000000..8630964bcce --- /dev/null +++ b/dlls/ddraw/dsurface/main.h @@ -0,0 +1,215 @@ +/* Copyright 2000 TransGaming Technologies Inc. */ + +#ifndef DDRAW_DSURFACE_MAIN_H_INCLUDED +#define DDRAW_DSURFACE_MAIN_H_INCLUDED + +#include "ddraw_private.h" + +/* Support for IDirectDrawSurface7::Set/Get/FreePrivateData. I don't think + * anybody uses it for much so a good implementation is optional. */ +typedef struct PrivateData +{ + struct PrivateData* next; + struct PrivateData* prev; + + GUID tag; + DWORD flags; /* DDSPD_* */ + DWORD uniqueness_value; + + union + { + LPVOID data; + LPUNKNOWN object; + } ptr; + + DWORD size; +} PrivateData; + +/* Non-interface functions */ +HRESULT +Main_DirectDrawSurface_Construct(IDirectDrawSurfaceImpl* This, + IDirectDrawImpl* pDD, + const DDSURFACEDESC2* pDDSD); +void Main_DirectDrawSurface_ForceDestroy(IDirectDrawSurfaceImpl* This); + +void +Main_DirectDrawSurface_final_release(IDirectDrawSurfaceImpl* This); +BOOL +Main_DirectDrawSurface_attach(IDirectDrawSurfaceImpl *This, + IDirectDrawSurfaceImpl *to); +BOOL Main_DirectDrawSurface_detach(IDirectDrawSurfaceImpl *This); +void +Main_DirectDrawSurface_lock_update(IDirectDrawSurfaceImpl* This, + LPCRECT pRect); +void +Main_DirectDrawSurface_unlock_update(IDirectDrawSurfaceImpl* This, + LPCRECT pRect); +void +Main_DirectDrawSurface_lose_surface(IDirectDrawSurfaceImpl* This); +void +Main_DirectDrawSurface_set_palette(IDirectDrawSurfaceImpl* This, + IDirectDrawPaletteImpl* pal); +void +Main_DirectDrawSurface_update_palette(IDirectDrawSurfaceImpl* This, + IDirectDrawPaletteImpl* pal, + DWORD dwStart, DWORD dwCount, + LPPALETTEENTRY palent); +HWND +Main_DirectDrawSurface_get_display_window(IDirectDrawSurfaceImpl* This); + +void Main_DirectDrawSurface_flip_data(IDirectDrawSurfaceImpl* front, + IDirectDrawSurfaceImpl* back); + +#define CHECK_LOST(This) \ + do { \ + if (This->lost) return DDERR_SURFACELOST; \ + } while (0) + +#define CHECK_TEXTURE(This) \ + do { \ + if (!(This->surface_desc.ddsCaps.dwCaps2 \ + & DDSCAPS2_TEXTUREMANAGE)) \ + return DDERR_INVALIDOBJECT; \ + } while (0) + +#define LOCK_OBJECT(This) do { } while (0) +#define UNLOCK_OBJECT(This) do { } while (0) + +/* IDirectDrawSurface7 (partial) implementation */ +ULONG WINAPI +Main_DirectDrawSurface_AddRef(LPDIRECTDRAWSURFACE7 iface); +ULONG WINAPI +Main_DirectDrawSurface_Release(LPDIRECTDRAWSURFACE7 iface); +HRESULT WINAPI +Main_DirectDrawSurface_QueryInterface(LPDIRECTDRAWSURFACE7 iface, REFIID riid, + LPVOID* ppObj); +HRESULT WINAPI +Main_DirectDrawSurface_AddAttachedSurface(LPDIRECTDRAWSURFACE7 iface, + LPDIRECTDRAWSURFACE7 pAttach); +HRESULT WINAPI +Main_DirectDrawSurface_AddOverlayDirtyRect(LPDIRECTDRAWSURFACE7 iface, + LPRECT pRect); +HRESULT WINAPI +Main_DirectDrawSurface_BltBatch(LPDIRECTDRAWSURFACE7 iface, + LPDDBLTBATCH pBatch, DWORD dwCount, + DWORD dwFlags); +HRESULT WINAPI +Main_DirectDrawSurface_ChangeUniquenessValue(LPDIRECTDRAWSURFACE7 iface); +HRESULT WINAPI +Main_DirectDrawSurface_DeleteAttachedSurface(LPDIRECTDRAWSURFACE7 iface, + DWORD dwFlags, + LPDIRECTDRAWSURFACE7 pAttach); +HRESULT WINAPI +Main_DirectDrawSurface_EnumAttachedSurfaces(LPDIRECTDRAWSURFACE7 iface, + LPVOID context, + LPDDENUMSURFACESCALLBACK7 cb); +HRESULT WINAPI +Main_DirectDrawSurface_EnumOverlayZOrders(LPDIRECTDRAWSURFACE7 iface, + DWORD dwFlags, LPVOID context, + LPDDENUMSURFACESCALLBACK7 cb); +HRESULT WINAPI +Main_DirectDrawSurface_Flip(LPDIRECTDRAWSURFACE7 iface, + LPDIRECTDRAWSURFACE7 override, DWORD dwFlags); +HRESULT WINAPI +Main_DirectDrawSurface_FreePrivateData(LPDIRECTDRAWSURFACE7 iface, + REFGUID tag); +HRESULT WINAPI +Main_DirectDrawSurface_GetAttachedSurface(LPDIRECTDRAWSURFACE7 iface, + LPDDSCAPS2 pCaps, + LPDIRECTDRAWSURFACE7* ppSurface); +HRESULT WINAPI +Main_DirectDrawSurface_GetBltStatus(LPDIRECTDRAWSURFACE7 iface, + DWORD dwFlags); +HRESULT WINAPI +Main_DirectDrawSurface_GetCaps(LPDIRECTDRAWSURFACE7 iface, + LPDDSCAPS2 pCaps); +HRESULT WINAPI +Main_DirectDrawSurface_GetClipper(LPDIRECTDRAWSURFACE7 iface, + LPDIRECTDRAWCLIPPER* ppClipper); +HRESULT WINAPI +Main_DirectDrawSurface_GetColorKey(LPDIRECTDRAWSURFACE7 iface, + DWORD dwFlags, LPDDCOLORKEY pCKey); +HRESULT WINAPI +Main_DirectDrawSurface_GetDC(LPDIRECTDRAWSURFACE7 iface, HDC *phDC); +HRESULT WINAPI +Main_DirectDrawSurface_GetDDInterface(LPDIRECTDRAWSURFACE7 iface, + LPVOID* pDD); +HRESULT WINAPI +Main_DirectDrawSurface_GetFlipStatus(LPDIRECTDRAWSURFACE7 iface, + DWORD dwFlags); +HRESULT WINAPI +Main_DirectDrawSurface_GetLOD(LPDIRECTDRAWSURFACE7 iface, + LPDWORD pdwMaxLOD); +HRESULT WINAPI +Main_DirectDrawSurface_GetOverlayPosition(LPDIRECTDRAWSURFACE7 iface, + LPLONG pX, LPLONG pY); +HRESULT WINAPI +Main_DirectDrawSurface_GetPalette(LPDIRECTDRAWSURFACE7 iface, + LPDIRECTDRAWPALETTE* ppPalette); +HRESULT WINAPI +Main_DirectDrawSurface_GetPixelFormat(LPDIRECTDRAWSURFACE7 iface, + LPDDPIXELFORMAT pDDPixelFormat); +HRESULT WINAPI +Main_DirectDrawSurface_GetPriority(LPDIRECTDRAWSURFACE7 iface, + LPDWORD pdwPriority); +HRESULT WINAPI +Main_DirectDrawSurface_GetPrivateData(LPDIRECTDRAWSURFACE7 iface, REFGUID tag, + LPVOID pBuffer, LPDWORD pcbBufferSize); +HRESULT WINAPI +Main_DirectDrawSurface_GetSurfaceDesc(LPDIRECTDRAWSURFACE7 iface, + LPDDSURFACEDESC2 pDDSD); +HRESULT WINAPI +Main_DirectDrawSurface_GetUniquenessValue(LPDIRECTDRAWSURFACE7 iface, + LPDWORD pValue); +HRESULT WINAPI +Main_DirectDrawSurface_Initialize(LPDIRECTDRAWSURFACE7 iface, + LPDIRECTDRAW pDD, LPDDSURFACEDESC2 pDDSD); +HRESULT WINAPI +Main_DirectDrawSurface_IsLost(LPDIRECTDRAWSURFACE7 iface); +HRESULT WINAPI +Main_DirectDrawSurface_Lock(LPDIRECTDRAWSURFACE7 iface, LPRECT prect, + LPDDSURFACEDESC2 pDDSD, DWORD flags, HANDLE h); +HRESULT WINAPI +Main_DirectDrawSurface_PageLock(LPDIRECTDRAWSURFACE7 iface, DWORD dwFlags); +HRESULT WINAPI +Main_DirectDrawSurface_PageUnlock(LPDIRECTDRAWSURFACE7 iface, DWORD dwFlags); +HRESULT WINAPI +Main_DirectDrawSurface_ReleaseDC(LPDIRECTDRAWSURFACE7 iface, HDC hDC); +HRESULT WINAPI +Main_DirectDrawSurface_SetClipper(LPDIRECTDRAWSURFACE7 iface, + LPDIRECTDRAWCLIPPER pDDClipper); +HRESULT WINAPI +Main_DirectDrawSurface_SetColorKey(LPDIRECTDRAWSURFACE7 iface, + DWORD dwFlags, LPDDCOLORKEY pCKey); +HRESULT WINAPI +Main_DirectDrawSurface_SetLOD(LPDIRECTDRAWSURFACE7 iface, DWORD dwMaxLOD); +HRESULT WINAPI +Main_DirectDrawSurface_SetOverlayPosition(LPDIRECTDRAWSURFACE7 iface, + LONG X, LONG Y); +HRESULT WINAPI +Main_DirectDrawSurface_SetPalette(LPDIRECTDRAWSURFACE7 iface, + LPDIRECTDRAWPALETTE pPalette); +HRESULT WINAPI +Main_DirectDrawSurface_SetPriority(LPDIRECTDRAWSURFACE7 iface, + DWORD dwPriority); +HRESULT WINAPI +Main_DirectDrawSurface_SetPrivateData(LPDIRECTDRAWSURFACE7 iface, + REFGUID tag, LPVOID pData, + DWORD cbSize, DWORD dwFlags); +HRESULT WINAPI +Main_DirectDrawSurface_Unlock(LPDIRECTDRAWSURFACE7 iface, LPRECT pRect); +HRESULT WINAPI +Main_DirectDrawSurface_UpdateOverlay(LPDIRECTDRAWSURFACE7 iface, + LPRECT pSrcRect, + LPDIRECTDRAWSURFACE7 pDstSurface, + LPRECT pDstRect, DWORD dwFlags, + LPDDOVERLAYFX pFX); +HRESULT WINAPI +Main_DirectDrawSurface_UpdateOverlayDisplay(LPDIRECTDRAWSURFACE7 iface, + DWORD dwFlags); +HRESULT WINAPI +Main_DirectDrawSurface_UpdateOverlayZOrder(LPDIRECTDRAWSURFACE7 iface, + DWORD dwFlags, + LPDIRECTDRAWSURFACE7 pDDSRef); + +#endif diff --git a/dlls/ddraw/dsurface/thunks.c b/dlls/ddraw/dsurface/thunks.c new file mode 100644 index 00000000000..ace0417dd7d --- /dev/null +++ b/dlls/ddraw/dsurface/thunks.c @@ -0,0 +1,401 @@ +/* IDirectDrawSurface3 -> IDirectDrawSurface7 thunks + * Copyright 2000 TransGaming Technologies Inc. + */ + +#include "config.h" +#include "ddraw.h" +#include "winerror.h" + +#include "ddcomimpl.h" +#include "dsurface/main.h" +#include "dsurface/thunks.h" + +#define CONVERT(pdds) COM_INTERFACE_CAST(IDirectDrawSurfaceImpl, \ + IDirectDrawSurface3, \ + IDirectDrawSurface7, \ + (pdds)) + +#define CONVERT_REV(pdds) COM_INTERFACE_CAST(IDirectDrawSurfaceImpl, \ + IDirectDrawSurface7, \ + IDirectDrawSurface3, \ + (pdds)) + +static HRESULT WINAPI +IDirectDrawSurface3Impl_QueryInterface(LPDIRECTDRAWSURFACE3 This, REFIID iid, + LPVOID *ppObj) +{ + return IDirectDrawSurface7_QueryInterface(CONVERT(This), iid, ppObj); +} + +static ULONG WINAPI +IDirectDrawSurface3Impl_AddRef(LPDIRECTDRAWSURFACE3 This) +{ + return IDirectDrawSurface7_AddRef(CONVERT(This)); +} + +static ULONG WINAPI +IDirectDrawSurface3Impl_Release(LPDIRECTDRAWSURFACE3 This) +{ + return IDirectDrawSurface7_Release(CONVERT(This)); +} + +static HRESULT WINAPI +IDirectDrawSurface3Impl_AddAttachedSurface(LPDIRECTDRAWSURFACE3 This, + LPDIRECTDRAWSURFACE3 pAttach) +{ + return IDirectDrawSurface7_AddAttachedSurface(CONVERT(This), + CONVERT(pAttach)); +} + +static HRESULT WINAPI +IDirectDrawSurface3Impl_AddOverlayDirtyRect(LPDIRECTDRAWSURFACE3 This, + LPRECT pRect) +{ + return IDirectDrawSurface7_AddOverlayDirtyRect(CONVERT(This), pRect); +} + +static HRESULT WINAPI +IDirectDrawSurface3Impl_Blt(LPDIRECTDRAWSURFACE3 This, LPRECT prcDst, + LPDIRECTDRAWSURFACE3 pSrcSurf, LPRECT prcSrc, + DWORD dwFlags, LPDDBLTFX pFX) +{ + return IDirectDrawSurface7_Blt(CONVERT(This), prcDst, CONVERT(pSrcSurf), + prcSrc, dwFlags, pFX); +} + +static HRESULT WINAPI +IDirectDrawSurface3Impl_BltBatch(LPDIRECTDRAWSURFACE3 This, + LPDDBLTBATCH pBatch, DWORD dwCount, + DWORD dwFlags) +{ + return IDirectDrawSurface7_BltBatch(CONVERT(This), pBatch, dwCount, + dwFlags); +} + +static HRESULT WINAPI +IDirectDrawSurface3Impl_BltFast(LPDIRECTDRAWSURFACE3 This, DWORD x, DWORD y, + LPDIRECTDRAWSURFACE3 pSrcSurf, LPRECT prcSrc, + DWORD dwTrans) +{ + return IDirectDrawSurface7_BltFast(CONVERT(This), x, y, CONVERT(pSrcSurf), + prcSrc, dwTrans); +} + +static HRESULT WINAPI +IDirectDrawSurface3Impl_DeleteAttachedSurface(LPDIRECTDRAWSURFACE3 This, + DWORD dwFlags, + LPDIRECTDRAWSURFACE3 pAttached) +{ + return IDirectDrawSurface7_DeleteAttachedSurface(CONVERT(This), dwFlags, + CONVERT(pAttached)); +} + +struct callback_info +{ + LPDDENUMSURFACESCALLBACK callback; + LPVOID context; +}; + +static HRESULT CALLBACK +EnumCallback(LPDIRECTDRAWSURFACE7 iface, LPDDSURFACEDESC2 pDDSD, + LPVOID context) +{ + const struct callback_info* info = context; + +#if 0 + /* This is an outgoing conversion so we have to do it. */ + DDSURFACEDESC ddsd; + memset(&ddsd, 0, sizeof(ddsd)); + ddsd.dwSize = sizeof(ddsd); + DDRAW_Convert_DDSURFACEDESC_2_To_1(pDDSD, &ddsd); +#endif + + return info->callback((LPDIRECTDRAWSURFACE)CONVERT_REV(iface), pDDSD, + info->context); +} + +static HRESULT WINAPI +IDirectDrawSurface3Impl_EnumAttachedSurfaces(LPDIRECTDRAWSURFACE3 This, + LPVOID context, + LPDDENUMSURFACESCALLBACK callback) +{ + struct callback_info info = { callback, context }; + return IDirectDrawSurface7_EnumAttachedSurfaces(CONVERT(This), &info, + EnumCallback); +} + +static HRESULT WINAPI +IDirectDrawSurface3Impl_EnumOverlayZOrders(LPDIRECTDRAWSURFACE3 This, + DWORD dwFlags, LPVOID context, + LPDDENUMSURFACESCALLBACK callback) +{ + struct callback_info info = { callback, context }; + return IDirectDrawSurface7_EnumOverlayZOrders(CONVERT(This), dwFlags, + &info, EnumCallback); +} + +static HRESULT WINAPI +IDirectDrawSurface3Impl_Flip(LPDIRECTDRAWSURFACE3 This, + LPDIRECTDRAWSURFACE3 pOverride, DWORD dwFlags) +{ + return IDirectDrawSurface7_Flip(CONVERT(This), CONVERT(pOverride), + dwFlags); +} + +static HRESULT WINAPI +IDirectDrawSurface3Impl_GetAttachedSurface(LPDIRECTDRAWSURFACE3 This, + LPDDSCAPS pCaps, + LPDIRECTDRAWSURFACE3* ppAttached) +{ + DDSCAPS2 caps = { pCaps->dwCaps, 0, 0, 0 }; + LPDIRECTDRAWSURFACE7 pAttached7; + HRESULT hr; + + hr = IDirectDrawSurface7_GetAttachedSurface(CONVERT(This), &caps, + &pAttached7); + if (FAILED(hr)) return hr; + + *ppAttached = CONVERT_REV(pAttached7); + return hr; +} + +static HRESULT WINAPI +IDirectDrawSurface3Impl_GetBltStatus(LPDIRECTDRAWSURFACE3 This, DWORD dwFlags) +{ + return IDirectDrawSurface7_GetBltStatus(CONVERT(This), dwFlags); +} + +static HRESULT WINAPI +IDirectDrawSurface3Impl_GetCaps(LPDIRECTDRAWSURFACE3 This, LPDDSCAPS pCaps) +{ + DDSCAPS2 caps; + HRESULT hr; + + hr = IDirectDrawSurface7_GetCaps(CONVERT(This), &caps); + if (FAILED(hr)) return hr; + + pCaps->dwCaps = caps.dwCaps; + return hr; +} + +static HRESULT WINAPI +IDirectDrawSurface3Impl_GetClipper(LPDIRECTDRAWSURFACE3 This, + LPDIRECTDRAWCLIPPER* ppClipper) +{ + return IDirectDrawSurface7_GetClipper(CONVERT(This), ppClipper); +} + +static HRESULT WINAPI +IDirectDrawSurface3Impl_GetColorKey(LPDIRECTDRAWSURFACE3 This, DWORD dwFlags, + LPDDCOLORKEY pCKey) +{ + return IDirectDrawSurface7_GetColorKey(CONVERT(This), dwFlags, pCKey); +} + +static HRESULT WINAPI +IDirectDrawSurface3Impl_GetDC(LPDIRECTDRAWSURFACE3 This, HDC* phDC) +{ + return IDirectDrawSurface7_GetDC(CONVERT(This), phDC); +} + +static HRESULT WINAPI +IDirectDrawSurface3Impl_GetFlipStatus(LPDIRECTDRAWSURFACE3 This, DWORD dwFlags) +{ + return IDirectDrawSurface7_GetFlipStatus(CONVERT(This), dwFlags); +} + +static HRESULT WINAPI +IDirectDrawSurface3Impl_GetOverlayPosition(LPDIRECTDRAWSURFACE3 This, LPLONG pX, + LPLONG pY) +{ + return IDirectDrawSurface7_GetOverlayPosition(CONVERT(This), pX, pY); +} + +static HRESULT WINAPI +IDirectDrawSurface3Impl_GetPalette(LPDIRECTDRAWSURFACE3 This, + LPDIRECTDRAWPALETTE* ppPalette) +{ + return IDirectDrawSurface7_GetPalette(CONVERT(This), ppPalette); +} + +static HRESULT WINAPI +IDirectDrawSurface3Impl_GetPixelFormat(LPDIRECTDRAWSURFACE3 This, + LPDDPIXELFORMAT pPixelFormat) +{ + return IDirectDrawSurface7_GetPixelFormat(CONVERT(This), pPixelFormat); +} + +static HRESULT WINAPI +IDirectDrawSurface3Impl_GetSurfaceDesc(LPDIRECTDRAWSURFACE3 This, + LPDDSURFACEDESC pDDSD) +{ + return IDirectDrawSurface7_GetSurfaceDesc(CONVERT(This), + (LPDDSURFACEDESC2)pDDSD); +} + +static HRESULT WINAPI +IDirectDrawSurface3Impl_Initialize(LPDIRECTDRAWSURFACE3 This, LPDIRECTDRAW pDD, + LPDDSURFACEDESC pDDSD) +{ + return IDirectDrawSurface7_Initialize(CONVERT(This), pDD, + (LPDDSURFACEDESC2)pDDSD); +} + +static HRESULT WINAPI +IDirectDrawSurface3Impl_IsLost(LPDIRECTDRAWSURFACE3 This) +{ + return IDirectDrawSurface7_IsLost(CONVERT(This)); +} + +static HRESULT WINAPI +IDirectDrawSurface3Impl_Lock(LPDIRECTDRAWSURFACE3 This, LPRECT pRect, + LPDDSURFACEDESC pDDSD, DWORD dwFlags, HANDLE h) +{ + return IDirectDrawSurface7_Lock(CONVERT(This), pRect, + (LPDDSURFACEDESC2)pDDSD, dwFlags, h); +} + +static HRESULT WINAPI +IDirectDrawSurface3Impl_ReleaseDC(LPDIRECTDRAWSURFACE3 This, HDC hDC) +{ + return IDirectDrawSurface7_ReleaseDC(CONVERT(This), hDC); +} + +static HRESULT WINAPI +IDirectDrawSurface3Impl_Restore(LPDIRECTDRAWSURFACE3 This) +{ + return IDirectDrawSurface7_Restore(CONVERT(This)); +} + +static HRESULT WINAPI +IDirectDrawSurface3Impl_SetClipper(LPDIRECTDRAWSURFACE3 This, + LPDIRECTDRAWCLIPPER pClipper) +{ + return IDirectDrawSurface7_SetClipper(CONVERT(This), pClipper); +} + +static HRESULT WINAPI +IDirectDrawSurface3Impl_SetColorKey(LPDIRECTDRAWSURFACE3 This, DWORD dwFlags, + LPDDCOLORKEY pCKey) +{ + return IDirectDrawSurface7_SetColorKey(CONVERT(This), dwFlags, pCKey); +} + +static HRESULT WINAPI +IDirectDrawSurface3Impl_SetOverlayPosition(LPDIRECTDRAWSURFACE3 This, LONG x, + LONG y) +{ + return IDirectDrawSurface7_SetOverlayPosition(CONVERT(This), x, y); +} + +static HRESULT WINAPI +IDirectDrawSurface3Impl_SetPalette(LPDIRECTDRAWSURFACE3 This, + LPDIRECTDRAWPALETTE pPalette) +{ + return IDirectDrawSurface7_SetPalette(CONVERT(This), pPalette); +} + +static HRESULT WINAPI +IDirectDrawSurface3Impl_Unlock(LPDIRECTDRAWSURFACE3 This, LPVOID data) +{ + /* XXX This might be wrong as LPVOID changed to LPRECT along the way. */ + return IDirectDrawSurface7_Unlock(CONVERT(This), data); +} + +static HRESULT WINAPI +IDirectDrawSurface3Impl_UpdateOverlay(LPDIRECTDRAWSURFACE3 This, LPRECT prcSrc, + LPDIRECTDRAWSURFACE3 pDstSurf, + LPRECT prcDst, DWORD dwFlags, + LPDDOVERLAYFX pFX) +{ + return IDirectDrawSurface7_UpdateOverlay(CONVERT(This), prcSrc, + CONVERT(pDstSurf), prcDst, + dwFlags, pFX); +} + +static HRESULT WINAPI +IDirectDrawSurface3Impl_UpdateOverlayDisplay(LPDIRECTDRAWSURFACE3 This, + DWORD dwFlags) +{ + return IDirectDrawSurface7_UpdateOverlayDisplay(CONVERT(This), dwFlags); +} + +static HRESULT WINAPI +IDirectDrawSurface3Impl_UpdateOverlayZOrder(LPDIRECTDRAWSURFACE3 This, + DWORD dwFlags, + LPDIRECTDRAWSURFACE3 pSurfReference) +{ + return IDirectDrawSurface7_UpdateOverlayZOrder(CONVERT(This), dwFlags, + CONVERT(pSurfReference)); +} + +static HRESULT WINAPI +IDirectDrawSurface3Impl_GetDDInterface(LPDIRECTDRAWSURFACE3 This, LPVOID* ppDD) +{ + return IDirectDrawSurface7_GetDDInterface(CONVERT(This), ppDD); +} + +static HRESULT WINAPI +IDirectDrawSurface3Impl_PageLock(LPDIRECTDRAWSURFACE3 This, DWORD dwFlags) +{ + return IDirectDrawSurface7_PageLock(CONVERT(This), dwFlags); +} + +static HRESULT WINAPI +IDirectDrawSurface3Impl_PageUnlock(LPDIRECTDRAWSURFACE3 This, DWORD dwFlags) +{ + return IDirectDrawSurface7_PageUnlock(CONVERT(This), dwFlags); +} + +static HRESULT WINAPI +IDirectDrawSurface3Impl_SetSurfaceDesc(LPDIRECTDRAWSURFACE3 This, + LPDDSURFACEDESC pDDSD, DWORD dwFlags) +{ + return IDirectDrawSurface7_SetSurfaceDesc(CONVERT(This), + (LPDDSURFACEDESC2)pDDSD, + dwFlags); +} + +ICOM_VTABLE(IDirectDrawSurface3) DDRAW_IDDS3_Thunk_VTable = +{ + IDirectDrawSurface3Impl_QueryInterface, + IDirectDrawSurface3Impl_AddRef, + IDirectDrawSurface3Impl_Release, + IDirectDrawSurface3Impl_AddAttachedSurface, + IDirectDrawSurface3Impl_AddOverlayDirtyRect, + IDirectDrawSurface3Impl_Blt, + IDirectDrawSurface3Impl_BltBatch, + IDirectDrawSurface3Impl_BltFast, + IDirectDrawSurface3Impl_DeleteAttachedSurface, + IDirectDrawSurface3Impl_EnumAttachedSurfaces, + IDirectDrawSurface3Impl_EnumOverlayZOrders, + IDirectDrawSurface3Impl_Flip, + IDirectDrawSurface3Impl_GetAttachedSurface, + IDirectDrawSurface3Impl_GetBltStatus, + IDirectDrawSurface3Impl_GetCaps, + IDirectDrawSurface3Impl_GetClipper, + IDirectDrawSurface3Impl_GetColorKey, + IDirectDrawSurface3Impl_GetDC, + IDirectDrawSurface3Impl_GetFlipStatus, + IDirectDrawSurface3Impl_GetOverlayPosition, + IDirectDrawSurface3Impl_GetPalette, + IDirectDrawSurface3Impl_GetPixelFormat, + IDirectDrawSurface3Impl_GetSurfaceDesc, + IDirectDrawSurface3Impl_Initialize, + IDirectDrawSurface3Impl_IsLost, + IDirectDrawSurface3Impl_Lock, + IDirectDrawSurface3Impl_ReleaseDC, + IDirectDrawSurface3Impl_Restore, + IDirectDrawSurface3Impl_SetClipper, + IDirectDrawSurface3Impl_SetColorKey, + IDirectDrawSurface3Impl_SetOverlayPosition, + IDirectDrawSurface3Impl_SetPalette, + IDirectDrawSurface3Impl_Unlock, + IDirectDrawSurface3Impl_UpdateOverlay, + IDirectDrawSurface3Impl_UpdateOverlayDisplay, + IDirectDrawSurface3Impl_UpdateOverlayZOrder, + IDirectDrawSurface3Impl_GetDDInterface, + IDirectDrawSurface3Impl_PageLock, + IDirectDrawSurface3Impl_PageUnlock, + IDirectDrawSurface3Impl_SetSurfaceDesc +}; diff --git a/dlls/ddraw/dsurface/thunks.h b/dlls/ddraw/dsurface/thunks.h new file mode 100644 index 00000000000..989f0a79e3a --- /dev/null +++ b/dlls/ddraw/dsurface/thunks.h @@ -0,0 +1,8 @@ +/* Copyright 2000 TransGaming Technologies Inc. */ + +#ifndef DDRAW_DSURFACE_THUNKS_H_INCLUDED +#define DDRAW_DSURFACE_THUNKS_H_INCLUDED + +extern ICOM_VTABLE(IDirectDrawSurface3) DDRAW_IDDS3_Thunk_VTable; + +#endif diff --git a/dlls/ddraw/dsurface/user.c b/dlls/ddraw/dsurface/user.c new file mode 100644 index 00000000000..8504ffe3d41 --- /dev/null +++ b/dlls/ddraw/dsurface/user.c @@ -0,0 +1,499 @@ +/* User-based primary surface driver + * + * Copyright 2000 TransGaming Technologies Inc. + */ + +#include "config.h" +#include "winerror.h" + +#include +#include + +#include "debugtools.h" +#include "ddraw_private.h" +#include "dsurface/main.h" +#include "dsurface/dib.h" +#include "dsurface/user.h" +#include "dsurface/wndproc.h" + +DEFAULT_DEBUG_CHANNEL(ddraw); + +/* if you use OWN_WINDOW, don't use SYNC_UPDATE, or you may get trouble */ +/* #define SYNC_UPDATE */ +#define OWN_WINDOW + +#ifdef OWN_WINDOW +static void User_create_own_window(IDirectDrawSurfaceImpl* This); +static void User_destroy_own_window(IDirectDrawSurfaceImpl* This); +#endif +#ifndef SYNC_UPDATE +static DWORD CALLBACK User_update_thread(LPVOID); +#endif +static void User_copy_to_screen(IDirectDrawSurfaceImpl* This, LPCRECT rc); +static void User_copy_from_screen(IDirectDrawSurfaceImpl* This, LPCRECT rc); + +static ICOM_VTABLE(IDirectDrawSurface7) User_IDirectDrawSurface7_VTable; + +HRESULT +User_DirectDrawSurface_Construct(IDirectDrawSurfaceImpl* This, + IDirectDrawImpl* pDD, + const DDSURFACEDESC2* pDDSD) +{ + USER_PRIV_VAR(priv, This); + HRESULT hr; + + TRACE("(%p,%p,%p)\n",This,pDD,pDDSD); + hr = DIB_DirectDrawSurface_Construct(This, pDD, pDDSD); + if (FAILED(hr)) return hr; + + ICOM_INIT_INTERFACE(This, IDirectDrawSurface7, + User_IDirectDrawSurface7_VTable); + + This->final_release = User_DirectDrawSurface_final_release; + This->duplicate_surface = User_DirectDrawSurface_duplicate_surface; + + This->lock_update = User_DirectDrawSurface_lock_update; + This->unlock_update = User_DirectDrawSurface_unlock_update; + + This->flip_data = User_DirectDrawSurface_flip_data; + This->flip_update = User_DirectDrawSurface_flip_update; + + This->get_dc = User_DirectDrawSurface_get_dc; + This->release_dc = User_DirectDrawSurface_release_dc; + + This->set_palette = User_DirectDrawSurface_set_palette; + This->update_palette = User_DirectDrawSurface_update_palette; + + This->get_display_window = User_DirectDrawSurface_get_display_window; + + if (This->surface_desc.ddsCaps.dwCaps & DDSCAPS_PRIMARYSURFACE) + { +#ifndef SYNC_UPDATE + priv->user.update_event = CreateEventA(NULL, FALSE, FALSE, NULL); + priv->user.update_thread = CreateThread(NULL, 0, User_update_thread, This, 0, NULL); +#else +#ifdef OWN_WINDOW + User_create_own_window(This); +#endif +#endif + } + + return DIB_DirectDrawSurface_alloc_dc(This, &priv->user.cached_dc); +} + +HRESULT +User_DirectDrawSurface_Create(IDirectDrawImpl *pDD, + const DDSURFACEDESC2 *pDDSD, + LPDIRECTDRAWSURFACE7 *ppSurf, + IUnknown *pUnkOuter) +{ + IDirectDrawSurfaceImpl* This; + HRESULT hr; + assert(pUnkOuter == NULL); + + This = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, + sizeof(*This) + sizeof(User_DirectDrawSurfaceImpl)); + if (This == NULL) return E_OUTOFMEMORY; + + This->private = (User_DirectDrawSurfaceImpl*)(This+1); + + hr = User_DirectDrawSurface_Construct(This, pDD, pDDSD); + if (FAILED(hr)) + HeapFree(GetProcessHeap(), 0, This); + else + *ppSurf = ICOM_INTERFACE(This, IDirectDrawSurface7); + + return hr; +} + +void User_DirectDrawSurface_final_release(IDirectDrawSurfaceImpl* This) +{ + USER_PRIV_VAR(priv, This); + + if (This->surface_desc.ddsCaps.dwCaps & DDSCAPS_PRIMARYSURFACE) + { +#ifndef SYNC_UPDATE + HANDLE event = priv->user.update_event; + priv->user.update_event = 0; + SetEvent(event); + TRACE("waiting for update thread to terminate...\n"); +#ifdef OWN_WINDOW + /* dispatch any waiting sendmessages */ + { + MSG msg; + PeekMessageA(&msg, 0, 0, 0, PM_NOREMOVE); + } + /* to avoid deadlocks, allow SendMessages from update thread + * through while we wait for it */ + while (MsgWaitForMultipleObjects(1, &priv->user.update_thread, FALSE, + INFINITE, QS_SENDMESSAGE) == WAIT_OBJECT_0+1) + { + MSG msg; + PeekMessageA(&msg, 0, 0, 0, PM_NOREMOVE); + } +#else + WaitForSingleObject(priv->user.update_thread,INFINITE); +#endif + TRACE("update thread terminated\n"); + CloseHandle(priv->user.update_thread); +#else +#ifdef OWN_WINDOW + User_destroy_own_window(This); +#endif +#endif + } + DIB_DirectDrawSurface_free_dc(This, priv->user.cached_dc); + DIB_DirectDrawSurface_final_release(This); +} + +void User_DirectDrawSurface_lock_update(IDirectDrawSurfaceImpl* This, + LPCRECT pRect) +{ + User_copy_from_screen(This, pRect); +} + +void User_DirectDrawSurface_unlock_update(IDirectDrawSurfaceImpl* This, + LPCRECT pRect) +{ +#ifdef SYNC_UPDATE + User_copy_to_screen(This, pRect); +#else + USER_PRIV_VAR(priv, This); + SetEvent(priv->user.update_event); +#endif +} + +void User_DirectDrawSurface_set_palette(IDirectDrawSurfaceImpl* This, + IDirectDrawPaletteImpl* pal) +{ + USER_PRIV_VAR(priv, This); + + if (!pal) { + FIXME("selecting null palette\n"); + /* I don't think selecting GDI object 0 will work, we should select + * the original palette, returned by the first SelectPalette */ + SelectPalette(priv->user.cached_dc, 0, FALSE); + return; + } + + SelectPalette(priv->user.cached_dc, pal->hpal, FALSE); + + DIB_DirectDrawSurface_set_palette(This, pal); +} + +void User_DirectDrawSurface_update_palette(IDirectDrawSurfaceImpl* This, + IDirectDrawPaletteImpl* pal, + DWORD dwStart, DWORD dwCount, + LPPALETTEENTRY palent) +{ + USER_PRIV_VAR(priv, This); + + DIB_DirectDrawSurface_update_palette(This, pal, dwStart, dwCount, palent); + /* FIXME: realize palette on display window */ + +#ifndef SYNC_UPDATE + /* with async updates, it's probably cool to force an update */ + SetEvent(priv->user.update_event); +#endif +} + +HRESULT User_DirectDrawSurface_duplicate_surface(IDirectDrawSurfaceImpl* This, + LPDIRECTDRAWSURFACE7* ppDup) +{ + return User_DirectDrawSurface_Create(This->ddraw_owner, + &This->surface_desc, ppDup, NULL); +} + +void User_DirectDrawSurface_flip_data(IDirectDrawSurfaceImpl* front, + IDirectDrawSurfaceImpl* back) +{ + USER_PRIV_VAR(front_priv, front); + USER_PRIV_VAR(back_priv, back); + + { + HDC tmp; + tmp = front_priv->user.cached_dc; + front_priv->user.cached_dc = back_priv->user.cached_dc; + back_priv->user.cached_dc = tmp; + } + + DIB_DirectDrawSurface_flip_data(front, back); +} + +void User_DirectDrawSurface_flip_update(IDirectDrawSurfaceImpl* This) +{ +#ifdef SYNC_UPDATE + assert(This->surface_desc.ddsCaps.dwCaps & DDSCAPS_PRIMARYSURFACE); + User_copy_to_screen(This,NULL); +#else + USER_PRIV_VAR(priv, This); + assert(This->surface_desc.ddsCaps.dwCaps & DDSCAPS_PRIMARYSURFACE); + SetEvent(priv->user.update_event); +#endif +} + +HRESULT User_DirectDrawSurface_get_dc(IDirectDrawSurfaceImpl* This, HDC* phDC) +{ + USER_PRIV_VAR(priv, This); + + *phDC = priv->user.cached_dc; + return S_OK; +} + +HRESULT User_DirectDrawSurface_release_dc(IDirectDrawSurfaceImpl* This, + HDC hDC) +{ + return S_OK; +} + +/* Returns the window that hosts the display. + * *pt is set to the upper left position of the window relative to the + * upper left corner of the surface. */ +static HWND get_display_window(IDirectDrawSurfaceImpl* This, LPPOINT pt) +{ + memset(pt, 0, sizeof(*pt)); + + if (This->ddraw_owner->cooperative_level & DDSCL_FULLSCREEN) + { +#ifdef OWN_WINDOW + USER_PRIV_VAR(priv, This); + SetWindowPos(priv->user.window, HWND_TOP, 0, 0, 0, 0, + SWP_DEFERERASE|SWP_NOACTIVATE|SWP_NOCOPYBITS|SWP_NOMOVE| + SWP_NOREDRAW|SWP_NOSENDCHANGING|SWP_NOSIZE); + return priv->user.window; +#else + return This->ddraw_owner->window; +#endif + } + else + { + if (This->clipper != NULL) + { + /* looks silly, but since we don't have the clipper locked */ + HWND hWnd = This->clipper->hWnd; + + if (hWnd != 0) + { + ClientToScreen(hWnd, pt); + return hWnd; + } + else + { + static BOOL warn = 0; + if (!warn++) FIXME("clipper clip lists not supported\n"); + + return GetDesktopWindow(); + } + } + else + { + static BOOL warn = 0; + if (!warn++) WARN("hosting on root\n"); + + return GetDesktopWindow(); + } + } +} + +HWND User_DirectDrawSurface_get_display_window(IDirectDrawSurfaceImpl* This) +{ + POINT offset; + return get_display_window(This, &offset); +} + +#ifdef OWN_WINDOW +static void User_create_own_window(IDirectDrawSurfaceImpl* This) +{ + USER_PRIV_VAR(priv, This); + + if (This->ddraw_owner->cooperative_level & DDSCL_FULLSCREEN) + { + DirectDrawSurface_RegisterClass(); + priv->user.window = CreateWindowExA(WS_EX_TOPMOST, + "WINE_DDRAW", "DirectDraw", + WS_POPUP, + 0, 0, + This->surface_desc.dwWidth, + This->surface_desc.dwHeight, + GetDesktopWindow(), + 0, 0, This); + SetWindowPos(priv->user.window, HWND_TOP, 0, 0, 0, 0, + SWP_DEFERERASE|SWP_NOACTIVATE|SWP_NOCOPYBITS|SWP_NOMOVE| + SWP_NOREDRAW|SWP_NOSENDCHANGING|SWP_NOSIZE|SWP_SHOWWINDOW); + UpdateWindow(priv->user.window); + } +} + +static void User_destroy_own_window(IDirectDrawSurfaceImpl* This) +{ + USER_PRIV_VAR(priv, This); + + if (This->ddraw_owner->cooperative_level & DDSCL_FULLSCREEN) + { + SetWindowPos(priv->user.window, 0, 0, 0, 0, 0, + SWP_DEFERERASE|SWP_NOACTIVATE|SWP_NOCOPYBITS|SWP_NOMOVE|SWP_NOZORDER| + SWP_NOREDRAW|SWP_NOSENDCHANGING|SWP_NOSIZE|SWP_HIDEWINDOW); + DestroyWindow(priv->user.window); + DirectDrawSurface_UnregisterClass(); + } +} +#endif + +#ifndef SYNC_UPDATE +static DWORD CALLBACK User_update_thread(LPVOID arg) +{ + IDirectDrawSurfaceImpl *This = (IDirectDrawSurfaceImpl *)arg; + USER_PRIV_VAR(priv, This); + volatile DWORD *pActive = (volatile DWORD *)&priv->user.update_event; + HANDLE event = *pActive; + +#ifdef OWN_WINDOW + User_create_own_window(This); +#endif + + /* the point of this is that many games lock the primary surface + * multiple times per frame; this thread will then simply copy as + * often as it can without keeping the main thread waiting for + * each unlock, thus keeping the frame rate high */ + do { +#ifdef OWN_WINDOW + DWORD ret = MsgWaitForMultipleObjects(1, &event, FALSE, INFINITE, QS_ALLINPUT); + MSG msg; + + while (PeekMessageA(&msg, 0, 0, 0, PM_REMOVE)) + { + switch (msg.message) { + case WM_PAINT: + DispatchMessageA(&msg); + break; + default: + /* since we risk getting keyboard messages posted to us, + * repost posted messages to cooperative window */ + PostMessageA(This->ddraw_owner->window, msg.message, msg.wParam, msg.lParam); + } + } +#else + DWORD ret = WaitForSingleObject(event, INFINITE); +#endif + if (ret == WAIT_OBJECT_0) + { + if (*pActive) + User_copy_to_screen(This, NULL); + else + break; + } + else if (ret != WAIT_OBJECT_0+1) break; + } while (TRUE); + +#ifdef OWN_WINDOW + User_destroy_own_window(This); +#endif + + return 0; +} +#endif + +static void User_copy_to_screen(IDirectDrawSurfaceImpl* This, LPCRECT rc) +{ + /* rc is unused. We copy the whole thing. */ + + if (This->surface_desc.ddsCaps.dwCaps & DDSCAPS_PRIMARYSURFACE) + { + POINT offset; + HWND hDisplayWnd; + HDC hDisplayDC; + HDC hSurfaceDC; + + if (FAILED(This->get_dc(This, &hSurfaceDC))) + return; + + hDisplayWnd = get_display_window(This, &offset); + hDisplayDC = GetDCEx(hDisplayWnd, 0, DCX_CLIPSIBLINGS); +#if 0 + /* FIXME: this doesn't work... if users really want to run + * X in 8bpp, then we need to call directly into display.drv + * (or Wine's equivalent), and force a private colormap + * without default entries. */ + if (This->palette) { + SelectPalette(hDisplayDC, This->palette->hpal, FALSE); + RealizePalette(hDisplayDC); /* sends messages => deadlocks */ + } +#endif + + BitBlt(hDisplayDC, 0, 0, This->surface_desc.dwWidth, + This->surface_desc.dwHeight, hSurfaceDC, offset.x, offset.y, + SRCCOPY); + + ReleaseDC(hDisplayWnd, hDisplayDC); + } +} + +static void User_copy_from_screen(IDirectDrawSurfaceImpl* This, LPCRECT rc) +{ + /* rc is unused. We copy the whole thing. */ + + if (This->surface_desc.ddsCaps.dwCaps & DDSCAPS_PRIMARYSURFACE) + { + POINT offset; + HWND hDisplayWnd = get_display_window(This, &offset); + HDC hDisplayDC = GetDC(hDisplayWnd); + + BitBlt(This->hDC, offset.x, offset.y, This->surface_desc.dwWidth, + This->surface_desc.dwHeight, hDisplayDC, 0, 0, SRCCOPY); + + ReleaseDC(hDisplayWnd, hDisplayDC); + } +} + +static ICOM_VTABLE(IDirectDrawSurface7) User_IDirectDrawSurface7_VTable = +{ + Main_DirectDrawSurface_QueryInterface, + Main_DirectDrawSurface_AddRef, + Main_DirectDrawSurface_Release, + Main_DirectDrawSurface_AddAttachedSurface, + Main_DirectDrawSurface_AddOverlayDirtyRect, + DIB_DirectDrawSurface_Blt, + Main_DirectDrawSurface_BltBatch, + DIB_DirectDrawSurface_BltFast, + Main_DirectDrawSurface_DeleteAttachedSurface, + Main_DirectDrawSurface_EnumAttachedSurfaces, + Main_DirectDrawSurface_EnumOverlayZOrders, + Main_DirectDrawSurface_Flip, + Main_DirectDrawSurface_GetAttachedSurface, + Main_DirectDrawSurface_GetBltStatus, + Main_DirectDrawSurface_GetCaps, + Main_DirectDrawSurface_GetClipper, + Main_DirectDrawSurface_GetColorKey, + Main_DirectDrawSurface_GetDC, + Main_DirectDrawSurface_GetFlipStatus, + Main_DirectDrawSurface_GetOverlayPosition, + Main_DirectDrawSurface_GetPalette, + Main_DirectDrawSurface_GetPixelFormat, + Main_DirectDrawSurface_GetSurfaceDesc, + Main_DirectDrawSurface_Initialize, + Main_DirectDrawSurface_IsLost, + Main_DirectDrawSurface_Lock, + Main_DirectDrawSurface_ReleaseDC, + DIB_DirectDrawSurface_Restore, + Main_DirectDrawSurface_SetClipper, + Main_DirectDrawSurface_SetColorKey, + Main_DirectDrawSurface_SetOverlayPosition, + Main_DirectDrawSurface_SetPalette, + Main_DirectDrawSurface_Unlock, + Main_DirectDrawSurface_UpdateOverlay, + Main_DirectDrawSurface_UpdateOverlayDisplay, + Main_DirectDrawSurface_UpdateOverlayZOrder, + Main_DirectDrawSurface_GetDDInterface, + Main_DirectDrawSurface_PageLock, + Main_DirectDrawSurface_PageUnlock, + DIB_DirectDrawSurface_SetSurfaceDesc, + Main_DirectDrawSurface_SetPrivateData, + Main_DirectDrawSurface_GetPrivateData, + Main_DirectDrawSurface_FreePrivateData, + Main_DirectDrawSurface_GetUniquenessValue, + Main_DirectDrawSurface_ChangeUniquenessValue, + Main_DirectDrawSurface_SetPriority, + Main_DirectDrawSurface_GetPriority, + Main_DirectDrawSurface_SetLOD, + Main_DirectDrawSurface_GetLOD +}; diff --git a/dlls/ddraw/dsurface/user.h b/dlls/ddraw/dsurface/user.h new file mode 100644 index 00000000000..c13922d1f06 --- /dev/null +++ b/dlls/ddraw/dsurface/user.h @@ -0,0 +1,58 @@ +/* Copyright 2000 TransGaming Technologies Inc. */ + +#ifndef DDRAW_DSURFACE_USER_H_INCLUDED +#define DDRAW_DSURFACE_USER_H_INCLUDED + +#define USER_PRIV(surf) ((User_DirectDrawSurfaceImpl*)((surf)->private)) + +#define USER_PRIV_VAR(name,surf) \ + User_DirectDrawSurfaceImpl* name = USER_PRIV(surf) + +struct User_DirectDrawSurfaceImpl_Part +{ + HWND window; + HDC cached_dc; + HANDLE update_thread, update_event; +}; + +typedef struct +{ + struct DIB_DirectDrawSurfaceImpl_Part dib; + struct User_DirectDrawSurfaceImpl_Part user; +} User_DirectDrawSurfaceImpl; + +HRESULT +User_DirectDrawSurface_Construct(IDirectDrawSurfaceImpl* This, + IDirectDrawImpl* pDD, + const DDSURFACEDESC2* pDDSD); + +HRESULT +User_DirectDrawSurface_Create(IDirectDrawImpl *pDD, + const DDSURFACEDESC2 *pDDSD, + LPDIRECTDRAWSURFACE7 *ppSurf, + IUnknown *pUnkOuter); + +void User_DirectDrawSurface_final_release(IDirectDrawSurfaceImpl* This); + +void User_DirectDrawSurface_lock_update(IDirectDrawSurfaceImpl* This, + LPCRECT pRect); +void User_DirectDrawSurface_unlock_update(IDirectDrawSurfaceImpl* This, + LPCRECT pRect); +void User_DirectDrawSurface_set_palette(IDirectDrawSurfaceImpl* This, + IDirectDrawPaletteImpl* pal); +void User_DirectDrawSurface_update_palette(IDirectDrawSurfaceImpl* This, + IDirectDrawPaletteImpl* pal, + DWORD dwStart, DWORD dwCount, + LPPALETTEENTRY palent); +HRESULT User_DirectDrawSurface_duplicate_surface(IDirectDrawSurfaceImpl* This, + LPDIRECTDRAWSURFACE7* ppDup); +void User_DirectDrawSurface_flip_data(IDirectDrawSurfaceImpl* front, + IDirectDrawSurfaceImpl* back); +void User_DirectDrawSurface_flip_update(IDirectDrawSurfaceImpl* This); +HWND User_DirectDrawSurface_get_display_window(IDirectDrawSurfaceImpl* This); + +HRESULT User_DirectDrawSurface_get_dc(IDirectDrawSurfaceImpl* This, HDC* phDC); +HRESULT User_DirectDrawSurface_release_dc(IDirectDrawSurfaceImpl* This, + HDC hDC); + +#endif diff --git a/dlls/ddraw/dsurface/wndproc.c b/dlls/ddraw/dsurface/wndproc.c new file mode 100644 index 00000000000..4a3a1b627c6 --- /dev/null +++ b/dlls/ddraw/dsurface/wndproc.c @@ -0,0 +1,85 @@ +/* User-based primary surface driver + * + * Copyright 2000 TransGaming Technologies Inc. + */ + +#include "config.h" +#include "winerror.h" + +#include +#include + +#include "debugtools.h" +#include "ddraw_private.h" + +DEFAULT_DEBUG_CHANNEL(ddraw); + +static LRESULT WINAPI DirectDrawSurface_WndProc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam); + +void DirectDrawSurface_RegisterClass(void) +{ + WNDCLASSA wc; + memset(&wc, 0, sizeof(wc)); + wc.lpfnWndProc = DirectDrawSurface_WndProc; + wc.cbWndExtra = sizeof(IDirectDrawSurfaceImpl*); + wc.hCursor = (HCURSOR)IDC_ARROWA; + wc.lpszClassName = "WINE_DDRAW"; + RegisterClassA(&wc); +} + +void DirectDrawSurface_UnregisterClass(void) +{ + UnregisterClassA("WINE_DDRAW", 0); +} + +static LRESULT WINAPI DirectDrawSurface_WndProc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam) +{ + IDirectDrawSurfaceImpl *This; + LRESULT ret; + + This = (IDirectDrawSurfaceImpl *)GetWindowLongA(hwnd, 0); + if (This) { + HWND window = This->ddraw_owner->window; + + switch (msg) { + case WM_DESTROY: + case WM_NCDESTROY: + case WM_SHOWWINDOW: + case WM_WINDOWPOSCHANGING: + case WM_WINDOWPOSCHANGED: + case WM_SIZE: + case WM_MOVE: + case WM_ERASEBKGND: + /* since we're pretending fullscreen, + * let's not pass these on to the app */ + ret = DefWindowProcA(hwnd, msg, wParam, lParam); + break; + case WM_NCHITTEST: + ret = HTCLIENT; + break; + case WM_MOUSEACTIVATE: + ret = MA_NOACTIVATE; + break; + case WM_PAINT: + { + PAINTSTRUCT ps; + HDC dc = BeginPaint(hwnd, &ps); + /* call User_copy_to_screen? */ + EndPaint(hwnd, &ps); + ret = 0; + } + break; + default: + ret = window ? SendMessageA(window, msg, wParam, lParam) + : DefWindowProcA(hwnd, msg, wParam, lParam); + } + } else { + if (msg == WM_CREATE) { + CREATESTRUCTA *cs = (CREATESTRUCTA *)lParam; + This = (IDirectDrawSurfaceImpl *)cs->lpCreateParams; + SetWindowLongA(hwnd, 0, (LONG)This); + } + ret = DefWindowProcA(hwnd, msg, wParam, lParam); + } + return ret; +} diff --git a/dlls/ddraw/dsurface/wndproc.h b/dlls/ddraw/dsurface/wndproc.h new file mode 100644 index 00000000000..f83548b6e2f --- /dev/null +++ b/dlls/ddraw/dsurface/wndproc.h @@ -0,0 +1,9 @@ +/* Copyright 2000 TransGaming Technologies Inc. */ + +#ifndef DDRAW_DSURFACE_WNDPROC_H_INCLUDED +#define DDRAW_DSURFACE_WNDPROC_H_INCLUDED + +void DirectDrawSurface_RegisterClass(void); +void DirectDrawSurface_UnregisterClass(void); + +#endif diff --git a/dlls/ddraw/dsurface/x11.c b/dlls/ddraw/dsurface/x11.c deleted file mode 100644 index 684b10b6af8..00000000000 --- a/dlls/ddraw/dsurface/x11.c +++ /dev/null @@ -1,723 +0,0 @@ -/* DirectDrawSurface Xlib implementation - * - * Copyright 1997-2000 Marcus Meissner - * Copyright 1998-2000 Lionel Ulmer (most of Direct3D stuff) - */ -#include "config.h" -#include "winerror.h" - -#include -#include -#include -#include -#include -#include - -#include "options.h" -#include "debugtools.h" -#include "x11_private.h" -#include "bitmap.h" -#include "win.h" -#include "d3d.h" - -#ifdef HAVE_OPENGL -/* for d3d texture stuff */ -# include "mesa_private.h" -#endif - -DEFAULT_DEBUG_CHANNEL(ddraw); - -#define VISIBLE(x) (SDDSCAPS(x) & (DDSCAPS_VISIBLE|DDSCAPS_PRIMARYSURFACE)) - -#define DDPRIVATE(x) x11_dd_private *ddpriv = ((x11_dd_private*)(x)->d->private) -#define DPPRIVATE(x) x11_dp_private *dppriv = ((x11_dp_private*)(x)->private) -#define DSPRIVATE(x) x11_ds_private *dspriv = ((x11_ds_private*)(x)->private) - -static BYTE Xlib_TouchData(LPVOID data) -{ - /* this is a function so it doesn't get optimized out */ - return *(BYTE*)data; -} - -/****************************************************************************** - * IDirectDrawSurface methods - * - * Since DDS3 and DDS2 are supersets of DDS, we implement DDS3 and let - * DDS and DDS2 use those functions. (Function calls did not change (except - * using different DirectDrawSurfaceX version), just added flags and functions) - */ -HRESULT WINAPI Xlib_IDirectDrawSurface4Impl_QueryInterface( - LPDIRECTDRAWSURFACE4 iface,REFIID refiid,LPVOID *obj -) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); - - TRACE("(%p)->(%s,%p)\n",This,debugstr_guid(refiid),obj); - - /* All DirectDrawSurface versions (1, 2, 3 and 4) use - * the same interface. And IUnknown does that too of course. - */ - if ( IsEqualGUID( &IID_IDirectDrawSurface4, refiid ) || - IsEqualGUID( &IID_IDirectDrawSurface3, refiid ) || - IsEqualGUID( &IID_IDirectDrawSurface2, refiid ) || - IsEqualGUID( &IID_IDirectDrawSurface, refiid ) || - IsEqualGUID( &IID_IUnknown, refiid ) - ) { - *obj = This; - IDirectDrawSurface4_AddRef(iface); - - TRACE(" Creating IDirectDrawSurface interface (%p)\n", *obj); - return S_OK; - } -#ifdef HAVE_OPENGL - if ( IsEqualGUID( &IID_IDirect3DTexture2, refiid ) ) { - /* Texture interface */ - *obj = d3dtexture2_create(This); - IDirectDrawSurface4_AddRef(iface); - TRACE(" Creating IDirect3DTexture2 interface (%p)\n", *obj); - return S_OK; - } - if ( IsEqualGUID( &IID_IDirect3DTexture, refiid ) ) { - /* Texture interface */ - *obj = d3dtexture_create(This); - IDirectDrawSurface4_AddRef(iface); - TRACE(" Creating IDirect3DTexture interface (%p)\n", *obj); - return S_OK; - } -#else - if ( IsEqualGUID( &IID_IDirect3DTexture2, refiid ) || - IsEqualGUID( &IID_IDirect3DTexture, refiid ) - ) - { - ERR( "Cannot provide 3D support without OpenGL/Mesa installed\n" ); - } -#endif /* HAVE_OPENGL */ - FIXME("(%p):interface for IID %s NOT found!\n",This,debugstr_guid(refiid)); - return OLE_E_ENUM_NOMORE; -} - -HRESULT WINAPI Xlib_IDirectDrawSurface4Impl_Lock( - LPDIRECTDRAWSURFACE4 iface,LPRECT lprect,LPDDSURFACEDESC lpddsd,DWORD flags, HANDLE hnd -) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); - DSPRIVATE(This); - DDPRIVATE(This->s.ddraw); - - /* DO NOT AddRef the surface! Lock/Unlock are NOT guaranteed to come in - * matched pairs! - Marcus Meissner 20000509 */ - TRACE("(%p)->Lock(%p,%p,%08lx,%08lx) ret=%p\n",This,lprect,lpddsd,flags,(DWORD)hnd,__builtin_return_address(0)); - if (flags & ~(DDLOCK_WAIT|DDLOCK_READONLY|DDLOCK_WRITEONLY)) - WARN("(%p)->Lock(%p,%p,%08lx,%08lx)\n", - This,lprect,lpddsd,flags,(DWORD)hnd); - - /* First, copy the Surface description */ - *lpddsd = This->s.surface_desc; - TRACE("locked surface: height=%ld, width=%ld, pitch=%ld\n", - lpddsd->dwHeight,lpddsd->dwWidth,lpddsd->lPitch); - - /* If asked only for a part, change the surface pointer */ - if (lprect) { - TRACE(" lprect: %dx%d-%dx%d\n", - lprect->top,lprect->left,lprect->bottom,lprect->right - ); - if ((lprect->top < 0) || - (lprect->left < 0) || - (lprect->bottom < 0) || - (lprect->right < 0)) { - ERR(" Negative values in LPRECT !!!\n"); - return DDERR_INVALIDPARAMS; - } - lpddsd->u1.lpSurface=(LPVOID)((char*)This->s.surface_desc.u1.lpSurface+ - (lprect->top*This->s.surface_desc.lPitch) + - lprect->left*GET_BPP(This->s.surface_desc)); - } else - assert(This->s.surface_desc.u1.lpSurface); - /* wait for any previous operations to complete */ -#ifdef HAVE_LIBXXSHM - if (dspriv->info.image && VISIBLE(This) && ddpriv->xshm_active) { -/* - int compl = InterlockedExchange( &(ddpriv->xshm_compl), 0 ); - if (compl) X11DRV_EVENT_WaitShmCompletion( compl ); -*/ - X11DRV_EVENT_WaitShmCompletions( ddpriv->drawable ); - } -#endif - - /* If part of a visible 'clipped' surface, copy what is seen on the - screen to the surface */ - if ((dspriv->info.image && VISIBLE(This)) && - (This->s.lpClipper)) { - HWND hWnd = ((IDirectDrawClipperImpl *) This->s.lpClipper)->hWnd; - WND *wndPtr = WIN_FindWndPtr(hWnd); - Drawable drawable = X11DRV_WND_GetXWindow(wndPtr); - int width = wndPtr->rectClient.right - wndPtr->rectClient.left; - int height = wndPtr->rectClient.bottom - wndPtr->rectClient.top; - /* Now, get the source / destination coordinates */ - int dest_x = wndPtr->rectClient.left; - int dest_y = wndPtr->rectClient.top; - - if (!drawable) { /* we are running in -desktop mode */ - drawable = X11DRV_WND_GetXWindow(WIN_GetDesktop()); - /* FIXME: not sure whether these are the right offsets */ - dest_x+=wndPtr->rectWindow.left; - dest_y+=wndPtr->rectWindow.top; - WIN_ReleaseDesktop(); - } - - TSXGetSubImage(display, drawable, 0, 0, width, height, 0xFFFFFFFF, - ZPixmap, dspriv->info.image, dest_x, dest_y); - - WIN_ReleaseWndPtr(wndPtr); - } - - return DD_OK; -} - -static void Xlib_copy_surface_on_screen(IDirectDrawSurface4Impl* This) { - DSPRIVATE(This); - DDPRIVATE(This->s.ddraw); - Drawable drawable = ddpriv->drawable; - POINT adjust[2] = {{0, 0}, {0, 0}}; - SIZE imgsiz; - - /* Get XImage size */ - imgsiz.cx = dspriv->info.image->width; - imgsiz.cy = dspriv->info.image->height; - - if (This->s.lpClipper) { - HWND hWnd = ((IDirectDrawClipperImpl *) This->s.lpClipper)->hWnd; - SIZE csiz; - WND *wndPtr = WIN_FindWndPtr(hWnd); - drawable = X11DRV_WND_GetXWindow(wndPtr); - - MapWindowPoints(hWnd, 0, adjust, 2); - - imgsiz.cx -= adjust[0].x; - imgsiz.cy -= adjust[0].y; - /* (note: the rectWindow here should be the X window's interior rect, in - * case anyone thinks otherwise while rewriting managed mode) */ - adjust[1].x -= wndPtr->rectWindow.left; - adjust[1].y -= wndPtr->rectWindow.top; - csiz.cx = wndPtr->rectClient.right - wndPtr->rectClient.left; - csiz.cy = wndPtr->rectClient.bottom - wndPtr->rectClient.top; - if (csiz.cx < imgsiz.cx) imgsiz.cx = csiz.cx; - if (csiz.cy < imgsiz.cy) imgsiz.cy = csiz.cy; - - TRACE("adjust: hwnd=%08x, surface %ldx%ld, drawable %ldx%ld\n", hWnd, - adjust[0].x, adjust[0].y, - adjust[1].x,adjust[1].y); - - WIN_ReleaseWndPtr(wndPtr); - } - - if (!drawable) { - WND *tmpWnd = WIN_FindWndPtr(This->s.ddraw->d->window); - drawable = X11DRV_WND_GetXWindow(tmpWnd); - WIN_ReleaseWndPtr(tmpWnd); - - /* We don't have a context for this window. Host off the desktop */ - if( !drawable ) { - FIXME("Have to use Desktop Root Window??? Bummer.\n"); - drawable = X11DRV_WND_GetXWindow(WIN_GetDesktop()); - WIN_ReleaseDesktop(); - } - ddpriv->drawable = drawable; - } - - if (This->s.ddraw->d->pixel_convert != NULL) - This->s.ddraw->d->pixel_convert(This->s.surface_desc.u1.lpSurface, - dspriv->info.image->data, - This->s.surface_desc.dwWidth, - This->s.surface_desc.dwHeight, - This->s.surface_desc.lPitch, - This->s.palette); - - /* if the DIB section is in GdiMod state, we must - * touch the surface to get any updates from the DIB */ - Xlib_TouchData(dspriv->info.image->data); -#ifdef HAVE_LIBXXSHM - if (ddpriv->xshm_active) { -/* - X11DRV_EVENT_WaitReplaceShmCompletion( &(ddpriv->xshm_compl), This->s.ddraw->d.drawable ); -*/ - /* let WaitShmCompletions track 'em for now */ - /* (you may want to track it again whenever you implement DX7's partial - * surface locking, where threads have concurrent access) */ - X11DRV_EVENT_PrepareShmCompletion( ddpriv->drawable ); - TSXShmPutImage(display, - drawable, - DefaultGCOfScreen(X11DRV_GetXScreen()), - dspriv->info.image, - adjust[0].x, adjust[0].y, adjust[1].x, adjust[1].y, - imgsiz.cx, imgsiz.cy, - True - ); - /* make sure the image is transferred ASAP */ - TSXFlush(display); - } else -#endif - TSXPutImage(display, - drawable, - DefaultGCOfScreen(X11DRV_GetXScreen()), - dspriv->info.image, - adjust[0].x, adjust[0].y, adjust[1].x, adjust[1].y, - imgsiz.cx, imgsiz.cy - ); -} - -#ifdef HAVE_XVIDEO -static void Xlib_copy_overlay_on_screen(IDirectDrawSurface4Impl* This) { - DSPRIVATE(This); - DDPRIVATE(This->s.ddraw); - Drawable drawable = ddpriv->drawable; - - if (!drawable) { - WND *tmpWnd = WIN_FindWndPtr(This->s.ddraw->d->window); - drawable = X11DRV_WND_GetXWindow(tmpWnd); - WIN_ReleaseWndPtr(tmpWnd); - - /* We don't have a context for this window. Host off the desktop */ - if( !drawable ) { - FIXME("Have to use Desktop Root Window??? Bummer.\n"); - drawable = X11DRV_WND_GetXWindow(WIN_GetDesktop()); - WIN_ReleaseDesktop(); - } - ddpriv->drawable = drawable; - } - -#ifdef HAVE_LIBXXSHM - if (ddpriv->xshm_active) { - /* let WaitShmCompletions track 'em for now */ - /* (you may want to track it again whenever you implement DX7's partial - * surface locking, where threads have concurrent access) */ - X11DRV_EVENT_PrepareShmCompletion( ddpriv->drawable ); - TSXvShmPutImage(display, ddpriv->port_id, drawable, DefaultGCOfScreen(X11DRV_GetXScreen()), - dspriv->info.overlay.image, - dspriv->info.overlay.src_rect.left, dspriv->info.overlay.src_rect.top, - dspriv->info.overlay.src_rect.right - dspriv->info.overlay.src_rect.left, - dspriv->info.overlay.src_rect.bottom - dspriv->info.overlay.src_rect.top, - dspriv->info.overlay.dst_rect.left, dspriv->info.overlay.dst_rect.top, - dspriv->info.overlay.dst_rect.right - dspriv->info.overlay.dst_rect.left, - dspriv->info.overlay.dst_rect.bottom - dspriv->info.overlay.dst_rect.top, - True); - /* make sure the image is transferred ASAP */ - TSXFlush(display); - } else -#endif - TSXvPutImage(display, ddpriv->port_id, drawable, DefaultGCOfScreen(X11DRV_GetXScreen()), - dspriv->info.overlay.image, - dspriv->info.overlay.src_rect.left, dspriv->info.overlay.src_rect.top, - dspriv->info.overlay.src_rect.right - dspriv->info.overlay.src_rect.left, - dspriv->info.overlay.src_rect.bottom - dspriv->info.overlay.src_rect.top, - dspriv->info.overlay.dst_rect.left, dspriv->info.overlay.dst_rect.top, - dspriv->info.overlay.dst_rect.right - dspriv->info.overlay.dst_rect.left, - dspriv->info.overlay.dst_rect.bottom - dspriv->info.overlay.dst_rect.top); -} -#endif - -HRESULT WINAPI Xlib_IDirectDrawSurface4Impl_Unlock( - LPDIRECTDRAWSURFACE4 iface,LPVOID surface -) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); - DDPRIVATE(This->s.ddraw); - DSPRIVATE(This); - TRACE("(%p)->Unlock(%p)\n",This,surface); - - /*if (!This->s.ddraw->d.paintable) - return DD_OK; */ - - /* Only redraw the screen when unlocking the buffer that is on screen */ - if (dspriv->info.image && VISIBLE(This)) { - Xlib_copy_surface_on_screen(This); - if (This->s.palette) { - DPPRIVATE(This->s.palette); - if(dppriv->cm) - TSXSetWindowColormap(display,ddpriv->drawable,dppriv->cm); - } - } else if (dspriv->is_overlay) { - /* Case of an overlay surface */ -#ifdef HAVE_XVIDEO - if (dspriv->info.overlay.shown) - Xlib_copy_overlay_on_screen(This); -#else - ERR("Why was this code activated WITHOUT XVideo support ?\n"); -#endif - } - /* DO NOT Release the surface! Lock/Unlock are NOT guaranteed to come in - * matched pairs! - Marcus Meissner 20000509 */ - return DD_OK; -} - -HRESULT WINAPI Xlib_IDirectDrawSurface4Impl_Flip( - LPDIRECTDRAWSURFACE4 iface,LPDIRECTDRAWSURFACE4 flipto,DWORD dwFlags -) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); - XImage *image; - DDPRIVATE(This->s.ddraw); - DSPRIVATE(This); - x11_ds_private *fspriv; - LPBYTE surf; - IDirectDrawSurface4Impl* iflipto=(IDirectDrawSurface4Impl*)flipto; - - TRACE("(%p)->Flip(%p,%08lx)\n",This,iflipto,dwFlags); - if ((!This->s.ddraw->d->paintable) && (dspriv->is_overlay == FALSE)) - return DD_OK; - - iflipto = _common_find_flipto(This,iflipto); - fspriv = (x11_ds_private*)iflipto->private; - - /* We need to switch the lowlevel surfaces, for xlib this is: */ - /* The surface pointer */ - surf = This->s.surface_desc.u1.lpSurface; - This->s.surface_desc.u1.lpSurface = iflipto->s.surface_desc.u1.lpSurface; - iflipto->s.surface_desc.u1.lpSurface = surf; - - /* the associated ximage - - NOTE : for XVideo, the pointer to the XvImage is at the same position - in memory than the standard XImage. This means that this code - still works :-) - */ - image = dspriv->info.image; - dspriv->info.image = fspriv->info.image; - fspriv->info.image = image; - - if (dspriv->opengl_flip) { -#ifdef HAVE_OPENGL - ENTER_GL(); - glXSwapBuffers(display, ddpriv->drawable); - LEAVE_GL(); -#endif - } else if (dspriv->is_overlay) { -#ifdef HAVE_XVIDEO - if (dspriv->info.overlay.shown) - Xlib_copy_overlay_on_screen(This); -#else - ERR("Why was this code activated WITHOUT XVideo support ?\n"); -#endif - } else { -#ifdef HAVE_LIBXXSHM - if (ddpriv->xshm_active) { - /* - int compl = InterlockedExchange( &(ddpriv->xshm_compl), 0 ); - if (compl) X11DRV_EVENT_WaitShmCompletion( compl ); - */ - X11DRV_EVENT_WaitShmCompletions( ddpriv->drawable ); - } -#endif - Xlib_copy_surface_on_screen(This); - if (iflipto->s.palette) { - DPPRIVATE(iflipto->s.palette); - if (dppriv->cm) - TSXSetWindowColormap(display,ddpriv->drawable,dppriv->cm); - } - } - return DD_OK; -} - -/* The IDirectDrawSurface4::SetPalette method attaches the specified - * DirectDrawPalette object to a surface. The surface uses this palette for all - * subsequent operations. The palette change takes place immediately. - */ -HRESULT WINAPI Xlib_IDirectDrawSurface4Impl_SetPalette( - LPDIRECTDRAWSURFACE4 iface,LPDIRECTDRAWPALETTE pal -) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); - DDPRIVATE(This->s.ddraw); - IDirectDrawPaletteImpl* ipal=(IDirectDrawPaletteImpl*)pal; - x11_dp_private *dppriv; - int i; - - TRACE("(%p)->(%p)\n",This,ipal); - - if (ipal == NULL) { - if( This->s.palette != NULL ) - IDirectDrawPalette_Release((IDirectDrawPalette*)This->s.palette); - This->s.palette = ipal; - return DD_OK; - } - dppriv = (x11_dp_private*)ipal->private; - - if (!dppriv->cm && - (This->s.ddraw->d->screen_pixelformat.u.dwRGBBitCount<=8) - ) { - dppriv->cm = TSXCreateColormap( - display, - ddpriv->drawable, - DefaultVisualOfScreen(X11DRV_GetXScreen()), - AllocAll - ); - if (!Options.managed) - TSXInstallColormap(display,dppriv->cm); - - for (i=0;i<256;i++) { - XColor xc; - - xc.red = ipal->palents[i].peRed<<8; - xc.blue = ipal->palents[i].peBlue<<8; - xc.green = ipal->palents[i].peGreen<<8; - xc.flags = DoRed|DoBlue|DoGreen; - xc.pixel = i; - TSXStoreColor(display,dppriv->cm,&xc); - } - TSXInstallColormap(display,dppriv->cm); - } - /* According to spec, we are only supposed to - * AddRef if this is not the same palette. - */ - if ( This->s.palette != ipal ) { - if( ipal != NULL ) - IDirectDrawPalette_AddRef( (IDirectDrawPalette*)ipal ); - if( This->s.palette != NULL ) - IDirectDrawPalette_Release( (IDirectDrawPalette*)This->s.palette ); - This->s.palette = ipal; - /* Perform the refresh, only if a palette was created */ - if (dppriv->cm) - TSXSetWindowColormap(display,ddpriv->drawable,dppriv->cm); - - if (This->s.hdc != 0) { - /* hack: set the DIBsection color map */ - BITMAPOBJ *bmp = (BITMAPOBJ *) GDI_GetObjPtr(This->s.DIBsection, BITMAP_MAGIC); - X11DRV_DIBSECTION *dib = (X11DRV_DIBSECTION *)bmp->dib; - dib->colorMap = This->s.palette ? This->s.palette->screen_palents : NULL; - GDI_ReleaseObj(This->s.DIBsection); - } - } - return DD_OK; -} - -ULONG WINAPI Xlib_IDirectDrawSurface4Impl_Release(LPDIRECTDRAWSURFACE4 iface) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); - DSPRIVATE(This); - DDPRIVATE(This->s.ddraw); - - TRACE( "(%p)->() decrementing from %lu.\n", This, This->ref ); - if (--(This->ref)) - return This->ref; - - IDirectDraw2_Release((IDirectDraw2*)This->s.ddraw); - - /* This frees the program-side surface. In some cases it had been - * allocated with MEM_SYSTEM, so it does not get 'really' freed - */ - VirtualFree(This->s.surface_desc.u1.lpSurface, 0, MEM_RELEASE); - - /* Now free the XImages and the respective screen-side surfaces */ - if (dspriv->info.image != NULL) { - if (dspriv->info.image->data != This->s.surface_desc.u1.lpSurface) - VirtualFree(dspriv->info.image->data, 0, MEM_RELEASE); -#ifdef HAVE_LIBXXSHM - if (ddpriv->xshm_active) { - TSXShmDetach(display, &(dspriv->shminfo)); - if (This->s.surface_desc.ddsCaps.dwCaps & DDSCAPS_OVERLAY) { - TSXFree(dspriv->info.image); - } else { - TSXDestroyImage(dspriv->info.image); - } - shmdt(dspriv->shminfo.shmaddr); - } else -#endif - { - if (This->s.surface_desc.ddsCaps.dwCaps & DDSCAPS_OVERLAY) { - TSXFree(dspriv->info.image); - } else { - /* normal X Image memory was never allocated by X, but always by - * ourselves -> Don't let X free our imagedata. - */ - dspriv->info.image->data = NULL; - TSXDestroyImage(dspriv->info.image); - } - } - dspriv->info.image = 0; - } - - if (This->s.palette) - IDirectDrawPalette_Release((IDirectDrawPalette*)This->s.palette); - - /* Free the DIBSection (if any) */ - if (This->s.hdc != 0) { - /* hack: restore the original DIBsection color map */ - BITMAPOBJ *bmp = (BITMAPOBJ *) GDI_GetObjPtr(This->s.DIBsection, BITMAP_MAGIC); - X11DRV_DIBSECTION *dib = (X11DRV_DIBSECTION *)bmp->dib; - dib->colorMap = dspriv->oldDIBmap; - GDI_ReleaseObj(This->s.DIBsection); - - SelectObject(This->s.hdc, This->s.holdbitmap); - DeleteDC(This->s.hdc); - DeleteObject(This->s.DIBsection); - } - - /* Free the clipper if present */ - if(This->s.lpClipper) - IDirectDrawClipper_Release(This->s.lpClipper); - HeapFree(GetProcessHeap(),0,This->private); - HeapFree(GetProcessHeap(),0,This); - return S_OK; -} - -HRESULT WINAPI Xlib_IDirectDrawSurface4Impl_GetDC(LPDIRECTDRAWSURFACE4 iface,HDC* lphdc) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); - DSPRIVATE(This); - int was_ok = This->s.hdc != 0; - HRESULT result = IDirectDrawSurface4Impl_GetDC(iface,lphdc); - if (This->s.hdc && !was_ok) { - /* hack: take over the DIBsection color map */ - BITMAPOBJ *bmp = (BITMAPOBJ *) GDI_GetObjPtr(This->s.DIBsection, BITMAP_MAGIC); - X11DRV_DIBSECTION *dib = (X11DRV_DIBSECTION *)bmp->dib; - dspriv->oldDIBmap = dib->colorMap; - dib->colorMap = This->s.palette ? This->s.palette->screen_palents : NULL; - GDI_ReleaseObj(This->s.DIBsection); - } - return result; -} - -#ifdef HAVE_XVIDEO -typedef struct { - BOOL shown; - LPRECT src_rect; - LPRECT dst_rect; - LPDIRECTDRAWSURFACE dest_surface; -} UpdateOverlayEnumerate; - -static HRESULT WINAPI enum_func(LPDIRECTDRAWSURFACE lpDDSurface, - LPDDSURFACEDESC lpDDSurfaceDesc, - LPVOID lpContext) { - ICOM_THIS(IDirectDrawSurface4Impl,lpDDSurface); - DSPRIVATE(This); - UpdateOverlayEnumerate *ctx = (UpdateOverlayEnumerate *) lpContext; - - if ((lpDDSurfaceDesc->ddsCaps.dwCaps) & DDSCAPS_BACKBUFFER) { - TRACE("Upgrading surface %p\n", lpDDSurface); - - if (ctx->shown) { - dspriv->info.overlay.shown = TRUE; - dspriv->info.overlay.src_rect = *(ctx->src_rect); - dspriv->info.overlay.dst_rect = *(ctx->dst_rect); - dspriv->info.overlay.dest_surface = ctx->dest_surface; - } else { - dspriv->info.overlay.shown = FALSE; - } - } - - return DDENUMRET_OK; -} -#endif - -HRESULT WINAPI Xlib_IDirectDrawSurface4Impl_UpdateOverlay( - LPDIRECTDRAWSURFACE4 iface, LPRECT lpSrcRect, - LPDIRECTDRAWSURFACE4 lpDDDestSurface, LPRECT lpDestRect, DWORD dwFlags, - LPDDOVERLAYFX lpDDOverlayFx -) { - ICOM_THIS(IDirectDrawSurface4Impl,iface); -#ifdef HAVE_XVIDEO - DSPRIVATE(This); - DDPRIVATE(This->s.ddraw); - - if (ddpriv->xvideo_active) { - TRACE("(%p)->(%p,%p,%p,0x%08lx,%p)\n", This, - lpSrcRect, lpDDDestSurface, lpDestRect, dwFlags, lpDDOverlayFx ); - - if (TRACE_ON(ddraw)) { - DPRINTF(" - dwFlags : "); - _dump_DDOVERLAY(dwFlags); - - if (lpSrcRect) DPRINTF(" - src rectangle :%dx%d-%dx%d\n",lpSrcRect->left,lpSrcRect->top, - lpSrcRect->right,lpSrcRect->bottom); - if (lpDestRect) DPRINTF(" - dest rectangle :%dx%d-%dx%d\n",lpDestRect->left,lpDestRect->top, - lpDestRect->right,lpDestRect->bottom); - } - - if (dwFlags & DDOVER_SHOW) { - UpdateOverlayEnumerate ctx; - - dwFlags &= ~DDOVER_SHOW; - - if ((lpSrcRect == NULL) || (lpDestRect == NULL)) { - FIXME("This is NOT supported yet...\n"); - return DD_OK; - } - - /* Set the shown BOOL to TRUE and update the rectangles */ - dspriv->info.overlay.shown = TRUE; - dspriv->info.overlay.src_rect = *lpSrcRect; - dspriv->info.overlay.dst_rect = *lpDestRect; - dspriv->info.overlay.dest_surface = (LPDIRECTDRAWSURFACE) lpDDDestSurface; - - /* Now the same for the backbuffers, except that they are NOT shown */ - ctx.shown = FALSE; - ctx.src_rect = lpSrcRect; - ctx.dst_rect = lpDestRect; - ctx.dest_surface = (LPDIRECTDRAWSURFACE) lpDDDestSurface; - - IDirectDrawSurface4Impl_EnumAttachedSurfaces(iface, &ctx, enum_func); - } else if (dwFlags & DDOVER_HIDE) { - UpdateOverlayEnumerate ctx; - - dwFlags &= ~DDOVER_HIDE; - - /* Set the shown BOOL to FALSE for all overlays */ - dspriv->info.overlay.shown = FALSE; - ctx.shown = FALSE; - IDirectDrawSurface4Impl_EnumAttachedSurfaces(iface, &ctx, enum_func); - } - - if (dwFlags && TRACE_ON(ddraw)) { - WARN("Unsupported flags : "); - _dump_DDOVERLAY(dwFlags); - } - } else -#endif - FIXME("(%p)->(%p,%p,%p,0x%08lx,%p) not supported without XVideo !\n", This, - lpSrcRect, lpDDDestSurface, lpDestRect, dwFlags, lpDDOverlayFx ); - - return DD_OK; -} - -ICOM_VTABLE(IDirectDrawSurface4) xlib_dds4vt = -{ - ICOM_MSVTABLE_COMPAT_DummyRTTIVALUE - Xlib_IDirectDrawSurface4Impl_QueryInterface, - IDirectDrawSurface4Impl_AddRef, - Xlib_IDirectDrawSurface4Impl_Release, - IDirectDrawSurface4Impl_AddAttachedSurface, - IDirectDrawSurface4Impl_AddOverlayDirtyRect, - IDirectDrawSurface4Impl_Blt, - IDirectDrawSurface4Impl_BltBatch, - IDirectDrawSurface4Impl_BltFast, - IDirectDrawSurface4Impl_DeleteAttachedSurface, - IDirectDrawSurface4Impl_EnumAttachedSurfaces, - IDirectDrawSurface4Impl_EnumOverlayZOrders, - Xlib_IDirectDrawSurface4Impl_Flip, - IDirectDrawSurface4Impl_GetAttachedSurface, - IDirectDrawSurface4Impl_GetBltStatus, - IDirectDrawSurface4Impl_GetCaps, - IDirectDrawSurface4Impl_GetClipper, - IDirectDrawSurface4Impl_GetColorKey, - Xlib_IDirectDrawSurface4Impl_GetDC, - IDirectDrawSurface4Impl_GetFlipStatus, - IDirectDrawSurface4Impl_GetOverlayPosition, - IDirectDrawSurface4Impl_GetPalette, - IDirectDrawSurface4Impl_GetPixelFormat, - IDirectDrawSurface4Impl_GetSurfaceDesc, - IDirectDrawSurface4Impl_Initialize, - IDirectDrawSurface4Impl_IsLost, - Xlib_IDirectDrawSurface4Impl_Lock, - IDirectDrawSurface4Impl_ReleaseDC, - IDirectDrawSurface4Impl_Restore, - IDirectDrawSurface4Impl_SetClipper, - IDirectDrawSurface4Impl_SetColorKey, - IDirectDrawSurface4Impl_SetOverlayPosition, - Xlib_IDirectDrawSurface4Impl_SetPalette, - Xlib_IDirectDrawSurface4Impl_Unlock, - Xlib_IDirectDrawSurface4Impl_UpdateOverlay, - IDirectDrawSurface4Impl_UpdateOverlayDisplay, - IDirectDrawSurface4Impl_UpdateOverlayZOrder, - IDirectDrawSurface4Impl_GetDDInterface, - IDirectDrawSurface4Impl_PageLock, - IDirectDrawSurface4Impl_PageUnlock, - IDirectDrawSurface4Impl_SetSurfaceDesc, - IDirectDrawSurface4Impl_SetPrivateData, - IDirectDrawSurface4Impl_GetPrivateData, - IDirectDrawSurface4Impl_FreePrivateData, - IDirectDrawSurface4Impl_GetUniquenessValue, - IDirectDrawSurface4Impl_ChangeUniquenessValue -}; diff --git a/dlls/ddraw/helper.c b/dlls/ddraw/helper.c index b7fc84e4e72..52f984b9802 100644 --- a/dlls/ddraw/helper.c +++ b/dlls/ddraw/helper.c @@ -3,16 +3,12 @@ * * Copyright 1997-1999 Marcus Meissner * Copyright 1998 Lionel Ulmer (most of Direct3D stuff) + * Copyright 2000 TransGaming Technologies Inc. */ #include "config.h" -#include -#include -#include -#include -#include -#include +#include #include "winerror.h" #include "heap.h" @@ -27,232 +23,205 @@ DEFAULT_DEBUG_CHANNEL(ddraw); /****************************************************************************** * debug output functions */ -void _dump_DDBLTFX(DWORD flagmask) { +typedef struct +{ + DWORD val; + const char* name; +} flag_info; + +#define FE(x) { x, #x } + +typedef struct +{ + DWORD val; + const char* name; + void (*func)(const void *); + ptrdiff_t offset; +} member_info; + +#define ME(x,f,e) { x, #x, (void (*)(const void *))(f), offsetof(STRUCT, e) } + +static void DDRAW_dump_flags(DWORD flags, const flag_info* names, + size_t num_names) +{ int i; - const struct { - DWORD mask; - char *name; - } flags[] = { -#define FE(x) { x, #x}, - FE(DDBLTFX_ARITHSTRETCHY) - FE(DDBLTFX_MIRRORLEFTRIGHT) - FE(DDBLTFX_MIRRORUPDOWN) - FE(DDBLTFX_NOTEARING) - FE(DDBLTFX_ROTATE180) - FE(DDBLTFX_ROTATE270) - FE(DDBLTFX_ROTATE90) - FE(DDBLTFX_ZBUFFERRANGE) - FE(DDBLTFX_ZBUFFERBASEDEST) -#undef FE - }; - for (i=0;idwCaps, flags, sizeof(flags)/sizeof(flags[0])); } -void _dump_paletteformat(DWORD dwFlags) { - int i; - const struct { - DWORD mask; - char *name; - } flags[] = { -#define FE(x) { x, #x}, - FE(DDPCAPS_4BIT) - FE(DDPCAPS_8BITENTRIES) - FE(DDPCAPS_8BIT) - FE(DDPCAPS_INITIALIZE) - FE(DDPCAPS_PRIMARYSURFACE) - FE(DDPCAPS_PRIMARYSURFACELEFT) - FE(DDPCAPS_ALLOW256) - FE(DDPCAPS_VSYNC) - FE(DDPCAPS_1BIT) - FE(DDPCAPS_2BIT) - FE(DDPCAPS_ALPHA) -#undef FE +void DDRAW_dump_pixelformat_flag(DWORD flagmask) +{ + static const flag_info flags[] = + { + FE(DDPF_ALPHAPIXELS), + FE(DDPF_ALPHA), + FE(DDPF_FOURCC), + FE(DDPF_PALETTEINDEXED4), + FE(DDPF_PALETTEINDEXEDTO8), + FE(DDPF_PALETTEINDEXED8), + FE(DDPF_RGB), + FE(DDPF_COMPRESSED), + FE(DDPF_RGBTOYUV), + FE(DDPF_YUV), + FE(DDPF_ZBUFFER), + FE(DDPF_PALETTEINDEXED1), + FE(DDPF_PALETTEINDEXED2), + FE(DDPF_ZPIXELS) }; - for (i=0;idwFlags); + DDRAW_dump_pixelformat_flag(pf->dwFlags); if (pf->dwFlags & DDPF_FOURCC) { DPRINTF(", dwFourCC code '%c%c%c%c' (0x%08lx) - %ld bits per pixel", (unsigned char)( pf->dwFourCC &0xff), @@ -260,13 +229,13 @@ void _dump_pixelformat(void *in) { (unsigned char)((pf->dwFourCC>>16)&0xff), (unsigned char)((pf->dwFourCC>>24)&0xff), pf->dwFourCC, - pf->u.dwYUVBitCount + pf->u1.dwYUVBitCount ); } if (pf->dwFlags & DDPF_RGB) { char *cmd; - DPRINTF(", RGB bits: %ld, ", pf->u.dwRGBBitCount); - switch (pf->u.dwRGBBitCount) { + DPRINTF(", RGB bits: %ld, ", pf->u1.dwRGBBitCount); + switch (pf->u1.dwRGBBitCount) { case 4: cmd = "%1lx"; break; case 8: cmd = "%02lx"; break; case 16: cmd = "%04lx"; break; @@ -274,114 +243,95 @@ void _dump_pixelformat(void *in) { case 32: cmd = "%08lx"; break; default: ERR("Unexpected bit depth !\n"); cmd = "%d"; break; } - DPRINTF(" R "); DPRINTF(cmd, pf->u1.dwRBitMask); - DPRINTF(" G "); DPRINTF(cmd, pf->u2.dwGBitMask); - DPRINTF(" B "); DPRINTF(cmd, pf->u3.dwBBitMask); + DPRINTF(" R "); DPRINTF(cmd, pf->u2.dwRBitMask); + DPRINTF(" G "); DPRINTF(cmd, pf->u3.dwGBitMask); + DPRINTF(" B "); DPRINTF(cmd, pf->u4.dwBBitMask); if (pf->dwFlags & DDPF_ALPHAPIXELS) { - DPRINTF(" A "); DPRINTF(cmd, pf->u4.dwRGBAlphaBitMask); + DPRINTF(" A "); DPRINTF(cmd, pf->u5.dwRGBAlphaBitMask); } if (pf->dwFlags & DDPF_ZPIXELS) { - DPRINTF(" Z "); DPRINTF(cmd, pf->u4.dwRGBZBitMask); + DPRINTF(" Z "); DPRINTF(cmd, pf->u5.dwRGBZBitMask); } } if (pf->dwFlags & DDPF_ZBUFFER) { - DPRINTF(", Z bits : %ld", pf->u.dwZBufferBitDepth); + DPRINTF(", Z bits : %ld", pf->u1.dwZBufferBitDepth); } if (pf->dwFlags & DDPF_ALPHA) { - DPRINTF(", Alpha bits : %ld", pf->u.dwAlphaBitDepth); + DPRINTF(", Alpha bits : %ld", pf->u1.dwAlphaBitDepth); } DPRINTF(")"); } -void _dump_colorkeyflag(DWORD ck) { - int i; - const struct { - DWORD mask; - char *name; - } flags[] = { -#define FE(x) { x, #x}, - FE(DDCKEY_COLORSPACE) - FE(DDCKEY_DESTBLT) - FE(DDCKEY_DESTOVERLAY) - FE(DDCKEY_SRCBLT) - FE(DDCKEY_SRCOVERLAY) -#undef FE +void DDRAW_dump_colorkeyflag(DWORD ck) +{ + static const flag_info flags[] = + { + FE(DDCKEY_COLORSPACE), + FE(DDCKEY_DESTBLT), + FE(DDCKEY_DESTOVERLAY), + FE(DDCKEY_SRCBLT), + FE(DDCKEY_SRCOVERLAY) }; - for (i=0;idwColorSpaceLowValue, ddck->dwColorSpaceHighValue); } -void _dump_surface_desc(DDSURFACEDESC *lpddsd) { - int i; - struct { - DWORD mask; - char *name; - void (*func)(void *); - void *elt; - } flags[16], *fe = flags; -#define FE(x,f,e) do { fe->mask = x; fe->name = #x; fe->func = f; fe->elt = (void *) &(lpddsd->e); fe++; } while(0) - FE(DDSD_CAPS, _dump_DDSCAPS, ddsCaps); - FE(DDSD_HEIGHT, _dump_DWORD, dwHeight); - FE(DDSD_WIDTH, _dump_DWORD, dwWidth); - FE(DDSD_PITCH, _dump_DWORD, lPitch); - FE(DDSD_BACKBUFFERCOUNT, _dump_DWORD, dwBackBufferCount); - FE(DDSD_ZBUFFERBITDEPTH, _dump_DWORD, u.dwZBufferBitDepth); - FE(DDSD_ALPHABITDEPTH, _dump_DWORD, dwAlphaBitDepth); - FE(DDSD_PIXELFORMAT, _dump_pixelformat, ddpfPixelFormat); - FE(DDSD_CKDESTOVERLAY, _dump_DDCOLORKEY, ddckCKDestOverlay); - FE(DDSD_CKDESTBLT, _dump_DDCOLORKEY, ddckCKDestBlt); - FE(DDSD_CKSRCOVERLAY, _dump_DDCOLORKEY, ddckCKSrcOverlay); - FE(DDSD_CKSRCBLT, _dump_DDCOLORKEY, ddckCKSrcBlt); - FE(DDSD_MIPMAPCOUNT, _dump_DWORD, u.dwMipMapCount); - FE(DDSD_REFRESHRATE, _dump_DWORD, u.dwRefreshRate); - FE(DDSD_LINEARSIZE, _dump_DWORD, u1.dwLinearSize); - FE(DDSD_LPSURFACE, _dump_PTR, u1.lpSurface); -#undef FE +void DDRAW_dump_surface_desc(const DDSURFACEDESC2 *lpddsd) +{ +#define STRUCT DDSURFACEDESC2 + static const member_info members[] = + { + ME(DDSD_CAPS, DDRAW_dump_DDSCAPS, ddsCaps), + ME(DDSD_HEIGHT, DDRAW_dump_DWORD, dwHeight), + ME(DDSD_WIDTH, DDRAW_dump_DWORD, dwWidth), + ME(DDSD_PITCH, DDRAW_dump_DWORD, u1.lPitch), + ME(DDSD_LINEARSIZE, DDRAW_dump_DWORD, u1.dwLinearSize), + ME(DDSD_BACKBUFFERCOUNT, DDRAW_dump_DWORD, dwBackBufferCount), + ME(DDSD_MIPMAPCOUNT, DDRAW_dump_DWORD, u2.dwMipMapCount), + ME(DDSD_REFRESHRATE, DDRAW_dump_DWORD, u2.dwRefreshRate), + ME(DDSD_ALPHABITDEPTH, DDRAW_dump_DWORD, dwAlphaBitDepth), + ME(DDSD_LPSURFACE, DDRAW_dump_PTR, lpSurface), + ME(DDSD_CKDESTOVERLAY, DDRAW_dump_DDCOLORKEY, u3.ddckCKDestOverlay), + ME(DDSD_CKDESTBLT, DDRAW_dump_DDCOLORKEY, ddckCKDestBlt), + ME(DDSD_CKSRCOVERLAY, DDRAW_dump_DDCOLORKEY, ddckCKSrcOverlay), + ME(DDSD_CKSRCBLT, DDRAW_dump_DDCOLORKEY, ddckCKSrcBlt), + ME(DDSD_PIXELFORMAT, DDRAW_dump_pixelformat, u4.ddpfPixelFormat) + }; - for (i=0;idwFlags) { - DPRINTF(" - %s : ",flags[i].name); - flags[i].func(flags[i].elt); - DPRINTF("\n"); - } + DDRAW_dump_members(lpddsd->dwFlags, lpddsd, members, + sizeof(members)/sizeof(members[0])); } -void _dump_cooperativelevel(DWORD cooplevel) { - int i; - const struct { - int mask; - char *name; - } flags[] = { -#define FE(x) { x, #x}, - FE(DDSCL_FULLSCREEN) - FE(DDSCL_ALLOWREBOOT) - FE(DDSCL_NOWINDOWCHANGES) - FE(DDSCL_NORMAL) - FE(DDSCL_ALLOWMODEX) - FE(DDSCL_EXCLUSIVE) - FE(DDSCL_SETFOCUSWINDOW) - FE(DDSCL_SETDEVICEWINDOW) + +void DDRAW_dump_cooperativelevel(DWORD cooplevel) +{ + static const flag_info flags[] = + { + FE(DDSCL_FULLSCREEN), + FE(DDSCL_ALLOWREBOOT), + FE(DDSCL_NOWINDOWCHANGES), + FE(DDSCL_NORMAL), + FE(DDSCL_ALLOWMODEX), + FE(DDSCL_EXCLUSIVE), + FE(DDSCL_SETFOCUSWINDOW), + FE(DDSCL_SETDEVICEWINDOW), FE(DDSCL_CREATEDEVICEWINDOW) -#undef FE }; - if (TRACE_ON(ddraw)) { + if (TRACE_ON(ddraw)) + { DPRINTF(" - "); - for (i=0;i #include -#include #include #include -#include #include "winerror.h" -#include "heap.h" -#include "wine/exception.h" #include "debugtools.h" +#include "heap.h" + +#include "initguid.h" +#include "ddraw.h" +#include "d3d.h" /* This for all the enumeration and creation of D3D-related objects */ #include "ddraw_private.h" -#define MAX_DDRAW_DRIVERS 3 -static ddraw_driver * ddraw_drivers[MAX_DDRAW_DRIVERS]; -static int nrof_ddraw_drivers = 0; +#define MAX_DDRAW_DRIVERS 3 +static const ddraw_driver* DDRAW_drivers[MAX_DDRAW_DRIVERS]; +static int DDRAW_num_drivers; /* = 0 */ +static int DDRAW_default_driver; DEFAULT_DEBUG_CHANNEL(ddraw); -/* register a direct draw driver. We better not use malloc for we are in - * the ELF startup initialisation at this point. - */ -void ddraw_register_driver(ddraw_driver *driver) { - ddraw_drivers[nrof_ddraw_drivers++] = driver; - - /* increase MAX_DDRAW_DRIVERS if the line below triggers */ - assert(nrof_ddraw_drivers <= MAX_DDRAW_DRIVERS); -} - /**********************************************************************/ typedef struct { @@ -51,7 +46,6 @@ HRESULT WINAPI DirectDrawEnumerateExA( LPDDENUMCALLBACKEXA lpCallback, LPVOID lpContext, DWORD dwFlags) { int i; - GUID zeroGUID; TRACE("(%p,%p, %08lx)\n", lpCallback, lpContext, dwFlags); if (TRACE_ON(ddraw)) { @@ -64,43 +58,20 @@ HRESULT WINAPI DirectDrawEnumerateExA( DPRINTF("DDENUM_NONDISPLAYDEVICES "); DPRINTF("\n"); } - if (dwFlags & DDENUM_ATTACHEDSECONDARYDEVICES) { - FIXME("no attached secondary devices supported.\n"); - /*return E_FAIL;*/ - } - memset(&zeroGUID,0,sizeof(zeroGUID)); + for (i=0; iinfo->szDriver, + DDRAW_drivers[i]->info->szDescription); - /* we have at least one DDRAW driver */ - if (ddraw_drivers[0]) { - if (!lpCallback( - &zeroGUID, /* FIXME: or NULL? -MM */ - "WINE DirectDraw", - "display", - lpContext, - 0 /* FIXME: flags not supported here */ - )) - return DD_OK; - } - /* Invoke callback for what flags we do support */ - for (i=0;icreateDDRAW(NULL)) /* !0 is failing */ - continue; - TRACE("Enumerating %s/%s interface\n",ddraw_drivers[i]->name,ddraw_drivers[i]->type); - if (!lpCallback( - ddraw_drivers[i]->guid, - (LPSTR)ddraw_drivers[i]->name, - (LPSTR)ddraw_drivers[i]->type, - lpContext, - 0 /* FIXME: flags not supported here */ - )) - return DD_OK; - } - if (nrof_ddraw_drivers) { - TRACE("Enumerating the default interface\n"); - if (!lpCallback(NULL,"WINE (default)", "display", lpContext, 0)) + /* We have to pass NULL from the primary display device. + * RoadRage chapter 6's enumeration routine expects it. */ + if (!lpCallback((DDRAW_default_driver == i) ? NULL + :(LPGUID)&DDRAW_drivers[i]->info->guidDeviceIdentifier, + (LPSTR)DDRAW_drivers[i]->info->szDescription, + (LPSTR)DDRAW_drivers[i]->info->szDriver, + lpContext, 0)) return DD_OK; } @@ -137,8 +108,6 @@ static BOOL CALLBACK DirectDrawEnumerateExProcW( return bResult; } -/**********************************************************************/ - HRESULT WINAPI DirectDrawEnumerateExW( LPDDENUMCALLBACKEXW lpCallback, LPVOID lpContext, DWORD dwFlags) { @@ -163,8 +132,6 @@ static BOOL CALLBACK DirectDrawEnumerateProcA( lpGUID, lpDriverDescription, lpDriverName, pEPD->lpContext); } -/**********************************************************************/ - HRESULT WINAPI DirectDrawEnumerateA( LPDDENUMCALLBACKA lpCallback, LPVOID lpContext) { @@ -189,8 +156,6 @@ static BOOL WINAPI DirectDrawEnumerateProcW( lpGUID, lpDriverDescription, lpDriverName, pEPD->lpContext); } -/**********************************************************************/ - HRESULT WINAPI DirectDrawEnumerateW( LPDDENUMCALLBACKW lpCallback, LPVOID lpContext) { @@ -201,215 +166,203 @@ HRESULT WINAPI DirectDrawEnumerateW( return DirectDrawEnumerateExW(DirectDrawEnumerateProcW, (LPVOID) &epd, 0); } -/****************************************************************************** - * DirectDraw Window Procedure +/*********************************************************************** + * DirectDrawCreate */ -static LRESULT WINAPI DDWndProc(HWND hwnd,UINT msg,WPARAM wParam,LPARAM lParam) + +const ddraw_driver* DDRAW_FindDriver(const GUID* pGUID) { - LRESULT ret; - IDirectDrawImpl* ddraw = NULL; - DWORD lastError; + static const GUID zeroGUID; /* gets zero-inited */ - /* FIXME(ddraw,"(0x%04x,%s,0x%08lx,0x%08lx),stub!\n",(int)hwnd,SPY_GetMsgName(msg),(long)wParam,(long)lParam); */ + TRACE("(%s)\n", pGUID ? debugstr_guid(pGUID) : "(null)"); - SetLastError( ERROR_SUCCESS ); - ddraw = (IDirectDrawImpl*)GetPropA( hwnd, ddProp ); - if( (!ddraw) && ( ( lastError = GetLastError() ) != ERROR_SUCCESS )) - ERR("Unable to retrieve this ptr from window. Error %08lx\n",lastError); + if (DDRAW_num_drivers == 0) return NULL; - if( ddraw ) { - /* Perform any special direct draw functions */ - if (msg==WM_PAINT) - ddraw->d->paintable = 1; + if (pGUID == (LPGUID)DDCREATE_EMULATIONONLY + || pGUID == (LPGUID)DDCREATE_HARDWAREONLY) + pGUID = NULL; - /* Now let the application deal with the rest of this */ - if( ddraw->d->mainWindow ) { + if (pGUID == NULL || memcmp(pGUID, &zeroGUID, sizeof(GUID)) == 0) + { + /* Use the default driver. */ + return DDRAW_drivers[DDRAW_default_driver]; + } + else + { + /* Look for a matching GUID. */ - /* Don't think that we actually need to call this but... - * might as well be on the safe side of things... - */ + int i; + for (i=0; i < DDRAW_num_drivers; i++) + { + if (IsEqualGUID(pGUID, + &DDRAW_drivers[i]->info->guidDeviceIdentifier)) + break; + } - /* I changed hwnd to ddraw->d->mainWindow as I did not see why - * it should be the procedures of our fake window that gets called - * instead of those of the window provided by the application. - * And with this patch, mouse clicks work with Monkey Island III - * - Lionel - */ - ret = DefWindowProcA( ddraw->d->mainWindow, msg, wParam, lParam ); + if (i < DDRAW_num_drivers) + { + return DDRAW_drivers[i]; + } + else + { + ERR("(%s): did not recognize requested GUID.\n",debugstr_guid(pGUID)); + return NULL; + } + } +} - if( !ret ) { - /* We didn't handle the message - give it to the application */ - if (ddraw && ddraw->d->mainWindow) - { - WNDPROC winproc = (WNDPROC)GetWindowLongA( ddraw->d->mainWindow, GWL_WNDPROC ); - ret = CallWindowProcA(winproc, ddraw->d->mainWindow, msg, wParam, lParam ); - } - } - return ret; - } /* else FALLTHROUGH */ - } /* else FALLTHROUGH */ - return DefWindowProcA(hwnd,msg,wParam,lParam); +static HRESULT DDRAW_Create( + LPGUID lpGUID, LPVOID *lplpDD, LPUNKNOWN pUnkOuter, REFIID iid, BOOL ex +) { + const ddraw_driver* driver; + LPDIRECTDRAW7 pDD; + HRESULT hr; + + if (DDRAW_num_drivers == 0) + { + WARN("no DirectDraw drivers registered\n"); + return DDERR_INVALIDDIRECTDRAWGUID; + } + + if (lpGUID == (LPGUID)DDCREATE_EMULATIONONLY + || lpGUID == (LPGUID)DDCREATE_HARDWAREONLY) + lpGUID = NULL; + + TRACE("(%s,%p,%p)\n",debugstr_guid(lpGUID),lplpDD,pUnkOuter); + + if (pUnkOuter != NULL) + return DDERR_INVALIDPARAMS; /* CLASS_E_NOAGGREGATION? */ + + driver = DDRAW_FindDriver(lpGUID); + if (driver == NULL) return DDERR_INVALIDDIRECTDRAWGUID; + + hr = driver->create(lpGUID, &pDD, pUnkOuter, ex); + if (FAILED(hr)) return hr; + + hr = IDirectDraw7_QueryInterface(pDD, iid, lplpDD); + IDirectDraw7_Release(pDD); + return hr; } /*********************************************************************** * DirectDrawCreate + * + * Only creates legacy IDirectDraw interfaces. + * Cannot create IDirectDraw7 interfaces. + * In theory. */ HRESULT WINAPI DirectDrawCreate( - LPGUID lpGUID, LPDIRECTDRAW *lplpDD, LPUNKNOWN pUnkOuter + LPGUID lpGUID, LPDIRECTDRAW* lplpDD, LPUNKNOWN pUnkOuter ) { - IDirectDrawImpl** ilplpDD=(IDirectDrawImpl**)lplpDD; - WNDCLASSA wc; - HRESULT ret = 0; - int i,drvindex=0; - GUID zeroGUID; - - struct ddraw_driver *ddd = NULL; - - if (!HIWORD(lpGUID)) lpGUID = NULL; - - TRACE("(%s,%p,%p)\n",debugstr_guid(lpGUID),ilplpDD,pUnkOuter); - - memset(&zeroGUID,0,sizeof(zeroGUID)); - while (1) { - ddd = NULL; - if ( ( !lpGUID ) || - ( IsEqualGUID( &zeroGUID, lpGUID ) ) || - ( IsEqualGUID( &IID_IDirectDraw, lpGUID ) ) || - ( IsEqualGUID( &IID_IDirectDraw2, lpGUID ) ) || - ( IsEqualGUID( &IID_IDirectDraw4, lpGUID ) ) || - ( IsEqualGUID( &IID_IDirectDraw7, lpGUID ) ) - ) { - /* choose an interface out of the list */ - for (i=0;ipreferencepreference)) { - drvindex = i; - ddd = xddd; - } - } - } else { - for (i=0;iguid,lpGUID)) { - drvindex = i; - ddd = ddraw_drivers[i]; - break; - } - } - } - if (!ddd) { - if (!nrof_ddraw_drivers) { - ERR("DirectDrawCreate(%s,%p,%p): no DirectDraw drivers compiled in.\n",debugstr_guid(lpGUID),lplpDD,pUnkOuter); - return DDERR_NODIRECTDRAWHW; - } - ERR("DirectDrawCreate(%s,%p,%p): did not recognize requested GUID.\n",debugstr_guid(lpGUID),lplpDD,pUnkOuter); - return DDERR_INVALIDDIRECTDRAWGUID; - } - TRACE("using \"%s\" driver, calling %p\n",ddd->name,ddd->createDDRAW); - - ret = ddd->createDDRAW(lplpDD); - if (!ret) - break; - ddraw_drivers[drvindex] = NULL; /* mark this one as unusable */ - } - - if (lpGUID && - (IsEqualGUID( &IID_IDirectDraw2, lpGUID ) || - IsEqualGUID( &IID_IDirectDraw4, lpGUID ) || - IsEqualGUID( &IID_IDirectDraw7, lpGUID ) - ) - ) { - LPVOID x; - ret = IDirectDraw_QueryInterface(*lplpDD,lpGUID,&x); - IDirectDraw_Release(*lplpDD); /* either drop 1 refcount, or release */ - if (!ret) - *lplpDD = x; - else - return ret; - } - wc.style = CS_GLOBALCLASS; - wc.lpfnWndProc = DDWndProc; - wc.cbClsExtra = 0; - wc.cbWndExtra = 0; - - /* We can be a child of the desktop since we're really important */ - wc.hInstance= 0; - wc.hIcon = 0; - wc.hCursor = (HCURSOR)IDC_ARROWA; - wc.hbrBackground = NULL_BRUSH; - wc.lpszMenuName = 0; - wc.lpszClassName = "WINE_DirectDraw"; - (*ilplpDD)->d->winclass = RegisterClassA(&wc); - return ret; + return DDRAW_Create(lpGUID,(LPVOID*)lplpDD,pUnkOuter,&IID_IDirectDraw,FALSE); } /*********************************************************************** * DirectDrawCreateEx + * + * Only creates new IDirectDraw7 interfaces. + * Supposed to fail if legacy interfaces are requested. + * In theory. */ HRESULT WINAPI DirectDrawCreateEx( LPGUID lpGUID, LPVOID* lplpDD, REFIID iid, LPUNKNOWN pUnkOuter ) { - LPDIRECTDRAW ddraw; - HRESULT hres; + if (!IsEqualGUID(iid, &IID_IDirectDraw7)) + return DDERR_INVALIDPARAMS; - FIXME("(%p,%p,%s,%p), might be wrong.\n",lpGUID,lplpDD,debugstr_guid(iid),pUnkOuter); - - hres=DirectDrawCreate(lpGUID,(LPDIRECTDRAW*)&ddraw,pUnkOuter); - if (!hres) { - hres=IDirectDraw_QueryInterface(ddraw,iid,lplpDD); - IDirectDraw_Release(ddraw); - } - return hres; + return DDRAW_Create(lpGUID, lplpDD, pUnkOuter, iid, TRUE); } -/******************************************************************************* +extern HRESULT Uninit_DirectDraw_Create(const GUID*, LPDIRECTDRAW7*, + LPUNKNOWN, BOOL); + +/* This is for the class factory. */ +static HRESULT DDRAW_CreateDirectDraw(IUnknown* pUnkOuter, REFIID iid, + LPVOID* ppObj) +{ + LPDIRECTDRAW7 pDD; + HRESULT hr; + + hr = Uninit_DirectDraw_Create(NULL, &pDD, pUnkOuter, TRUE); /* ex? */ + if (FAILED(hr)) return hr; + + hr = IDirectDraw7_QueryInterface(pDD, iid, ppObj); + IDirectDraw_Release(pDD); + return hr; +} + +/****************************************************************************** * DirectDraw ClassFactory - * - * Heavily inspired (well, can you say completely copied :-) ) from DirectSound - * */ typedef struct { - /* IUnknown fields */ - ICOM_VFIELD(IClassFactory); - DWORD ref; + ICOM_VFIELD_MULTI(IClassFactory); + + DWORD ref; + HRESULT (*pfnCreateInstance)(IUnknown *pUnkOuter, REFIID iid, + LPVOID *ppObj); } IClassFactoryImpl; +struct object_creation_info +{ + const CLSID *clsid; + HRESULT (*pfnCreateInstance)(IUnknown *pUnkOuter, REFIID riid, + LPVOID *ppObj); +}; + +/* There should be more, but these are the only ones listed in the header + * file. */ +extern HRESULT DDRAW_CreateDirectDrawClipper(IUnknown *pUnkOuter, REFIID riid, + LPVOID *ppObj); + +static const struct object_creation_info object_creation[] = +{ + { &CLSID_DirectDraw, DDRAW_CreateDirectDraw }, + { &CLSID_DirectDraw7, DDRAW_CreateDirectDraw }, + { &CLSID_DirectDrawClipper, DDRAW_CreateDirectDrawClipper } +}; + static HRESULT WINAPI -DDCF_QueryInterface(LPCLASSFACTORY iface,REFIID riid,LPVOID *ppobj) { +DDCF_QueryInterface(LPCLASSFACTORY iface,REFIID riid,LPVOID *ppobj) +{ ICOM_THIS(IClassFactoryImpl,iface); - FIXME("(%p)->(%s,%p),stub!\n",This,debugstr_guid(riid),ppobj); + if (IsEqualGUID(riid, &IID_IUnknown) + || IsEqualGUID(riid, &IID_IClassFactory)) + { + IClassFactory_AddRef(iface); + *ppobj = This; + return S_OK; + } + + WARN("(%p)->(%s,%p),not found\n",This,debugstr_guid(riid),ppobj); return E_NOINTERFACE; } -static ULONG WINAPI -DDCF_AddRef(LPCLASSFACTORY iface) { +static ULONG WINAPI DDCF_AddRef(LPCLASSFACTORY iface) { ICOM_THIS(IClassFactoryImpl,iface); return ++(This->ref); } static ULONG WINAPI DDCF_Release(LPCLASSFACTORY iface) { ICOM_THIS(IClassFactoryImpl,iface); - /* static class, won't be freed */ - return --(This->ref); + + ULONG ref = --This->ref; + + if (ref == 0) + HeapFree(GetProcessHeap(), 0, This); + + return ref; } + static HRESULT WINAPI DDCF_CreateInstance( LPCLASSFACTORY iface,LPUNKNOWN pOuter,REFIID riid,LPVOID *ppobj ) { ICOM_THIS(IClassFactoryImpl,iface); TRACE("(%p)->(%p,%s,%p)\n",This,pOuter,debugstr_guid(riid),ppobj); - if ( ( IsEqualGUID( &IID_IDirectDraw, riid ) ) || - ( IsEqualGUID( &IID_IDirectDraw2, riid ) ) || - ( IsEqualGUID( &IID_IDirectDraw4, riid ) ) ) { - /* FIXME: reuse already created DirectDraw if present? */ - return DirectDrawCreate((LPGUID) riid,(LPDIRECTDRAW*)ppobj,pOuter); - } - return CLASS_E_CLASSNOTAVAILABLE; + + return This->pfnCreateInstance(pOuter, riid, ppobj); } static HRESULT WINAPI DDCF_LockServer(LPCLASSFACTORY iface,BOOL dolock) { @@ -427,7 +380,6 @@ static ICOM_VTABLE(IClassFactory) DDCF_Vtbl = DDCF_CreateInstance, DDCF_LockServer }; -static IClassFactoryImpl DDRAW_CF = {&DDCF_Vtbl, 1 }; /******************************************************************************* * DllGetClassObject [DDRAW.13] @@ -448,14 +400,37 @@ static IClassFactoryImpl DDRAW_CF = {&DDCF_Vtbl, 1 }; */ DWORD WINAPI DDRAW_DllGetClassObject(REFCLSID rclsid,REFIID riid,LPVOID *ppv) { + int i; + IClassFactoryImpl *factory; + TRACE("(%p,%p,%p)\n", debugstr_guid(rclsid), debugstr_guid(riid), ppv); - if ( IsEqualGUID( &IID_IClassFactory, riid ) ) { - *ppv = (LPVOID)&DDRAW_CF; - IClassFactory_AddRef((IClassFactory*)*ppv); - return S_OK; + + if ( !IsEqualGUID( &IID_IClassFactory, riid ) + && ! IsEqualGUID( &IID_IUnknown, riid) ) + return E_NOINTERFACE; + + for (i=0; i < sizeof(object_creation)/sizeof(object_creation[0]); i++) + { + if (IsEqualGUID(&object_creation[i].clsid, rclsid)) + break; } - FIXME("(%p,%p,%p): no interface found.\n", debugstr_guid(rclsid), debugstr_guid(riid), ppv); - return CLASS_E_CLASSNOTAVAILABLE; + + if (i == sizeof(object_creation)/sizeof(object_creation[0])) + { + FIXME("%s: no class found.\n", debugstr_guid(rclsid)); + return CLASS_E_CLASSNOTAVAILABLE; + } + + factory = HeapAlloc(GetProcessHeap(), 0, sizeof(*factory)); + if (factory == NULL) return E_OUTOFMEMORY; + + ICOM_INIT_INTERFACE(factory, IClassFactory, DDCF_Vtbl); + factory->ref = 1; + + factory->pfnCreateInstance = object_creation[i].pfnCreateInstance; + + *ppv = ICOM_INTERFACE(factory, IClassFactory); + return S_OK; } @@ -470,3 +445,89 @@ DWORD WINAPI DDRAW_DllCanUnloadNow(void) { FIXME("(void): stub\n"); return S_FALSE; } + +/****************************************************************************** + * Initialisation + */ + +/* Choose which driver is considered the primary display driver. It will + * be created when we get a NULL guid for the DirectDrawCreate(Ex). */ +static int DDRAW_ChooseDefaultDriver(void) +{ + int i; + int best = 0; + int best_score = 0; + + assert(DDRAW_num_drivers > 0); + + /* This algorithm is really stupid. */ + for (i=0; i < DDRAW_num_drivers; i++) + { + if (DDRAW_drivers[i]->preference > best_score) + { + best_score = DDRAW_drivers[i]->preference; + best = i; + } + } + + assert(best_score > 0); + + return best; +} + +BOOL WINAPI DDRAW_DllMain(HINSTANCE hInstDLL, DWORD fdwReason, LPVOID lpv) +{ + /* If we were sufficiently cool, DDraw drivers would just be COM + * objects, registered with a particular component category. */ + + DDRAW_User_Init(hInstDLL, fdwReason, lpv); + +#ifdef HAVE_LIBXXF86VM + DDRAW_XVidMode_Init(hInstDLL, fdwReason, lpv); +#endif +#ifdef HAVE_LIBXXF86DGA2 + DDRAW_XF86DGA2_Init(hInstDLL, fdwReason, lpv); +#endif + + if (DDRAW_num_drivers > 0) + DDRAW_default_driver = DDRAW_ChooseDefaultDriver(); + + return TRUE; +} + +/* Register a direct draw driver. This should be called from your init + * function. (That's why there is no locking: your init func is called from + * our DllInit, which is serialised.) */ +void DDRAW_register_driver(const ddraw_driver *driver) +{ + int i; + + for (i = 0; i < DDRAW_num_drivers; i++) + { + if (DDRAW_drivers[i] == driver) + { + ERR("Driver reregistering %p\n", driver); + return; + } + } + + if (DDRAW_num_drivers == sizeof(DDRAW_drivers)/sizeof(DDRAW_drivers[0])) + { + ERR("too many DDRAW drivers\n"); + return; + } + + DDRAW_drivers[DDRAW_num_drivers++] = driver; +} + +/* This totally doesn't belong here. */ +LONG DDRAW_width_bpp_to_pitch(DWORD width, DWORD bpp) +{ + LONG pitch; + + assert(bpp != 0); /* keeps happening... */ + + if (bpp == 15) bpp = 16; + pitch = width * (bpp / 8); + return pitch + (8 - (pitch % 8)) % 8; +} diff --git a/dlls/ddraw/mesa_private.h b/dlls/ddraw/mesa_private.h index 5aa5c947fb8..398a0fd21c4 100644 --- a/dlls/ddraw/mesa_private.h +++ b/dlls/ddraw/mesa_private.h @@ -14,8 +14,6 @@ #undef USE_OSMESA -#include "x11_private.h" - /***************************************************************************** * IDirect3DLight MESA private structure */ @@ -110,8 +108,8 @@ void set_render_state(D3DRENDERSTATETYPE dwRenderStateType, DWORD dwRenderState, RenderState *rs) ; /* All non-static functions 'exported' by various sub-objects */ -extern LPDIRECT3DTEXTURE2 d3dtexture2_create(IDirectDrawSurface4Impl* surf); -extern LPDIRECT3DTEXTURE d3dtexture_create(IDirectDrawSurface4Impl* surf); +extern LPDIRECT3DTEXTURE2 d3dtexture2_create(IDirectDrawSurfaceImpl* surf); +extern LPDIRECT3DTEXTURE d3dtexture_create(IDirectDrawSurfaceImpl* surf); extern LPDIRECT3DLIGHT d3dlight_create_dx3(IDirect3DImpl* d3d1); extern LPDIRECT3DLIGHT d3dlight_create(IDirect3D2Impl* d3d2); @@ -129,8 +127,8 @@ extern int d3d_OpenGL_dx3(LPD3DENUMDEVICESCALLBACK cb, LPVOID context) ; extern int d3d_OpenGL(LPD3DENUMDEVICESCALLBACK cb, LPVOID context) ; extern int is_OpenGL(REFCLSID rguid, IDirectDrawSurfaceImpl* surface, IDirect3DDevice2Impl** device, IDirect3D2Impl* d3d); -extern LPDIRECT3DTEXTURE2 mesa_d3dtexture2_create(IDirectDrawSurface4Impl*); -extern LPDIRECT3DTEXTURE mesa_d3dtexture_create(IDirectDrawSurface4Impl*); +extern LPDIRECT3DTEXTURE2 mesa_d3dtexture2_create(IDirectDrawSurfaceImpl*); +extern LPDIRECT3DTEXTURE mesa_d3dtexture_create(IDirectDrawSurfaceImpl*); static const GUID WINE_UNUSED IID_D3DDEVICE2_OpenGL = { 0x39a0da38, diff --git a/dlls/ddraw/struct_convert.c b/dlls/ddraw/struct_convert.c new file mode 100644 index 00000000000..929e6d4a857 --- /dev/null +++ b/dlls/ddraw/struct_convert.c @@ -0,0 +1,28 @@ +/* ddraw/d3d structure version conversion + * + * Copyright 2000 TransGaming Technologies Inc. + */ + +#include + +#include + +#include "ddraw_private.h" + +void DDRAW_Convert_DDSCAPS_1_To_2(const DDSCAPS* pIn, DDSCAPS2* pOut) +{ + /* 2 adds three additional caps fields to the end. Both versions + * are unversioned. */ + pOut->dwCaps = pIn->dwCaps; + pOut->dwCaps2 = 0; + pOut->dwCaps3 = 0; + pOut->dwCaps4 = 0; +} + +void DDRAW_Convert_DDDEVICEIDENTIFIER_2_To_1(const DDDEVICEIDENTIFIER* pIn, + DDDEVICEIDENTIFIER2* pOut) +{ + /* 2 adds a dwWHQLLevel field to the end. Both structures are + * unversioned. */ + memcpy(pOut, pIn, sizeof(*pOut)); +} diff --git a/dlls/ddraw/x11.c b/dlls/ddraw/x11.c deleted file mode 100644 index a3902ab8c0f..00000000000 --- a/dlls/ddraw/x11.c +++ /dev/null @@ -1,178 +0,0 @@ -/* DirectDraw using DGA or Xlib(XSHM) - * - * Copyright 1997-1999 Marcus Meissner - * Copyright 1998 Lionel Ulmer (most of Direct3D stuff) - */ -#include "config.h" - -#include -#include -#include -#include -#include - -#include "winerror.h" -#include "options.h" -#include "debugtools.h" -#include "ddraw.h" - -DEFAULT_DEBUG_CHANNEL(ddraw); - -#include "x11_private.h" - -#ifdef HAVE_LIBXXSHM -int XShmErrorFlag = 0; -#endif - -static inline BOOL get_option( const char *name, BOOL def ) { - return PROFILE_GetWineIniBool( "x11drv", name, def ); -} - -static BOOL -DDRAW_XSHM_Available(void) { -#ifdef HAVE_LIBXXSHM - if (get_option( "UseXShm", 1 )) { - if (TSXShmQueryExtension(display)) { - int major,minor; - Bool shpix; - - if (TSXShmQueryVersion(display, &major, &minor, &shpix)) - return TRUE; - } - } -#endif - return FALSE; -} - -#ifdef HAVE_XVIDEO -static BOOL -DDRAW_XVIDEO_Available(x11_dd_private *x11ddp) { - unsigned int p_version, p_release, p_request_base, p_event_base, p_error_base; - - if (TSXvQueryExtension(display, &p_version, &p_release, &p_request_base, - &p_event_base, &p_error_base) == Success) { - XvAdaptorInfo *ai; - int num_adaptators, i, default_port; - - if ((p_version < 2) || ((p_version == 2) && (p_release < 2))) { - TRACE("XVideo extension does NOT support needed features (need version 2.2) !\n"); - return FALSE; - } - - if (TSXvQueryAdaptors(display, X11DRV_GetXRootWindow(), &num_adaptators, &ai) != Success) { - TRACE("Failed to get list of adaptators.\n"); - return FALSE; - } - if (num_adaptators == 0) { - TRACE("No XVideo supporting adaptators found.\n"); - return FALSE; - } - - default_port = PROFILE_GetWineIniInt("x11drv", "XVideoPort", -1); - for (i = 0; i < num_adaptators; i++) { - if ((ai[i].type & XvInputMask) && (ai[i].type & XvImageMask)) { - /* This supports everything I want : XvImages and the possibility to put something */ - if (default_port == -1) { - default_port = ai[i].base_id; - break; - } else { - if ((ai[i].base_id <= default_port) && - ((ai[i].base_id + ai[i].num_ports) > default_port)) { - break; - } - } - } - } - if (i == num_adaptators) { - if (default_port != -1) { - ERR("User specified port (%d) not found.\n", default_port); - } else { - TRACE("No input + image capable device found.\n"); - } - TSXvFreeAdaptorInfo(ai); - return FALSE; - } - x11ddp->port_id = default_port; - - TRACE("XVideo support available (using version %d.%d)\n", p_version, p_release); - TSXvFreeAdaptorInfo(ai); - return TRUE; - } - return FALSE; -} -#endif - -static HRESULT X11_Create( LPDIRECTDRAW *lplpDD ) { - IDirectDrawImpl* ddraw; - int depth; - x11_dd_private *x11priv; - - if (lplpDD == NULL) /* Testing ... this driver works all the time */ - return DD_OK; - - *lplpDD = (LPDIRECTDRAW)HeapAlloc( - GetProcessHeap(), - HEAP_ZERO_MEMORY, - sizeof(IDirectDrawImpl) - ); - ddraw = (IDirectDrawImpl*)*lplpDD; - ICOM_VTBL(ddraw)= &xlib_ddvt; - ddraw->ref = 1; - - ddraw->d = HeapAlloc(GetProcessHeap(),HEAP_ZERO_MEMORY,sizeof(*(ddraw->d))); - ddraw->d->ref = 1; - ddraw->d->private = HeapAlloc( - GetProcessHeap(), - HEAP_ZERO_MEMORY, - sizeof(x11_dd_private) - ); - x11priv = (x11_dd_private*)ddraw->d->private; - - /* At DirectDraw creation, the depth is the default depth */ - depth = DefaultDepthOfScreen(X11DRV_GetXScreen()); - - switch (_common_depth_to_pixelformat(depth,(LPDIRECTDRAW)ddraw)) { - case -2: ERR("no depth conversion mode for depth %d found\n",depth); break; - case -1: WARN("No conversion needed for depth %d.\n",depth); break; - case 0: MESSAGE("Conversion needed from %d.\n",depth); break; - } - - ddraw->d->height = GetSystemMetrics(SM_CYSCREEN); - ddraw->d->width = GetSystemMetrics(SM_CXSCREEN); -#ifdef HAVE_LIBXXSHM - /* Test if XShm is available. */ - if ((x11priv->xshm_active = DDRAW_XSHM_Available())) { - x11priv->xshm_compl = 0; - TRACE("Using XShm extension.\n"); - } -#endif - -#ifdef HAVE_XVIDEO - /* Test if XVideo support is available */ - if ((x11priv->xvideo_active = DDRAW_XVIDEO_Available(x11priv))) { - TRACE("Using XVideo extension on port '%ld'.\n", x11priv->port_id); - } -#endif - return DD_OK; -} - -/* Where do these GUIDs come from? mkuuid. - * They exist solely to distinguish between the targets Wine support, - * and should be different than any other GUIDs in existence. - */ -static GUID X11_DirectDraw_GUID = { /* 1574a740-dc61-11d1-8407-f7875a7d1879 */ - 0x1574a740, - 0xdc61, - 0x11d1, - {0x84, 0x07, 0xf7, 0x87, 0x5a, 0x7d, 0x18, 0x79} -}; - -ddraw_driver x11_driver = { - &X11_DirectDraw_GUID, - "display", - "WINE X11 DirectDraw Driver", - 50, - X11_Create -}; - -DECL_GLOBAL_CONSTRUCTOR(X11_register) { ddraw_register_driver(&x11_driver); } diff --git a/dlls/ddraw/x11_private.h b/dlls/ddraw/x11_private.h deleted file mode 100644 index e135fa8c014..00000000000 --- a/dlls/ddraw/x11_private.h +++ /dev/null @@ -1,93 +0,0 @@ -#ifndef __WINE_DDRAW_X11_PRIVATE_H -#define __WINE_DDRAW_X11_PRIVATE_H - -/* This file contains all X11 private and specific definitions. - * It may also be used by all ports that reuse X11 stuff (like XF86 DGA) - */ -#include "config.h" -#include "ts_xlib.h" -#include "ts_xutil.h" - -#ifdef HAVE_LIBXXSHM -# include -# ifdef HAVE_SYS_IPC_H -# include -# endif -# ifdef HAVE_SYS_SHM_H -# include -# endif -# include "ts_xshm.h" -#endif /* defined(HAVE_LIBXXSHM) */ - -#ifdef HAVE_LIBXXF86VM -# include "ts_xf86vmode.h" -extern XF86VidModeModeInfo *orig_mode; -#endif /* defined(HAVE_LIBXXF86VM) */ - -extern void xf86vmode_setdisplaymode(DWORD,DWORD); -extern void xf86vmode_restore(); - -#ifdef HAVE_XVIDEO -#include "ts_xvideo.h" -#else -/* Fake type so that NOT to have too many #ifdef XVideo lying around */ -typedef int XvImage; -#endif - -#include "x11drv.h" - -#include "ddraw_private.h" - -#include "wine_gl.h" - -extern ICOM_VTABLE(IDirectDraw) xlib_ddvt; -extern ICOM_VTABLE(IDirectDraw2) xlib_dd2vt; -extern ICOM_VTABLE(IDirectDraw4) xlib_dd4vt; -extern ICOM_VTABLE(IDirectDraw7) xlib_dd7vt; -extern ICOM_VTABLE(IDirectDrawPalette) xlib_ddpalvt; -extern ICOM_VTABLE(IDirectDrawSurface4) xlib_dds4vt; - -typedef struct x11_dd_private { -#ifdef HAVE_LIBXXSHM - int xshm_active, xshm_compl; -#endif /* defined(HAVE_LIBXXSHM) */ -#ifdef HAVE_XVIDEO - BOOL xvideo_active; - XvPortID port_id; -#endif - Window drawable; - void *device_capabilities; -} x11_dd_private; - -typedef struct x11_dp_private { - BOOL installed; /* is colormap installed */ - Colormap cm; /* the X11 Colormap associated */ -} x11_dp_private; - -extern HRESULT WINAPI Xlib_IDirectDrawPaletteImpl_SetEntries(LPDIRECTDRAWPALETTE,DWORD,DWORD,DWORD,LPPALETTEENTRY); -extern ULONG WINAPI Xlib_IDirectDrawPaletteImpl_Release(LPDIRECTDRAWPALETTE iface); - -typedef struct x11_ds_private { - BOOL is_overlay; - union { - XImage *image; - struct { - /* The 'image' field should be in FIRST !!!! The Flip function depends on that... */ - XvImage *image; - BOOL shown; - RECT src_rect; - RECT dst_rect; - LPDIRECTDRAWSURFACE dest_surface; - } overlay; - } info; -#ifdef HAVE_LIBXXSHM - XShmSegmentInfo shminfo; -#endif - int *oldDIBmap; - BOOL opengl_flip; -} x11_ds_private; - -#ifdef HAVE_LIBXXSHM -extern int XShmErrorFlag; -#endif -#endif /* __WINE_DDRAW_X11_PRIVATE_H */ diff --git a/documentation/ddraw.txt b/documentation/ddraw.txt new file mode 100644 index 00000000000..830eab15f3c --- /dev/null +++ b/documentation/ddraw.txt @@ -0,0 +1,134 @@ +This is an outline of the architecture. Many details are +skipped, but hopefully this is useful. + +By Andrew Lewycky +(with updates by Ove Kåven ) + + +* DirectDraw inheritance tree + + Main + | + User + |-----------\ + XVidMode DGA2 + +Most of the DirectDraw functionality is implemented in a common base +class. Derived classes are responsible for providing display +mode functions (Enum, Set, Restore), GetCaps, GetDevice identifier +and internal functions called to create primary and backbuffer +surfaces. + +User provides for DirectDraw capabilities based on drawing to a +Wine window. It uses the User DirectDrawSurface implementation +for primary and backbuffer surfaces. + +XVidMode attempt to use the XFree86 VidMode extension to set the +display resolution to match the parameters to SetDisplayMode. + +DGA2 attempt to use the XFree86 DGA 2.x extension to set the +display resolution and direct access to the framebuffer, if the +full-screen-exclusive cooperative level is used. If not, it just +uses the User implementation. + + +* DirectDrawSurface inheritance tree + + Main + |--------------\ + | | + DIB Fake Z-Buffer + | + |------\---------\ + | | | + User DGA2 DIBTexture + +Main provides a very simple base class that does not implement any of +the image-related functions. Therefore it does not place any +constraints on how the surface data is stored. + +DIB stores the surface data in a DIB section. It is used by the Main +DirectDraw driver to create off-screen surfaces. + +User implements primary and backbuffer surfaces for the User DirectDraw +driver. If it is a primary surface, it will attempt to keep itself +synchronized to the window. + +DGA2 surfaces claims an appropriate section of framebuffer space and +lets DIB build its DIB section on top of it. + +Fake Z-Buffer surfaces are used by Direct3D to indicate that a primary +surface has an associated z-buffer. For a first implementation, it +doesn't need to store any image data since it is just a placeholder. + +(Actually 3D programs will rarely use Lock or GetDC on primary +surfaces, backbuffers or z-buffers so we may want to arrange for +lazy allocation of the DIB sections.) + + +* Interface Thunks + +Only the most recent version of an interface needs to be implemented. +Other versions are handled by having thunks convert their parameters +and call the root version. + +Not all interface versions have thunks. Some versions could be combined +because their parameters were compatible. For example if a structure +changes but the structure has a dwSize field, methods using that structure +are compatible, as long as the implementation remembers to take the dwSize +into account. + +Interface thunks for Direct3D are more complicated since the paradigm +changed between versions. + + +* Logical Object Layout + +The objects are split into the generic part (essentially the fields for +Main) and a private part. This is necessary because some objects +can be created with CoCreateInstance, then Initialized later. Only +at initialisation time do we know which class to use. Each class +except Main declares a Part structure and adds that to its Impl. + +For example, the DIBTexture DirectDrawSurface implementation looks +like this: + +struct DIBTexture_DirectDrawSurfaceImpl_Part +{ + union DIBTexture_data data; /*declared in the real header*/ +}; + +typedef struct +{ + struct DIB_DirectDrawSurfaceImpl_Part dib; + struct DIBTexture_DirectDrawSurfaceImpl_Part dibtexture; +} DIBTexture_DirectDrawSurfaceImpl; + +So the DIBTexture surface class is derived from the DIB surface +class and it adds one piece of data, a union. + +Main does not have a Part structure. Its fields are stored in +IDirectDrawImpl/IDirectDrawSurfaceImpl. + +To access private data, one says + +DIBTexture_DirectDrawSurfaceImpl* priv = This->private; +do_something_with(priv->dibtexture.data); + + +* Creating Objects + +Classes have two functions relevant to object creation, Create and +Construct. To create a new object, the class' Create function is +called. It allocates enough memory for IDirectDrawImpl or +IDirectDrawSurfaceImpl as well as the private data for derived +classes and then calls Construct. + +Each class's Construct function calls the base class's Construct, +then does the necessary initialization. + +For example, creating a primary surface with the user ddraw driver +calls User_DirectDrawSurface_Create which allocates memory for the +object and calls User_DirectDrawSurface_Construct to initialize it. +This calls DIB_DirectDrawSurface_Construct which calls +Main_DirectDrawSurface_Construct. diff --git a/include/acconfig.h b/include/acconfig.h index 8dc758f92c4..91b3d56fcee 100644 --- a/include/acconfig.h +++ b/include/acconfig.h @@ -129,5 +129,8 @@ /* Define if the X libraries support XVideo */ #undef HAVE_XVIDEO +/* Define if Mesa's OSMesa (off-screen rendering) library is present */ +#undef HAVE_OSMESA + /* Define if Linux-style gethostbyname_r and gethostbyaddr_r are available */ #undef HAVE_LINUX_GETHOSTBYNAME_R_6 diff --git a/include/config.h.in b/include/config.h.in index e1839df6ee4..27c2df3fddb 100644 --- a/include/config.h.in +++ b/include/config.h.in @@ -164,6 +164,9 @@ /* Define if the X libraries support XVideo */ #undef HAVE_XVIDEO +/* Define if Mesa's OSMesa (off-screen rendering) library is present */ +#undef HAVE_OSMESA + /* Define if Linux-style gethostbyname_r and gethostbyaddr_r are available */ #undef HAVE_LINUX_GETHOSTBYNAME_R_6 @@ -290,6 +293,9 @@ /* Define if you have the header file. */ #undef HAVE_GL_GLX_H +/* Define if you have the header file. */ +#undef HAVE_GL_OSMESA_H + /* Define if you have the header file. */ #undef HAVE_X11_XKBLIB_H diff --git a/include/ddraw.h b/include/ddraw.h index dba5a3102c3..d71260a3cc1 100644 --- a/include/ddraw.h +++ b/include/ddraw.h @@ -3,14 +3,14 @@ #include "windef.h" /* LARGE_INTEGER ... */ #include "wingdi.h" /* PALETTE stuff ... */ -#include "wine/obj_base.h" +#include "objbase.h" #ifdef __cplusplus extern "C" { #endif /* defined(__cplusplus) */ #ifndef DIRECTDRAW_VERSION -#define DIRECTDRAW_VERSION 0x0500 +#define DIRECTDRAW_VERSION 0x0700 #endif /* DIRECTDRAW_VERSION */ /***************************************************************************** @@ -225,6 +225,14 @@ typedef struct IDirectDrawGammaControl IDirectDrawGammaControl,*LPDIRECTDRAWGAMM #define DDGBS_CANBLT 0x00000001 #define DDGBS_ISBLTDONE 0x00000002 +/* dwFlags for IDirectDrawSurface7::GetFlipStatus */ +#define DDGFS_CANFLIP 1L +#define DDGFS_ISFLIPDONE 2L + +/* dwFlags for IDirectDrawSurface7::SetPrivateData */ +#define DDSPD_IUNKNOWNPTR 1L +#define DDSPD_VOLATILE 2L + /* DDSCAPS.dwCaps */ /* reserved1, was 3d capable */ #define DDSCAPS_RESERVED1 0x00000001 @@ -703,25 +711,35 @@ typedef struct _DDPIXELFORMAT { DWORD dwYUVBitCount; /* C: how many bits per pixel */ DWORD dwZBufferBitDepth; /* C: how many bits for z buffers */ DWORD dwAlphaBitDepth; /* C: how many bits for alpha channels*/ - } DUMMYUNIONNAME; + DWORD dwLuminanceBitCount; + DWORD dwBumpBitCount; + } DUMMYUNIONNAME1; union { DWORD dwRBitMask; /* 10: mask for red bit*/ DWORD dwYBitMask; /* 10: mask for Y bits*/ - } DUMMYUNIONNAME1; + DWORD dwStencilBitDepth; + DWORD dwLuminanceBitMask; + DWORD dwBumpDuBitMask; + } DUMMYUNIONNAME2; union { DWORD dwGBitMask; /* 14: mask for green bits*/ DWORD dwUBitMask; /* 14: mask for U bits*/ - } DUMMYUNIONNAME2; + DWORD dwZBitMask; + DWORD dwBumpDvBitMask; + } DUMMYUNIONNAME3; union { DWORD dwBBitMask; /* 18: mask for blue bits*/ DWORD dwVBitMask; /* 18: mask for V bits*/ - } DUMMYUNIONNAME3; + DWORD dwStencilBitMask; + DWORD dwBumpLuminanceBitMask; + } DUMMYUNIONNAME4; union { DWORD dwRGBAlphaBitMask; /* 1C: mask for alpha channel */ DWORD dwYUVAlphaBitMask; /* 1C: mask for alpha channel */ + DWORD dwLuminanceAlphaBitMask; DWORD dwRGBZBitMask; /* 1C: mask for Z channel */ DWORD dwYUVZBitMask; /* 1C: mask for Z channel */ - } DUMMYUNIONNAME4; + } DUMMYUNIONNAME5; /* 20: next structure */ } DDPIXELFORMAT,*LPDDPIXELFORMAT; @@ -920,19 +938,19 @@ typedef struct _DDSURFACEDESC DWORD dwFlags; /* 4: determines what fields are valid*/ DWORD dwHeight; /* 8: height of surface to be created*/ DWORD dwWidth; /* C: width of input surface*/ - LONG lPitch; /*10: distance to start of next line (return value only)*/ + union { + LONG lPitch; /* 10: distance to start of next line (return value only)*/ + DWORD dwLinearSize; + } DUMMYUNIONNAME1; DWORD dwBackBufferCount;/* 14: number of back buffers requested*/ union { DWORD dwMipMapCount;/* 18:number of mip-map levels requested*/ DWORD dwZBufferBitDepth;/*18: depth of Z buffer requested*/ DWORD dwRefreshRate;/* 18:refresh rate (used when display mode is described)*/ - } DUMMYUNIONNAME; + } DUMMYUNIONNAME2; DWORD dwAlphaBitDepth;/* 1C:depth of alpha buffer requested*/ DWORD dwReserved; /* 20:reserved*/ - union { - LPVOID lpSurface; /* 24:pointer to the associated surface memory*/ - DWORD dwLinearSize; /* 24:Formless late-allocated optimized surface size*/ - } DUMMYUNIONNAME1; + LPVOID lpSurface; /* 24:pointer to the associated surface memory*/ DDCOLORKEY ddckCKDestOverlay;/* 28: CK for dest overlay use*/ DDCOLORKEY ddckCKDestBlt; /* 30: CK for destination blt use*/ DDCOLORKEY ddckCKSrcOverlay;/* 38: CK for source overlay use*/ @@ -950,13 +968,13 @@ typedef struct _DDSURFACEDESC2 union { LONG lPitch; /*10: distance to start of next line (return value only)*/ DWORD dwLinearSize; /*10: formless late-allocated optimized surface size */ - } DUMMYUNIONNAME; + } DUMMYUNIONNAME1; DWORD dwBackBufferCount;/* 14: number of back buffers requested*/ union { DWORD dwMipMapCount;/* 18:number of mip-map levels requested*/ DWORD dwRefreshRate;/* 18:refresh rate (used when display mode is described)*/ DWORD dwSrcVBHandle;/* 18:source used in VB::Optimize */ - } DUMMYUNIONNAME2; + } DUMMYUNIONNAME2; DWORD dwAlphaBitDepth;/* 1C:depth of alpha buffer requested*/ DWORD dwReserved; /* 20:reserved*/ LPVOID lpSurface; /* 24:pointer to the associated surface memory*/ @@ -964,16 +982,16 @@ typedef struct _DDSURFACEDESC2 DDCOLORKEY ddckCKDestOverlay; /* 28: CK for dest overlay use*/ DWORD dwEmptyFaceColor; /* 28: color for empty cubemap faces */ } DUMMYUNIONNAME3; - DDCOLORKEY ddckCKDestBlt; /* 2C: CK for destination blt use*/ - DDCOLORKEY ddckCKSrcOverlay;/* 30: CK for source overlay use*/ - DDCOLORKEY ddckCKSrcBlt; /* 34: CK for source blt use*/ + DDCOLORKEY ddckCKDestBlt; /* 30: CK for destination blt use*/ + DDCOLORKEY ddckCKSrcOverlay;/* 38: CK for source overlay use*/ + DDCOLORKEY ddckCKSrcBlt; /* 40: CK for source blt use*/ union { - DDPIXELFORMAT ddpfPixelFormat;/* 38: pixel format description of the surface*/ - DWORD dwFVF; /* 38: vertex format description of vertex buffers */ + DDPIXELFORMAT ddpfPixelFormat;/* 48: pixel format description of the surface*/ + DWORD dwFVF; /* 48: vertex format description of vertex buffers */ } DUMMYUNIONNAME4; - DDSCAPS2 ddsCaps; /* 3C: DDraw surface caps */ - DWORD dwTextureStage; /* 40: stage in multitexture cascade */ + DDSCAPS2 ddsCaps; /* 68: DDraw surface caps */ + DWORD dwTextureStage; /* 78: stage in multitexture cascade */ } DDSURFACEDESC2,*LPDDSURFACEDESC2; /* DDCOLORCONTROL.dwFlags */ @@ -1003,8 +1021,9 @@ typedef BOOL CALLBACK (*LPDDENUMCALLBACKW)(GUID *, LPWSTR, LPWSTR, LPVOID); DECL_WINELIB_TYPE_AW(LPDDENUMCALLBACK) typedef HRESULT CALLBACK (*LPDDENUMMODESCALLBACK)(LPDDSURFACEDESC, LPVOID); -typedef HRESULT CALLBACK (*LPDDENUMMODESCALLBACK7)(LPDDSURFACEDESC2, LPVOID); +typedef HRESULT CALLBACK (*LPDDENUMMODESCALLBACK2)(LPDDSURFACEDESC2, LPVOID); typedef HRESULT CALLBACK (*LPDDENUMSURFACESCALLBACK)(LPDIRECTDRAWSURFACE, LPDDSURFACEDESC, LPVOID); +typedef HRESULT CALLBACK (*LPDDENUMSURFACESCALLBACK2)(LPDIRECTDRAWSURFACE4, LPDDSURFACEDESC2, LPVOID); typedef HRESULT CALLBACK (*LPDDENUMSURFACESCALLBACK7)(LPDIRECTDRAWSURFACE7, LPDDSURFACEDESC2, LPVOID); typedef BOOL CALLBACK (*LPDDENUMCALLBACKEXA)(GUID *, LPSTR, LPSTR, LPVOID, HMONITOR); @@ -1020,6 +1039,10 @@ HRESULT WINAPI DirectDrawEnumerateExW( LPDDENUMCALLBACKEXW lpCallback, LPVOID lp #define DDENUM_DETACHEDSECONDARYDEVICES 0x00000002 #define DDENUM_NONDISPLAYDEVICES 0x00000004 +/* flags for DirectDrawCreate or IDirectDraw::Initialize */ +#define DDCREATE_HARDWAREONLY 1L +#define DDCREATE_EMULATIONONLY 2L + typedef struct _DDBLTFX { DWORD dwSize; /* size of structure */ @@ -1036,13 +1059,13 @@ typedef struct _DDBLTFX { DWORD dwZDestConst; /* Constant to use as Z buffer for dest */ LPDIRECTDRAWSURFACE lpDDSZBufferDest; /* Surface to use as Z buffer for dest */ - } DUMMYUNIONNAME; + } DUMMYUNIONNAME1; DWORD dwZSrcConstBitDepth; /* Bit depth used to specify Z constant for source */ union { DWORD dwZSrcConst; /* Constant to use as Z buffer for src */ LPDIRECTDRAWSURFACE lpDDSZBufferSrc; /* Surface to use as Z buffer for src */ - } DUMMYUNIONNAME1; + } DUMMYUNIONNAME2; DWORD dwAlphaEdgeBlendBitDepth; /* Bit depth used to specify constant for alpha edge blend */ DWORD dwAlphaEdgeBlend; /* Alpha for edge blending */ DWORD dwReserved; @@ -1051,20 +1074,20 @@ typedef struct _DDBLTFX { DWORD dwAlphaDestConst; /* Constant to use as Alpha Channel */ LPDIRECTDRAWSURFACE lpDDSAlphaDest; /* Surface to use as Alpha Channel */ - } DUMMYUNIONNAME2; + } DUMMYUNIONNAME3; DWORD dwAlphaSrcConstBitDepth; /* Bit depth used to specify alpha constant for source */ union { DWORD dwAlphaSrcConst; /* Constant to use as Alpha Channel */ LPDIRECTDRAWSURFACE lpDDSAlphaSrc; /* Surface to use as Alpha Channel */ - } DUMMYUNIONNAME3; + } DUMMYUNIONNAME4; union { DWORD dwFillColor; /* color in RGB or Palettized */ DWORD dwFillDepth; /* depth value for z-buffer */ DWORD dwFillPixel; /* pixel val for RGBA or RGBZ */ LPDIRECTDRAWSURFACE lpDDSPattern; /* Surface to use as pattern */ - } DUMMYUNIONNAME4; + } DUMMYUNIONNAME5; DDCOLORKEY ddckDestColorkey; /* DestColorkey override */ DDCOLORKEY ddckSrcColorkey; /* SrcColorkey override */ } DDBLTFX,*LPDDBLTFX; @@ -1100,13 +1123,13 @@ typedef struct _DDOVERLAYFX { DWORD dwAlphaDestConst; /* Constant to use as alpha channel for dest */ LPDIRECTDRAWSURFACE lpDDSAlphaDest; /* Surface to use as alpha channel for dest */ - } DUMMYUNIONNAME; + } DUMMYUNIONNAME1; DWORD dwAlphaSrcConstBitDepth; /* Bit depth used to specify alpha constant for source */ union { DWORD dwAlphaSrcConst; /* Constant to use as alpha channel for src */ LPDIRECTDRAWSURFACE lpDDSAlphaSrc; /* Surface to use as alpha channel for src */ - } DUMMYUNIONNAME1; + } DUMMYUNIONNAME2; DDCOLORKEY dckDestColorkey; /* DestColorkey override */ DDCOLORKEY dckSrcColorkey; /* DestColorkey override */ DWORD dwDDFX; /* Overlay FX */ @@ -1340,14 +1363,37 @@ ICOM_DEFINE(IDirectDraw2,IUnknown) */ #define ICOM_INTERFACE IDirectDraw4 #define IDirectDraw4_METHODS \ - ICOM_METHOD2(HRESULT,GetSurfaceFromDC, HDC,, LPDIRECTDRAWSURFACE*,) \ +/*0c*/ ICOM_METHOD (HRESULT,Compact) \ +/*10*/ ICOM_METHOD3(HRESULT,CreateClipper, DWORD,dwFlags, LPDIRECTDRAWCLIPPER*,lplpDDClipper, IUnknown*,pUnkOuter) \ +/*14*/ ICOM_METHOD4(HRESULT,CreatePalette, DWORD,dwFlags, LPPALETTEENTRY,lpColorTable, LPDIRECTDRAWPALETTE*,lplpDDPalette, IUnknown*,pUnkOuter) \ +/*18*/ ICOM_METHOD3(HRESULT,CreateSurface, LPDDSURFACEDESC2,lpDDSurfaceDesc, LPDIRECTDRAWSURFACE4*,lplpDDSurface, IUnknown*,pUnkOuter) \ +/*1c*/ ICOM_METHOD2(HRESULT,DuplicateSurface, LPDIRECTDRAWSURFACE4,lpDDSurface, LPDIRECTDRAWSURFACE4*,lplpDupDDSurface) \ +/*20*/ ICOM_METHOD4(HRESULT,EnumDisplayModes, DWORD,dwFlags, LPDDSURFACEDESC2,lpDDSurfaceDesc, LPVOID,lpContext, LPDDENUMMODESCALLBACK2,lpEnumModesCallback) \ +/*24*/ ICOM_METHOD4(HRESULT,EnumSurfaces, DWORD,dwFlags, LPDDSURFACEDESC2,lpDDSD, LPVOID,lpContext, LPDDENUMSURFACESCALLBACK2,lpEnumSurfacesCallback) \ +/*28*/ ICOM_METHOD (HRESULT,FlipToGDISurface) \ +/*2c*/ ICOM_METHOD2(HRESULT,GetCaps, LPDDCAPS,lpDDDriverCaps, LPDDCAPS,lpDDHELCaps) \ +/*30*/ ICOM_METHOD1(HRESULT,GetDisplayMode, LPDDSURFACEDESC2,lpDDSurfaceDesc) \ +/*34*/ ICOM_METHOD2(HRESULT,GetFourCCCodes, LPDWORD,lpNumCodes, LPDWORD,lpCodes) \ +/*38*/ ICOM_METHOD1(HRESULT,GetGDISurface, LPDIRECTDRAWSURFACE4*,lplpGDIDDSurface) \ +/*3c*/ ICOM_METHOD1(HRESULT,GetMonitorFrequency, LPDWORD,lpdwFrequency) \ +/*40*/ ICOM_METHOD1(HRESULT,GetScanLine, LPDWORD,lpdwScanLine) \ +/*44*/ ICOM_METHOD1(HRESULT,GetVerticalBlankStatus, BOOL*,lpbIsInVB) \ +/*48*/ ICOM_METHOD1(HRESULT,Initialize, GUID*,lpGUID) \ +/*4c*/ ICOM_METHOD (HRESULT,RestoreDisplayMode) \ +/*50*/ ICOM_METHOD2(HRESULT,SetCooperativeLevel, HWND,hWnd, DWORD,dwFlags) \ +/*54*/ ICOM_METHOD5(HRESULT,SetDisplayMode, DWORD,dwWidth, DWORD,dwHeight, DWORD,dwBPP, DWORD,dwRefreshRate, DWORD,dwFlags) \ +/*58*/ ICOM_METHOD2(HRESULT,WaitForVerticalBlank, DWORD,dwFlags, HANDLE,hEvent) \ + /* added in v2 */ \ +/*5c*/ ICOM_METHOD3(HRESULT,GetAvailableVidMem, LPDDSCAPS2,lpDDCaps, LPDWORD,lpdwTotal, LPDWORD,lpdwFree) \ + /* added in v4 */ \ + ICOM_METHOD2(HRESULT,GetSurfaceFromDC, HDC,, LPDIRECTDRAWSURFACE4*,) \ ICOM_METHOD (HRESULT,RestoreAllSurfaces) \ ICOM_METHOD (HRESULT,TestCooperativeLevel) \ ICOM_METHOD2(HRESULT,GetDeviceIdentifier, LPDDDEVICEIDENTIFIER,, DWORD,) #define IDirectDraw4_IMETHODS \ - IDirectDraw2_IMETHODS \ + IUnknown_IMETHODS \ IDirectDraw4_METHODS -ICOM_DEFINE(IDirectDraw4,IDirectDraw2) +ICOM_DEFINE(IDirectDraw4,IUnknown) #undef ICOM_INTERFACE /*** IUnknown methods ***/ @@ -1378,7 +1424,7 @@ ICOM_DEFINE(IDirectDraw4,IDirectDraw2) /*** IDirectDraw2 methods ***/ #define IDirectDraw4_GetAvailableVidMem(p,a,b,c) ICOM_CALL3(GetAvailableVidMem,p,a,b,c) /*** IDirectDraw4 methods ***/ -#define IDirectDraw4_GetSurfaceFromDC(p,a,b) ICOM_CALL2(GetSurfaceFromDC,p,a,b,c) +#define IDirectDraw4_GetSurfaceFromDC(p,a,b) ICOM_CALL2(GetSurfaceFromDC,p,a,b) #define IDirectDraw4_RestoreAllSurfaces(pc) ICOM_CALL (RestoreAllSurfaces,p) #define IDirectDraw4_TestCooperativeLevel(p) ICOM_CALL (TestCooperativeLevel,p) #define IDirectDraw4_GetDeviceIdentifier(p,a,b) ICOM_CALL2(GetDeviceIdentifier,p,a,b) @@ -1397,7 +1443,7 @@ ICOM_DEFINE(IDirectDraw4,IDirectDraw2) /*14*/ ICOM_METHOD4(HRESULT,CreatePalette, DWORD,dwFlags, LPPALETTEENTRY,lpColorTable, LPDIRECTDRAWPALETTE*,lplpDDPalette, IUnknown*,pUnkOuter) \ /*18*/ ICOM_METHOD3(HRESULT,CreateSurface, LPDDSURFACEDESC2,lpDDSurfaceDesc, LPDIRECTDRAWSURFACE7*,lplpDDSurface, IUnknown*,pUnkOuter) \ /*1c*/ ICOM_METHOD2(HRESULT,DuplicateSurface, LPDIRECTDRAWSURFACE7,lpDDSurface, LPDIRECTDRAWSURFACE7*,lplpDupDDSurface) \ -/*20*/ ICOM_METHOD4(HRESULT,EnumDisplayModes, DWORD,dwFlags, LPDDSURFACEDESC2,lpDDSurfaceDesc, LPVOID,lpContext, LPDDENUMMODESCALLBACK7,lpEnumModesCallback) \ +/*20*/ ICOM_METHOD4(HRESULT,EnumDisplayModes, DWORD,dwFlags, LPDDSURFACEDESC2,lpDDSurfaceDesc, LPVOID,lpContext, LPDDENUMMODESCALLBACK2,lpEnumModesCallback) \ /*24*/ ICOM_METHOD4(HRESULT,EnumSurfaces, DWORD,dwFlags, LPDDSURFACEDESC2,lpDDSD, LPVOID,lpContext, LPDDENUMSURFACESCALLBACK7,lpEnumSurfacesCallback) \ /*28*/ ICOM_METHOD (HRESULT,FlipToGDISurface) \ /*2c*/ ICOM_METHOD2(HRESULT,GetCaps, LPDDCAPS,lpDDDriverCaps, LPDDCAPS,lpDDHELCaps) \ @@ -1418,7 +1464,7 @@ ICOM_DEFINE(IDirectDraw4,IDirectDraw2) /*60*/ ICOM_METHOD2(HRESULT,GetSurfaceFromDC, HDC,, LPDIRECTDRAWSURFACE7*,) \ /*64*/ ICOM_METHOD (HRESULT,RestoreAllSurfaces) \ /*68*/ ICOM_METHOD (HRESULT,TestCooperativeLevel) \ -/*6c*/ ICOM_METHOD2(HRESULT,GetDeviceIdentifier, LPDDDEVICEIDENTIFIER,, DWORD,) \ +/*6c*/ ICOM_METHOD2(HRESULT,GetDeviceIdentifier, LPDDDEVICEIDENTIFIER2,, DWORD,) \ /* added in v7 */ \ /*70*/ ICOM_METHOD3(HRESULT,StartModeTest, LPSIZE,, DWORD,, DWORD,) \ /*74*/ ICOM_METHOD2(HRESULT,EvaluateMode, DWORD,, DWORD *,) @@ -1456,8 +1502,8 @@ ICOM_DEFINE(IDirectDraw7,IUnknown) /*** added in IDirectDraw2 ***/ #define IDirectDraw7_GetAvailableVidMem(p,a,b,c) ICOM_CALL3(GetAvailableVidMem,p,a,b,c) /*** added in IDirectDraw4 ***/ -#define IDirectDraw7_GetSurfaceFromDC(p,a,b) ICOM_CALL2(GetSurfaceFromDC,p,a,b,c) -#define IDirectDraw7_RestoreAllSurfaces(pc) ICOM_CALL (RestoreAllSurfaces,p) +#define IDirectDraw7_GetSurfaceFromDC(p,a,b) ICOM_CALL2(GetSurfaceFromDC,p,a,b) +#define IDirectDraw7_RestoreAllSurfaces(p) ICOM_CALL (RestoreAllSurfaces,p) #define IDirectDraw7_TestCooperativeLevel(p) ICOM_CALL (TestCooperativeLevel,p) #define IDirectDraw7_GetDeviceIdentifier(p,a,b) ICOM_CALL2(GetDeviceIdentifier,p,a,b) /*** added in IDirectDraw 7 ***/ @@ -1539,7 +1585,7 @@ ICOM_DEFINE(IDirectDrawSurface,IUnknown) #define IDirectDrawSurface_Lock(p,a,b,c,d) ICOM_CALL4(Lock,p,a,b,c,d) #define IDirectDrawSurface_ReleaseDC(p,a) ICOM_CALL1(ReleaseDC,p,a) #define IDirectDrawSurface_Restore(p) ICOM_CALL (Restore,p) -#define IDirectDrawSurface_SetClipper(p,a,b) ICOM_CALL1(SetClipper,p,a,b) +#define IDirectDrawSurface_SetClipper(p,a) ICOM_CALL1(SetClipper,p,a) #define IDirectDrawSurface_SetColorKey(p,a,b) ICOM_CALL2(SetColorKey,p,a,b) #define IDirectDrawSurface_SetOverlayPosition(p,a,b) ICOM_CALL2(SetOverlayPosition,p,a,b) #define IDirectDrawSurface_SetPalette(p,a) ICOM_CALL1(SetPalette,p,a) @@ -1629,8 +1675,8 @@ ICOM_DEFINE(IDirectDrawSurface2,IUnknown) #define IDirectDrawSurface2_IsLost(p) ICOM_CALL (IsLost,p) #define IDirectDrawSurface2_Lock(p,a,b,c,d) ICOM_CALL4(Lock,p,a,b,c,d) #define IDirectDrawSurface2_ReleaseDC(p,a) ICOM_CALL1(ReleaseDC,p,a) -#define IDirectDrawSurface2_Restore(p,a,b) ICOM_CALL (Restore,p,a,b) -#define IDirectDrawSurface2_SetClipper(p,a,b) ICOM_CALL1(SetClipper,p,a,b) +#define IDirectDrawSurface2_Restore(p) ICOM_CALL (Restore,p) +#define IDirectDrawSurface2_SetClipper(p,a) ICOM_CALL1(SetClipper,p,a) #define IDirectDrawSurface2_SetColorKey(p,a,b) ICOM_CALL2(SetColorKey,p,a,b) #define IDirectDrawSurface2_SetOverlayPosition(p,a,b) ICOM_CALL2(SetOverlayPosition,p,a,b) #define IDirectDrawSurface2_SetPalette(p,a) ICOM_CALL1(SetPalette,p,a) @@ -1726,8 +1772,8 @@ ICOM_DEFINE(IDirectDrawSurface3,IUnknown) #define IDirectDrawSurface3_IsLost(p) ICOM_CALL (IsLost,p) #define IDirectDrawSurface3_Lock(p,a,b,c,d) ICOM_CALL4(Lock,p,a,b,c,d) #define IDirectDrawSurface3_ReleaseDC(p,a) ICOM_CALL1(ReleaseDC,p,a) -#define IDirectDrawSurface3_Restore(p,a,b) ICOM_CALL (Restore,p,a,b) -#define IDirectDrawSurface3_SetClipper(p,a,b) ICOM_CALL1(SetClipper,p,a,b) +#define IDirectDrawSurface3_Restore(p) ICOM_CALL (Restore,p) +#define IDirectDrawSurface3_SetClipper(p,a) ICOM_CALL1(SetClipper,p,a) #define IDirectDrawSurface3_SetColorKey(p,a,b) ICOM_CALL2(SetColorKey,p,a,b) #define IDirectDrawSurface3_SetOverlayPosition(p,a,b) ICOM_CALL2(SetOverlayPosition,p,a,b) #define IDirectDrawSurface3_SetPalette(p,a) ICOM_CALL1(SetPalette,p,a) @@ -1784,7 +1830,7 @@ ICOM_DEFINE(IDirectDrawSurface3,IUnknown) ICOM_METHOD2(HRESULT,SetColorKey, DWORD,dwFlags, LPDDCOLORKEY,lpDDColorKey) \ ICOM_METHOD2(HRESULT,SetOverlayPosition, LONG,lX, LONG,lY) \ ICOM_METHOD1(HRESULT,SetPalette, LPDIRECTDRAWPALETTE,lpDDPalette) \ - ICOM_METHOD1(HRESULT,Unlock, LPVOID,lpSurfaceData) \ + ICOM_METHOD1(HRESULT,Unlock, LPRECT,lpSurfaceData) \ ICOM_METHOD5(HRESULT,UpdateOverlay, LPRECT,lpSrcRect, LPDIRECTDRAWSURFACE4,lpDDDestSurface, LPRECT,lpDestRect, DWORD,dwFlags, LPDDOVERLAYFX,lpDDOverlayFx) \ ICOM_METHOD1(HRESULT,UpdateOverlayDisplay, DWORD,dwFlags) \ ICOM_METHOD2(HRESULT,UpdateOverlayZOrder, DWORD,dwFlags, LPDIRECTDRAWSURFACE4,lpDDSReference) \ @@ -1835,8 +1881,8 @@ ICOM_DEFINE(IDirectDrawSurface4,IUnknown) #define IDirectDrawSurface4_IsLost(p) ICOM_CALL (IsLost,p) #define IDirectDrawSurface4_Lock(p,a,b,c,d) ICOM_CALL4(Lock,p,a,b,c,d) #define IDirectDrawSurface4_ReleaseDC(p,a) ICOM_CALL1(ReleaseDC,p,a) -#define IDirectDrawSurface4_Restore(p,a,b) ICOM_CALL (Restore,p,a,b) -#define IDirectDrawSurface4_SetClipper(p,a,b) ICOM_CALL1(SetClipper,p,a,b) +#define IDirectDrawSurface4_Restore(p) ICOM_CALL (Restore,p) +#define IDirectDrawSurface4_SetClipper(p,a) ICOM_CALL1(SetClipper,p,a) #define IDirectDrawSurface4_SetColorKey(p,a,b) ICOM_CALL2(SetColorKey,p,a,b) #define IDirectDrawSurface4_SetOverlayPosition(p,a,b) ICOM_CALL2(SetOverlayPosition,p,a,b) #define IDirectDrawSurface4_SetPalette(p,a) ICOM_CALL1(SetPalette,p,a) @@ -1849,7 +1895,7 @@ ICOM_DEFINE(IDirectDrawSurface4,IUnknown) #define IDirectDrawSurface4_PageLock(p,a) ICOM_CALL1(PageLock,p,a) #define IDirectDrawSurface4_PageUnlock(p,a) ICOM_CALL1(PageUnlock,p,a) /*** IDirectDrawSurface3 methods ***/ -#define IDirectDrawSurface4_SetSurfaceDesc(p,a) ICOM_CALL(SetSurfaceDesc,p,a) +#define IDirectDrawSurface4_SetSurfaceDesc(p,a,b) ICOM_CALL2(SetSurfaceDesc,p,a,b) /*** IDirectDrawSurface4 methods ***/ #define IDirectDrawSurface4_SetPrivateData(p,a,b,c,d) ICOM_CALL4(SetPrivateData,p,a,b,c,d) #define IDirectDrawSurface4_GetPrivateData(p,a,b,c) ICOM_CALL3(GetPrivateData,p,a,b,c) @@ -1869,8 +1915,8 @@ ICOM_DEFINE(IDirectDrawSurface4,IUnknown) ICOM_METHOD3(HRESULT,BltBatch, LPDDBLTBATCH,lpDDBltBatch, DWORD,dwCount, DWORD,dwFlags) \ ICOM_METHOD5(HRESULT,BltFast, DWORD,dwX, DWORD,dwY, LPDIRECTDRAWSURFACE7,lpDDSrcSurface, LPRECT,lpSrcRect, DWORD,dwTrans) \ ICOM_METHOD2(HRESULT,DeleteAttachedSurface, DWORD,dwFlags, LPDIRECTDRAWSURFACE7,lpDDSAttachedSurface) \ - ICOM_METHOD2(HRESULT,EnumAttachedSurfaces, LPVOID,lpContext, LPDDENUMSURFACESCALLBACK,lpEnumSurfacesCallback) \ - ICOM_METHOD3(HRESULT,EnumOverlayZOrders, DWORD,dwFlags, LPVOID,lpContext, LPDDENUMSURFACESCALLBACK,lpfnCallback) \ + ICOM_METHOD2(HRESULT,EnumAttachedSurfaces, LPVOID,lpContext, LPDDENUMSURFACESCALLBACK7,lpEnumSurfacesCallback) \ + ICOM_METHOD3(HRESULT,EnumOverlayZOrders, DWORD,dwFlags, LPVOID,lpContext, LPDDENUMSURFACESCALLBACK7,lpfnCallback) \ ICOM_METHOD2(HRESULT,Flip, LPDIRECTDRAWSURFACE7,lpDDSurfaceTargetOverride, DWORD,dwFlags) \ ICOM_METHOD2(HRESULT,GetAttachedSurface, LPDDSCAPS2,lpDDSCaps, LPDIRECTDRAWSURFACE7*,lplpDDAttachedSurface) \ ICOM_METHOD1(HRESULT,GetBltStatus, DWORD,dwFlags) \ @@ -1892,7 +1938,7 @@ ICOM_DEFINE(IDirectDrawSurface4,IUnknown) ICOM_METHOD2(HRESULT,SetColorKey, DWORD,dwFlags, LPDDCOLORKEY,lpDDColorKey) \ ICOM_METHOD2(HRESULT,SetOverlayPosition, LONG,lX, LONG,lY) \ ICOM_METHOD1(HRESULT,SetPalette, LPDIRECTDRAWPALETTE,lpDDPalette) \ - ICOM_METHOD1(HRESULT,Unlock, LPVOID,lpSurfaceData) \ + ICOM_METHOD1(HRESULT,Unlock, LPRECT,lpSurfaceData) \ ICOM_METHOD5(HRESULT,UpdateOverlay, LPRECT,lpSrcRect, LPDIRECTDRAWSURFACE7,lpDDDestSurface, LPRECT,lpDestRect, DWORD,dwFlags, LPDDOVERLAYFX,lpDDOverlayFx) \ ICOM_METHOD1(HRESULT,UpdateOverlayDisplay, DWORD,dwFlags) \ ICOM_METHOD2(HRESULT,UpdateOverlayZOrder, DWORD,dwFlags, LPDIRECTDRAWSURFACE7,lpDDSReference) \ @@ -1919,6 +1965,61 @@ ICOM_DEFINE(IDirectDrawSurface4,IUnknown) ICOM_DEFINE(IDirectDrawSurface7,IUnknown) #undef ICOM_INTERFACE + /*** IUnknown methods ***/ +#define IDirectDrawSurface7_QueryInterface(p,a,b) ICOM_CALL2(QueryInterface,p,a,b) +#define IDirectDrawSurface7_AddRef(p) ICOM_CALL (AddRef,p) +#define IDirectDrawSurface7_Release(p) ICOM_CALL (Release,p) +/*** IDirectDrawSurface (almost) methods ***/ +#define IDirectDrawSurface7_AddAttachedSurface(p,a) ICOM_CALL1(AddAttachedSurface,p,a) +#define IDirectDrawSurface7_AddOverlayDirtyRect(p,a) ICOM_CALL1(AddOverlayDirtyRect,p,a) +#define IDirectDrawSurface7_Blt(p,a,b,c,d,e) ICOM_CALL5(Blt,p,a,b,c,d,e) +#define IDirectDrawSurface7_BltBatch(p,a,b,c) ICOM_CALL3(BltBatch,p,a,b,c) +#define IDirectDrawSurface7_BltFast(p,a,b,c,d,e) ICOM_CALL5(BltFast,p,a,b,c,d,e) +#define IDirectDrawSurface7_DeleteAttachedSurface(p,a,b) ICOM_CALL2(DeleteAttachedSurface,p,a,b) +#define IDirectDrawSurface7_EnumAttachedSurfaces(p,a,b) ICOM_CALL2(EnumAttachedSurfaces,p,a,b) +#define IDirectDrawSurface7_EnumOverlayZOrders(p,a,b,c) ICOM_CALL3(EnumOverlayZOrders,p,a,b,c) +#define IDirectDrawSurface7_Flip(p,a,b) ICOM_CALL2(Flip,p,a,b) +#define IDirectDrawSurface7_GetAttachedSurface(p,a,b) ICOM_CALL2(GetAttachedSurface,p,a,b) +#define IDirectDrawSurface7_GetBltStatus(p,a) ICOM_CALL1(GetBltStatus,p,a) +#define IDirectDrawSurface7_GetCaps(p,a) ICOM_CALL1(GetCaps,p,a) +#define IDirectDrawSurface7_GetClipper(p,a) ICOM_CALL1(GetClipper,p,a) +#define IDirectDrawSurface7_GetColorKey(p,a,b) ICOM_CALL2(GetColorKey,p,a,b) +#define IDirectDrawSurface7_GetDC(p,a) ICOM_CALL1(GetDC,p,a) +#define IDirectDrawSurface7_GetFlipStatus(p,a) ICOM_CALL1(GetFlipStatus,p,a) +#define IDirectDrawSurface7_GetOverlayPosition(p,a,b) ICOM_CALL2(GetOverlayPosition,p,a,b) +#define IDirectDrawSurface7_GetPalette(p,a) ICOM_CALL1(GetPalette,p,a) +#define IDirectDrawSurface7_GetPixelFormat(p,a) ICOM_CALL1(GetPixelFormat,p,a) +#define IDirectDrawSurface7_GetSurfaceDesc(p,a) ICOM_CALL1(GetSurfaceDesc,p,a) +#define IDirectDrawSurface7_Initialize(p,a,b) ICOM_CALL2(Initialize,p,a,b) +#define IDirectDrawSurface7_IsLost(p) ICOM_CALL (IsLost,p) +#define IDirectDrawSurface7_Lock(p,a,b,c,d) ICOM_CALL4(Lock,p,a,b,c,d) +#define IDirectDrawSurface7_ReleaseDC(p,a) ICOM_CALL1(ReleaseDC,p,a) +#define IDirectDrawSurface7_Restore(p) ICOM_CALL (Restore,p) +#define IDirectDrawSurface7_SetClipper(p,a) ICOM_CALL1(SetClipper,p,a) +#define IDirectDrawSurface7_SetColorKey(p,a,b) ICOM_CALL2(SetColorKey,p,a,b) +#define IDirectDrawSurface7_SetOverlayPosition(p,a,b) ICOM_CALL2(SetOverlayPosition,p,a,b) +#define IDirectDrawSurface7_SetPalette(p,a) ICOM_CALL1(SetPalette,p,a) +#define IDirectDrawSurface7_Unlock(p,a) ICOM_CALL1(Unlock,p,a) +#define IDirectDrawSurface7_UpdateOverlay(p,a,b,c,d,e) ICOM_CALL5(UpdateOverlay,p,a,b,c,d,e) +#define IDirectDrawSurface7_UpdateOverlayDisplay(p,a) ICOM_CALL1(UpdateOverlayDisplay,p,a) +#define IDirectDrawSurface7_UpdateOverlayZOrder(p,a,b) ICOM_CALL2(UpdateOverlayZOrder,p,a,b) +/*** IDirectDrawSurface2 methods ***/ +#define IDirectDrawSurface7_GetDDInterface(p,a) ICOM_CALL1(GetDDInterface,p,a) +#define IDirectDrawSurface7_PageLock(p,a) ICOM_CALL1(PageLock,p,a) +#define IDirectDrawSurface7_PageUnlock(p,a) ICOM_CALL1(PageUnlock,p,a) +/*** IDirectDrawSurface3 methods ***/ +#define IDirectDrawSurface7_SetSurfaceDesc(p,a,b) ICOM_CALL2(SetSurfaceDesc,p,a,b) +/*** IDirectDrawSurface4 methods ***/ +#define IDirectDrawSurface7_SetPrivateData(p,a,b,c,d) ICOM_CALL4(SetPrivateData,p,a,b,c,d) +#define IDirectDrawSurface7_GetPrivateData(p,a,b,c) ICOM_CALL3(GetPrivateData,p,a,b,c) +#define IDirectDrawSurface7_FreePrivateData(p,a) ICOM_CALL1(FreePrivateData,p,a) +#define IDirectDrawSurface7_GetUniquenessValue(p,a) ICOM_CALL1(GetUniquenessValue,p,a) +#define IDirectDrawSurface7_ChangeUniquenessValue(p) ICOM_CALL (ChangeUniquenessValue,p) +/*** IDirectDrawSurface7 methods ***/ +#define IDirectDrawSurface7_SetPriority(p,a) ICOM_CALL1(SetPriority,p,a) +#define IDirectDrawSurface7_GetPriority(p,a) ICOM_CALL1(GetPriority,p,a) +#define IDirectDrawSurface7_SetLOD(p,a) ICOM_CALL1(SetLOD,p,a) +#define IDirectDrawSurface7_GetLOD(p,a) ICOM_CALL1(GetLOD,p,a) /***************************************************************************** * IDirectDrawColorControl interface diff --git a/msdos/vga.c b/msdos/vga.c index ff70d0f359c..84c3dabcc37 100644 --- a/msdos/vga.c +++ b/msdos/vga.c @@ -100,7 +100,7 @@ int VGA_GetMode(unsigned*Height,unsigned*Width,unsigned*Depth) if (!lpddsurf) return 1; if (Height) *Height=sdesc.dwHeight; if (Width) *Width=sdesc.dwWidth; - if (Depth) *Depth=sdesc.ddpfPixelFormat.u.dwRGBBitCount; + if (Depth) *Depth=sdesc.ddpfPixelFormat.u1.dwRGBBitCount; return 0; } @@ -147,16 +147,16 @@ LPSTR VGA_Lock(unsigned*Pitch,unsigned*Height,unsigned*Width,unsigned*Depth) ERR("could not lock surface!\n"); return NULL; } - if (Pitch) *Pitch=sdesc.lPitch; + if (Pitch) *Pitch=sdesc.u1.lPitch; if (Height) *Height=sdesc.dwHeight; if (Width) *Width=sdesc.dwWidth; - if (Depth) *Depth=sdesc.ddpfPixelFormat.u.dwRGBBitCount; - return sdesc.u1.lpSurface; + if (Depth) *Depth=sdesc.ddpfPixelFormat.u1.dwRGBBitCount; + return sdesc.lpSurface; } void VGA_Unlock(void) { - IDirectDrawSurface_Unlock(lpddsurf,sdesc.u1.lpSurface); + IDirectDrawSurface_Unlock(lpddsurf,sdesc.lpSurface); } /*** TEXT MODE ***/