[Python-checkins] CVS: python/dist/src/Modules _tkinter.c,1.112,1.113

Guido van Rossum python-dev@python.org
Fri, 6 Oct 2000 09:58:29 -0700


Update of /cvsroot/python/python/dist/src/Modules
In directory slayer.i.sourceforge.net:/tmp/cvs-serv9460

Modified Files:
	_tkinter.c 
Log Message:
[ Bug #113803 ] [2.0b1 NT4.0] printing non asci char causes idle to abort
http://sourceforge.net/bugs/?func=detailbug&bug_id=113803&group_id=5470

Add Unicode support and error handling to AsString().  Both AsString()
and Merge() now return NULL and set a proper Python exception
condition when an error happens; Merge() and other callers of
AsString() check for errors from AsString().  Also fixed cleanup in
Merge() and Tkapp_Call() return cleanup code; the fv array was not
necessarily completely initialized, causing calls to ckfree() with
garbage arguments!

(Also reindented some lines that were longer than 80 chars and
reformatted some code that used an alien coding standard.)


Index: _tkinter.c
===================================================================
RCS file: /cvsroot/python/python/dist/src/Modules/_tkinter.c,v
retrieving revision 1.112
retrieving revision 1.113
diff -C2 -r1.112 -r1.113
*** _tkinter.c	2000/10/05 19:24:25	1.112
--- _tkinter.c	2000/10/06 16:58:26	1.113
***************
*** 138,142 ****
  
  #define LEAVE_TCL \
! 	tcl_tstate = NULL; PyThread_release_lock(tcl_lock); Py_END_ALLOW_THREADS}
  
  #define ENTER_OVERLAP \
--- 138,142 ----
  
  #define LEAVE_TCL \
!     tcl_tstate = NULL; PyThread_release_lock(tcl_lock); Py_END_ALLOW_THREADS}
  
  #define ENTER_OVERLAP \
***************
*** 178,185 ****
  
  typedef int (*TclMacConvertEventPtr) (EventRecord *eventPtr);
! void Tcl_MacSetEventProc (TclMacConvertEventPtr procPtr);
! int TkMacConvertEvent (EventRecord *eventPtr);
  
! staticforward int PyMacConvertEvent (EventRecord *eventPtr);
  
  #if defined(__CFM68K__) && !defined(__USING_STATIC_LIBS__)
--- 178,185 ----
  
  typedef int (*TclMacConvertEventPtr) (EventRecord *eventPtr);
! void Tcl_MacSetEventProc(TclMacConvertEventPtr procPtr);
! int TkMacConvertEvent(EventRecord *eventPtr);
  
! staticforward int PyMacConvertEvent(EventRecord *eventPtr);
  
  #if defined(__CFM68K__) && !defined(__USING_STATIC_LIBS__)
***************
*** 262,268 ****
  	if (PyString_Check(value))
  		return PyString_AsString(value);
  	else {
  		PyObject *v = PyObject_Str(value);
! 		PyList_Append(tmp, v);
  		Py_DECREF(v);
  		return PyString_AsString(v);
--- 262,284 ----
  	if (PyString_Check(value))
  		return PyString_AsString(value);
+ 	else if (PyUnicode_Check(value)) {
+ 		PyObject *v = PyUnicode_AsUTF8String(value);
+ 		if (v == NULL)
+ 			return NULL;
+ 		if (PyList_Append(tmp, v) != 0) {
+ 			Py_DECREF(v);
+ 			return NULL;
+ 		}
+ 		Py_DECREF(v);
+ 		return PyString_AsString(v);
+ 	}
  	else {
  		PyObject *v = PyObject_Str(value);
! 		if (v == NULL)
! 			return NULL;
! 		if (PyList_Append(tmp, v) != 0) {
! 			Py_DECREF(v);
! 			return NULL;
! 		}
  		Py_DECREF(v);
  		return PyString_AsString(v);
***************
*** 282,286 ****
  	int fvStore[ARGSZ];
  	int *fv = NULL;
! 	int argc = 0, i;
  	char *res = NULL;
  
--- 298,302 ----
  	int fvStore[ARGSZ];
  	int *fv = NULL;
! 	int argc = 0, fvc = 0, i;
  	char *res = NULL;
  
***************
*** 297,301 ****
  		argc = 1;
  		fv[0] = 0;
! 		argv[0] = AsString(args, tmp);
  	}
  	else {
--- 313,318 ----
  		argc = 1;
  		fv[0] = 0;
! 		if (!(argv[0] = AsString(args, tmp)))
! 			goto finally;
  	}
  	else {
***************
*** 317,320 ****
--- 334,338 ----
  				if (!(argv[i] = Merge(v)))
  					goto finally;
+ 				fvc++;
  			}
  			else if (v == Py_None) {
***************
*** 324,335 ****
  			else {
  				fv[i] = 0;
! 				argv[i] = AsString(v, tmp);
  			}
  		}
  	}
  	res = Tcl_Merge(argc, argv);
  
    finally:
