Sign in Join

Live chat for Free Pascal, Lazarus, Delphi and every Pascal programmer.

Mailing lists / fpc-pascal / 2005-04

Re: FPC and GTK2: problems with GTKCombo

3 messages · 2 people · –

Reply by email Subscribe to this list Your subscription

Read-only archive. Use j and k to move between messages.

Jan Je/lowicki

Hello all,

Today I have localised a problem with GtkCombo; there is a minimal program that could reproduce crash of GtkCombo in W32 environment. I cannot see any bug, there are just standard instructions; maybe I am wrong? or rather the bug is in the GTK binary for Windows? or even in FPC bind?

Tested with GTK+2.4,14, 2.4.7, 2.2.4, 2.0.7 binaries in win2000 and wine20040914 with w2k emulation.

Sory for yesterday's sample. It wasn't too hard to clear it. Here is the right code -- at least possible to analysis for anyone:

program samp;
uses
  glib2, gdk2, gtk2;
const
  n = 5;
var
  items: array[1..n] of pchar;
const
  current_item: integer = 0;
var
  e: pGTKWidget;
  function sample_stop(w: pGTKWidget; data: pointer): longbool; cdecl;
  begin
writeln('inside: ---------------');
writeln('postselected: "', gtk_entry_get_text(pGTKEntry(e)), '"');
    gtk_widget_destroy(data);
    gtk_main_quit();
    result := false;
  end;
var
  d: pGTKWidget;
  h: pGTKWidget;
  b: pGTKWidget;
  c: pGTKWidget;
  g: pGList;
  l: pGTKWidget;
var
  i: integer;
begin
  gtk_init(@argc, @argv);
  items[1] := 'field 1'#0;
  items[2] := 'field 2'#0;
  items[3] := 'field 3'#0;
  items[4] := 'field 4'#0;
  items[5] := 'last field'#0;
  current_item := 3;
writeln('starting: --------------');
  d := gtk_dialog_new;
  gtk_window_set_title(pGTKWindow(d), 'A sample dialog');
  h := pGTKDialog(d)^.vbox;
  l := gtk_label_new('A sample Combo list');
  gtk_widget_show(l);
  gtk_box_pack_start(pGTKBox(h), l, false, false, 0);
  c := gtk_combo_new();
  e := pGTKCombo(c)^.entry;
  writeln('is Entry nil? ', e=nil);
  g := nil;
  for i := 1 to n do
    g := g_list_append(g, items[i]);
  gtk_combo_set_popdown_strings(pgtkcombo(c), g);
  gtk_entry_set_text(pgtkentry(e), items[current_item]);
writeln('before: --------------');
writeln('preselected:  "', gtk_entry_get_text(pGTKEntry(e)), '"');
  gtk_combo_set_value_in_list(pgtkcombo(c), true, false);
  gtk_entry_set_editable(pgtkentry(e), false);
  gtk_box_pack_start(pGTKBox(h), c, false, false, 0);
  gtk_widget_show(c);
  b := gtk_button_new_with_label(' OK ');
  gtk_signal_connect(pGTKObject(b), 'clicked', @sample_stop, d);
  gtk_box_pack_start(pGTKBox(h), b, false, false, 0);
  gtk_widget_show(b);
  gtk_widget_show(d);
  gtk_main();
writeln('thanks ---------------');
end.
(* runtime log in linux:

test]$ ../../bin/gtk/samp
starting: --------------
is Entry nil? FALSE
before: --------------
preselected: "field 3"
inside: ---------------
postselected: "last field"
thanks ---------------
test]$

*)

(* runtime log in wine -- w2k gives the same

F:\devel\src\test>../../bin/gtkw/samp.exe
starting: --------------
is Entry nil? TRUE

(samp.exe): Gtk-CRITICAL **: file gtkentry.c: line 3642 (gtk_entry_set_text): assertion `GTK_IS_ENTRY (entry)' failed before: --------------

(samp.exe): Gtk-CRITICAL **: file gtkentry.c: line 3797 (gtk_entry_get_text): assertion `GTK_IS_ENTRY (entry)' failed preselected: ""

(samp.exe): Gtk-CRITICAL **: file gtkentry.c: line 3777 (gtk_entry_set_editable): assertion `GTK_IS_ENTRY (entry)' failed inside: ---------------

(samp.exe): Gtk-CRITICAL **: file gtkentry.c: line 3797 (gtk_entry_get_text): assertion `GTK_IS_ENTRY (entry)' failed postselected: ""
thanks ---------------
F:\devel\src\test>

*)

With regards,

Jan Jelowicki

------------------------------------------------------------------- Wroclaw University of Agriculture Akademia Rolnicza we Wroclawiu Department of Mathematics Katedra Matematyki -------------------------------------------------------------------

Michalis Kamburelis
to Jan Je/lowicki

Hi

I found the problem: TGtkBox record layout and size is not correct for Win32 GTK 2 libraries. This causes that "PGtkCombo(c)^.entry" does not work as it should, because address of "entry" field in "TGtkCombo" is different than it should be. TGtkBox is currently defined as

    TGtkBox = record
         container : TGtkContainer;
         children : PGList;
         spacing: gint16;
         flag0: word;
      end;

and with "packing C" FPC understands that spacing and flag0 are packed together into one 32 bit value. And this is correct for GTK 2 Linux libraries, but surprisingly inside GTK 2 Win32 dlls GtkBox record (even though declared the same way in C headers) has different layout, namely both spacing and flag0 are expanded into 32-bit values. This means that correct definition of TGtkBox should be

    TGtkBox = record
         container : TGtkContainer;
         children : PGList;
         spacing: {$ifdef WIN32} LongInt {$else} gint16 {$endif};
         flag0: {$ifdef WIN32} LongInt {$else} word {$endif};
      end;

No, this is *not* a bug somewhere in general FPC record aligning algorithm. You can treat it as a bug in FPC GTK 2 bindings, or you can treat it as a bug in Win32 GTK 2 libraries (because they apparently are compiled in such way that struct alignment is different than in Linux).

I'm attaching test program test_align_differ.pas, compile and run this under Win32 and Linux and watch what it prints on stdout under each OS. Results prove that

1. sizes of all three records (TGtkContainer, TGtkBoxModified, TGtkBox) are the same under Win32 and Linux. So it's not a bug inside FPC compiler with aligning records, because both under Win32 and Linux records are aligned the same in FPC units.

2. At the same time, you can see that definition of TGtkBoxModified does not work as it should under Linux and definition of TGtkBox does not work as it should under Win32.

This proves that structures are aligned differently in Linux and Win32 libraries.

Michalis

Jan Je/lowicki

Hello,

That is exactly the meritum.
I was trying to write adequate C example for comparison, unfortunately I realized that I had no GTK+ source packages at home. And today morning I knew the solution from your mail.

Show quoted text 5 lines
No, this is *not* a bug somewhere in general FPC record aligning algorithm. You can treat it as a bug in FPC GTK 2 bindings, or you can treat it as a bug in Win32 GTK 2 libraries (because they apparently are compiled in such way that struct alignment is different than in Linux).

There is nothing to add. I would prefer to think about bug in GTK, since it is a good idea to keep the software portable. Especially when serious project, like GTK, has its own basic data types to avoid confusions...

Thank you once more

Jan Jelowicki

------------------------------------------------------------------- Wroclaw University of Agriculture Akademia Rolnicza we Wroclawiu Department of Mathematics Katedra Matematyki -------------------------------------------------------------------