GNOME Bugzilla – Bug 556359
undoing or redoing into a negative score causes the game to crash
Last modified: 2011-12-03 23:24:24 UTC
Steps to reproduce: 1. Get a negative score in a game. This can be done like so: a) Open a game of "triple peaks" b) in the "triple peaks" menu, make sure that both "progressive rounds" and "multiplier scoring" are checked c) By playing the game successfully, you can eventually get to a point where all cards can be played in one turn. At that point, your score will increment by 2^18 - 1 with each round. d) When your score goes over 2^31, it will wrap around to -(2 ^ 31). 2. Once the score wraps around to a negative, hit the "undo" button. 3. if the resulting score from the undo is also negative then the game will crash. 4) Similarly, if you play to the point of getting a negative score, then undo gives you a positive score, it will not crash. If however you then redo to the negative score, it will crash at that point. On the other hand, if you undo from a negative score to a positive score, and then repeat a play that gives you the negative score, it will not crash. In other words, it will crash when either an undo or a redo would bring it to a negative score Stack trace: errr... ummm... uhhh.... Well, I can paste the "bug report" that came up, although there's no mention of a stack trace in it..... System: Linux 2.6.25.14-108.fc9.i686 #1 SMP Mon Aug 4 14:08:11 EDT 2008 i686 X Vendor: The X.Org Foundation X Vendor Release: 10499905 Selinux: No Accessibility: Disabled GTK+ Theme: Clearlooks Icon Theme: gnome Memory status: size: 95965184 vsize: 95965184 resident: 24084480 share: 11751424 rss: 24084480 rss_rlim: 4294967295 CPU usage: start_time: 1223943869 rtime: 7125 utime: 6359 stime: 766 cutime:0 cstime: 0 timeout: 0 it_real_value: 0 frequency: 100 Variation: triple_peaks.scm Seed: 1588153365 Scheme error: (#f Value out of range ~S to ~S: ~S (-2147483648 2147483647 2214600480) (2214600480)) Scheme tag: out-of-range Backtrace: In current input: 1: 0* [redo] In /usr/share/gnome-games/aisleriot/games/sol.scm: 600: 1 (and (not (null? FUTURE)) (record-move -1 (quote ())) ...) 602: 2* [eval-move (#<procedure undo-func (data)> (2214600480 0 ()) (# () # # ...))] 583: 3* [undo-func (2214600480 0 ())] 611: 4* [set-score! 2214600480] Deck State: Slot 0 (3 5 #f), (2 3 #f), (1 1 #f) , (0 4 #f), (1 2 #f), (0 13 #f), (3 11 #f), (2 9 #f), (2 7 #f), (3 2 #f), (2 13 #f), (0 11 #f), (0 5 #f), (1 7 #f) Slot 1 (Empty) Slot 2 (0 1 #t) Slot 3 (1 10 #f) Slot 4 (0 9 #f) Slot 5 (2 8 #f) Slot 6 (1 9 #f) Slot 7 (1 8 #f) Slot 8 (3 9 #f) Slot 9 (3 10 #f) Slot 10 (1 11 #f) Slot 11 (3 12 #f) Slot 12 (2 11 #f) Slot 13 (1 12 #f) Slot 14 (1 13 #f) Slot 15 (3 1 #f) Slot 16 (2 2 #f) Slot 17 (1 3 #f) Slot 18 (3 4 #f) Slot 19 (3 3 #f) Slot 20 (1 4 #f) Slot 21 (2 5 #t) Slot 22 (1 6 #t) Slot 23 (0 7 #t) Slot 24 (2 6 #t) Slot 25 (3 7 #t) Slot 26 (3 6 #t) Slot 27 (1 5 #t) Slot 28 (2 4 #t) Slot 29 (0 3 #t) Slot 30 (0 2 #t) Backtrace was generated from '/usr/libexec/aisleriot' (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) [Thread debugging using libthread_db enabled] [New Thread 0xb803b760 (LWP 22228)] (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) (no debugging symbols found) 0x00110416 in __kernel_vsyscall ()
+ Trace 208200
Thread 1 (Thread 0xb803b760 (LWP 22228))
The program is running. Quit anyway (and detach it)? (y or n) [answered Y; input not from terminal] ----------- .xsession-errors (3747351 sec old) --------------------- ** (nm-applet:22355): WARNING **: nm_object_get_property: Error getting 'ActiveConnections' for /org/freedesktop/NetworkManager: The name org.freedesktop.NetworkManager was not provided by any .servic ** Message: <info> disconnected by the system bus. gnome-session: Fatal IO error 11 (Resource temporarily unavailable) on X server :0.0. ICE default IO error handler doing an exit(), pid = 22837, errno = 11 Window manager warning: Fatal IO error 11 (Resource temporarily unavailable) on display ':0.0'. The application 'gnome-panel' lost its connection to the display :0.0; most likely the X server was shut down or you killed/destroyed the application. nautilus: Fatal IO error 11 (Resource temporarily unavailable) on X server :0.0. nm-applet: Fatal IO error 11 (Resource temporarily unavailable) on X server :0.0. pam-panel-icon: Fatal IO error 11 (Resource temporarily unavailable) on X server :0.0. brightside: Fatal IO error 11 (Resource temporarily unavailable) on X server :0.0. -------------------------------------------------- Other information:
Thanks for taking the time to report this bug. However, you are using a version that is too old and not supported anymore. GNOME developers are no longer working on that version, so unfortunately there will not be any bug fixes for the version that you use. By upgrading to a newer version of GNOME you could receive bug fixes and new functionality. You may need to upgrade your Linux distribution to obtain a newer version of GNOME. Please feel free to reopen this bug if the problem still occurs with a newer version of GNOME.
There have been no scheme changes since that version, so it's irrelevant that it was an old version.
Then it will be good to move bugs to new stable version. I felt trace doesn't have proper debug symbols so i closed the bug. Sorry for the noise.
Sorry, wouldn't this be in the C component rather than scheme? Scheme integers do not overflow.
I don't think so; the C side is not involved at all in redo (it simply calls the redo function from sol.scm). The scheme stack from the exception supports this: Variation: triple_peaks.scm Seed: 1588153365 Scheme error: (#f Value out of range ~S to ~S: ~S (-2147483648 2147483647 2214600480) (2214600480)) Scheme tag: out-of-range Backtrace: In current input: 1: 0* [redo] In /usr/share/gnome-games/aisleriot/games/sol.scm: 600: 1 (and (not (null? FUTURE)) (record-move -1 (quote ())) ...) 602: 2* [eval-move (#<procedure undo-func (data)> (2214600480 0 ()) (# () # # ...))] 583: 3* [undo-func (2214600480 0 ())] 611: 4* [set-score! 2214600480]
It's not involved in redo, but it does implement both set-score! and get-score. The out-of-range error comes from calling set-score!, which I would argue should accept any nonnegative integer.
Oh right, I missed that. Sorry! I'll fix it.
struct_ Game { ... guint score; ... } static SCM scm_get_score (void) { AisleriotGame *game = app_game; return scm_from_uint (game->score); } static SCM scm_set_score (SCM new) { AisleriotGame *game = app_game; set_game_score (game, scm_num2int (new, SCM_ARG1, NULL)); return new; } static SCM scm_add_to_score (SCM delta) { AisleriotGame *game = app_game; guint new_score; new_score = game->score + scm_num2int (delta, SCM_ARG1, NULL); set_game_score (game, new_score); return scm_from_uint (new_score); } There seems to be some int/uint confusion here. Should "score" be int, or uint (that is, are negative scores useful for anything) ?
I changed score to "int" and uses to/from_int, on master. I wonder if we should simply keep score handling all on the scheme side, and simply _inform_ the C side of the new score, instead of getting the current score from the C side too?
I don't see why not. All the C side has to do (as I understand it) is display the current score. A string type might even make sense.
Mass-moving only open aisleriot bugs to the new product. Search for "aisleriot-mass-move" to filter them.
Created attachment 202727 [details] [review] sol: Move score keeping to the guile side
Patch looks good to me.
Comment on attachment 202727 [details] [review] sol: Move score keeping to the guile side Pushed to master. Now the only remaining issue is what we display in the UI when the value overflows.
Do you need to store it as an integer on the C side at all? Why not have guile convert it to a string, and use that?
Created attachment 202729 [details] [review] sol: Use string instead of number for storing the score in the frontend
Created attachment 202730 [details] [review] sol: Use string instead of number for storing the score in the frontend
I think set-score! needs to return a number. I remember at least one game uses the return value but I don't remember how.
"Giant" uses that. @@ -624,7 +624,8 @@ (define-public (set-score! value) (begin (set! SCORE value) - (update-score (number->locale-string SCORE)))) + (update-score (number->locale-string SCORE)) + SCORE)) Does that look right / best way to do this? (remember only I'm a scheme novice :-)
Yep, that looks right.
Thanks! Pushed to master. All is done here :-)