! 	for (i = 0; i < argc; i++)
  		if (fv[i]) {
  			ckfree(argv[i]);
--- 342,357 ----
  			else {
  				fv[i] = 0;
! 				if (!(argv[i] = AsString(v, tmp)))
! 					goto finally;
! 				fvc++;
  			}
  		}
  	}
  	res = Tcl_Merge(argc, argv);
+ 	if (res == NULL)
+ 		PyErr_SetString(Tkinter_TclError, "merge failed");
  
    finally:
! 	for (i = 0; i < fvc; i++)
  		if (fv[i]) {
  			ckfree(argv[i]);
***************
*** 508,516 ****
  #if TKMAJORMINOR <= 8001
  		/* In Tcl 8.1 we must use UTF-8 */
! 		PyObject* utf8 = PyUnicode_AsUTF8String (value);
  		if (!utf8)
  			return 0;
! 		result = Tcl_NewStringObj (PyString_AS_STRING (utf8),
! 					 PyString_GET_SIZE (utf8));
  		Py_DECREF(utf8);
  		return result;
--- 530,538 ----
  #if TKMAJORMINOR <= 8001
  		/* In Tcl 8.1 we must use UTF-8 */
! 		PyObject* utf8 = PyUnicode_AsUTF8String(value);
  		if (!utf8)
  			return 0;
! 		result = Tcl_NewStringObj(PyString_AS_STRING(utf8),
! 					  PyString_GET_SIZE(utf8));
  		Py_DECREF(utf8);
  		return result;
***************
*** 520,524 ****
  			/* XXX Should really test this at compile time */
  			PyErr_SetString(PyExc_SystemError,
! 					"Py_UNICODE and Tcl_UniChar differ in size");
  			return 0;
  		}
--- 542,546 ----
  			/* XXX Should really test this at compile time */
  			PyErr_SetString(PyExc_SystemError,
! 				"Py_UNICODE and Tcl_UniChar differ in size");
  			return 0;
  		}
***************
*** 610,615 ****
  			res = PyUnicode_DecodeUTF8(s, (int)(p-s), "strict");
  			if (res == NULL) {
! 				PyErr_Clear();
! 				res = PyString_FromStringAndSize(s, (int)(p-s));
  			}
  		}
--- 632,637 ----
  			res = PyUnicode_DecodeUTF8(s, (int)(p-s), "strict");
  			if (res == NULL) {
! 			    PyErr_Clear();
! 			    res = PyString_FromStringAndSize(s, (int)(p-s));
  			}
  		}
***************
*** 637,641 ****
  	int fvStore[ARGSZ];
  	int *fv = NULL;
! 	int argc = 0, i;
  	PyObject *res = NULL; /* except this has a different type */
  	Tcl_CmdInfo info; /* and this is added */
--- 659,663 ----
  	int fvStore[ARGSZ];
  	int *fv = NULL;
! 	int argc = 0, fvc = 0, i;
  	PyObject *res = NULL; /* except this has a different type */
  	Tcl_CmdInfo info; /* and this is added */
***************
*** 654,658 ****
  		argc = 1;
  		fv[0] = 0;
! 		argv[0] = AsString(args, tmp);
  	}
  	else {
--- 676,681 ----
  		argc = 1;
  		fv[0] = 0;
! 		if (!(argv[0] = AsString(args, tmp)))
! 			goto finally;
  	}
  	else {
***************
*** 674,677 ****
--- 697,701 ----
  				if (!(argv[i] = Merge(v)))
  					goto finally;
+ 				fvc++;
  			}
  			else if (v == Py_None) {
***************
*** 681,685 ****
  			else {
  				fv[i] = 0;
! 				argv[i] = AsString(v, tmp);
  			}
  		}
--- 705,711 ----
  			else {
  				fv[i] = 0;
! 				if (!(argv[i] = AsString(v, tmp)))
! 					goto finally;
! 				fvc++;
  			}
  		}
***************
*** 726,730 ****
  	/* Copied from Merge() again */
    finally:
! 	for (i = 0; i < argc; i++)
  		if (fv[i]) {
  			ckfree(argv[i]);
--- 752,756 ----
  	/* Copied from Merge() again */
    finally:
! 	for (i = 0; i < fvc; i++)
  		if (fv[i]) {
  			ckfree(argv[i]);
***************
*** 754,761 ****
  
  	cmd  = Merge(args);
! 	if (!cmd)
! 		PyErr_SetString(Tkinter_TclError, "merge failed");
! 
! 	else {
  		int err;
  		ENTER_TCL
--- 780,784 ----
  
  	cmd  = Merge(args);
! 	if (cmd) {
  		int err;
  		ENTER_TCL
***************
*** 767,774 ****
  			res = PyString_FromString(Tkapp_Result(self));
  		LEAVE_OVERLAP_TCL
- 	}
- 
- 	if (cmd)
  		ckfree(cmd);
  
  	return res;
--- 790,795 ----
  			res = PyString_FromString(Tkapp_Result(self));
  		LEAVE_OVERLAP_TCL
  		ckfree(cmd);
+ 	}
  
  	return res;
***************
*** 893,896 ****
--- 914,919 ----
  		/* XXX Merge? */
  		s = AsString(newValue, tmp);
+ 		if (s == NULL)
+ 			return NULL;
  		ENTER_TCL
  		ok = Tcl_SetVar(Tkapp_Interp(self), name1, s, flags);
***************
*** 899,904 ****
  	else {
  		PyErr_Clear();
! 		if (PyArg_ParseTuple(args, "ssO:setvar", &name1, &name2, &newValue)) {
! 			s = AsString (newValue, tmp);
  			ENTER_TCL
  			ok = Tcl_SetVar2(Tkapp_Interp(self), name1, name2, 
--- 922,930 ----
  	else {
  		PyErr_Clear();
! 		if (PyArg_ParseTuple(args, "ssO:setvar",
! 				     &name1, &name2, &newValue)) {
! 			s = AsString(newValue, tmp);
! 			if (s == NULL)
! 				return NULL;
  			ENTER_TCL
  			ok = Tcl_SetVar2(Tkapp_Interp(self), name1, name2, 
***************
*** 1193,1198 ****
  		ckfree(s);
  	}
- 	else
- 		PyErr_SetString(Tkinter_TclError, "merge failed");
  
  	return res;
--- 1219,1222 ----
***************
*** 1226,1230 ****
  	PythonCmd_ClientData *data = (PythonCmd_ClientData *)clientData;
  	PyObject *self, *func, *arg, *res, *tmp;
! 	int i;
  
  	ENTER_PYTHON
--- 1250,1255 ----
  	PythonCmd_ClientData *data = (PythonCmd_ClientData *)clientData;
  	PyObject *self, *func, *arg, *res, *tmp;
! 	int i, rv;
! 	char *s;
  
  	ENTER_PYTHON
***************
*** 1257,1262 ****
  		return PythonCmd_Error(interp);
  	}
  
- 	Tcl_SetResult(Tkapp_Interp(self), AsString(res, tmp), TCL_VOLATILE);
  	Py_DECREF(res);
  	Py_DECREF(tmp);
--- 1282,1295 ----
  		return PythonCmd_Error(interp);
  	}
+ 
+ 	s = AsString(res, tmp);
+ 	if (s == NULL) {
+ 		rv = PythonCmd_Error(interp);
+ 	}
+ 	else {
+ 		Tcl_SetResult(Tkapp_Interp(self), s, TCL_VOLATILE);
+ 		rv = TCL_OK;
+ 	}
  
  	Py_DECREF(res);
  	Py_DECREF(tmp);
***************
*** 1264,1268 ****
  	LEAVE_PYTHON
  
! 	return TCL_OK;
  }
  
--- 1297,1301 ----
  	LEAVE_PYTHON
  
! 	return rv;
  }
  
***************
*** 1418,1422 ****
  	int mask, tfile;
  
! 	if (!PyArg_ParseTuple(args, "OiO:createfilehandler", &file, &mask, &func))
  		return NULL;
  	tfile = PyObject_AsFileDescriptor(file);
--- 1451,1456 ----
  	int mask, tfile;
  
! 	if (!PyArg_ParseTuple(args, "OiO:createfilehandler",
! 			      &file, &mask, &func))
  		return NULL;
  	tfile = PyObject_AsFileDescriptor(file);
***************
*** 1605,1609 ****
  	TkttObject *v;
  
! 	if (!PyArg_ParseTuple(args, "iO:createtimerhandler", &milliseconds, &func))
  		return NULL;
  	if (!PyCallable_Check(func)) {
--- 1639,1644 ----
  	TkttObject *v;
  
! 	if (!PyArg_ParseTuple(args, "iO:createtimerhandler",
! 			      &milliseconds, &func))
  		return NULL;
  	if (!PyCallable_Check(func)) {
***************
*** 1802,1807 ****
  _bump(FlattenContext* context, int size)
  {
! 	/* expand tuple to hold (at least) size new items.	return true if
! 	   successful, false if an exception was raised*/
  
  	int maxsize = context->maxsize * 2;
--- 1837,1842 ----
  _bump(FlattenContext* context, int size)
  {
! 	/* expand tuple to hold (at least) size new items.
! 	   return true if successful, false if an exception was raised */
  
  	int maxsize = context->maxsize * 2;
***************
*** 1823,1832 ****
  
  	if (depth > 1000) {
! 		PyErr_SetString(PyExc_ValueError,"nesting too deep in _flatten");
  		return 0;
  	} else if (PyList_Check(item)) {
  		size = PyList_GET_SIZE(item);
  		/* preallocate (assume no nesting) */
! 		if (context->size + size > context->maxsize && !_bump(context, size))
  			return 0;
  		/* copy items to output tuple */
--- 1858,1869 ----
  
  	if (depth > 1000) {
! 		PyErr_SetString(PyExc_ValueError,
! 				"nesting too deep in _flatten");
  		return 0;
  	} else if (PyList_Check(item)) {
  		size = PyList_GET_SIZE(item);
  		/* preallocate (assume no nesting) */
! 		if (context->size + size > context->maxsize &&
! 		    !_bump(context, size))
  			return 0;
  		/* copy items to output tuple */
***************
*** 1837,1844 ****
  					return 0;
  			} else if (o != Py_None) {
! 				if (context->size + 1 > context->maxsize && !_bump(context, 1))
  					return 0;
  				Py_INCREF(o);
! 				PyTuple_SET_ITEM(context->tuple, context->size++, o);
  			}
  		}
--- 1874,1883 ----
  					return 0;
  			} else if (o != Py_None) {
! 				if (context->size + 1 > context->maxsize &&
! 				    !_bump(context, 1))
  					return 0;
  				Py_INCREF(o);
! 				PyTuple_SET_ITEM(context->tuple,
! 						 context->size++, o);
  			}
  		}
***************
*** 1846,1850 ****
  		/* same, for tuples */
  		size = PyTuple_GET_SIZE(item);
! 		if (context->size + size > context->maxsize && !_bump(context, size))
  			return 0;
  		for (i = 0; i < size; i++) {
--- 1885,1890 ----
  		/* same, for tuples */
  		size = PyTuple_GET_SIZE(item);
! 		if (context->size + size > context->maxsize &&
! 		    !_bump(context, size))
  			return 0;
  		for (i = 0; i < size; i++) {
***************
*** 1854,1861 ****
  					return 0;
  			} else if (o != Py_None) {
! 				if (context->size + 1 > context->maxsize && !_bump(context, 1))
  					return 0;
  				Py_INCREF(o);
! 				PyTuple_SET_ITEM(context->tuple, context->size++, o);
  			}
  		}
--- 1894,1903 ----
  					return 0;
  			} else if (o != Py_None) {
! 				if (context->size + 1 > context->maxsize &&
! 				    !_bump(context, 1))
  					return 0;
  				Py_INCREF(o);
! 				PyTuple_SET_ITEM(context->tuple,
! 						 context->size++, o);
  			}
  		}