Changeset 174
- Timestamp:
- Jan 3, 2004, 11:37:17 AM (21 years ago)
- File:
-
- 1 edited
-
trunk/ccl/lisp-kernel/lisp-exceptions.c (modified) (4 diffs)
Legend:
- Unmodified
- Added
- Removed
-
trunk/ccl/lisp-kernel/lisp-exceptions.c
r137 r174 1786 1786 return(noErr); 1787 1787 } 1788 1789 if ((the_trap & OP_MASK) == OP(major_opcode_TWI)) {1790 /* TWI. If the RA field is "nargs", that means that the1791 instruction is either a number-of-args check or an1792 event-poll. Otherwise, the trap is some sort of1793 typecheck. */1794 1795 if (RA_field(the_trap) == nargs) {1796 fn_reg = nfn;1797 switch (TO_field(the_trap)) {1798 case TO_NE:1799 error_msg = ( (xpGPR(xp, nargs) < D_field(the_trap))1800 ? "Too few arguments (no opt/rest)"1801 : "Too many arguments (no opt/rest)" );1802 break;1803 1804 case TO_GT:1805 error_msg = "Event poll !";1806 break;1807 1808 case TO_HI:1809 error_msg = "Too many arguments (with opt)";1810 break;1811 1812 case TO_LT:1813 error_msg = "Too few arguments (with opt/rest/key)";1814 break;1815 1816 default: /* some weird trap, not ours. */1817 fn_reg = 0;1818 break;1819 }1820 } else {1821 /* A type or boundp trap of some sort. */1822 switch (TO_field(the_trap)) {1823 case TO_EQ:1824 /* Boundp traps are of the form:1825 tweqi rX,unbound1826 where some preceding instruction is of the form:1827 lwz rX,symbol.value(rY).1828 The error message should try to say that rY is unbound. */1829 1830 if (D_field(the_trap) == unbound) {1831 instr = scan_for_instr(LWZ_instruction(RA_field(the_trap),1832 unmasked_register,1833 offsetof(lispsymbol,vcell)-fulltag_misc),1834 D_RT_IMM_MASK,1835 where);1836 if (instr) {1837 ra = RA_field(instr);1838 if (lisp_reg_p(ra)) {1839 error_msg = "Unbound variable: %s";1840 (void)symbol_name( xpGPR(xp, ra), name, kNameBufLen );1841 err_arg1 = (unsigned)name;1842 fn_reg = fn;1843 }1844 }1845 }1846 break;1847 1848 case TO_NE:1849 /* A type check. If the type (the immediate field of the trap instruction)1850 is a header type, an "lbz rX,misc_header_offset(rY)" should precede it,1851 in which case we say that "rY is not of header type <type>." If the1852 type is not a header type, then rX should have been set by a preceding1853 "clrlwi rX,rY,29/30". In that case, scan backwards for an RLWINM instruction1854 that set rX and report that rY isn't of the indicated type. */1855 err_arg2 = D_field(the_trap);1856 if (((err_arg2 & fulltagmask) == fulltag_nodeheader) ||1857 ((err_arg2 & fulltagmask) == fulltag_immheader)) {1858 instr = scan_for_instr(LBZ_instruction(RA_field(the_trap),1859 unmasked_register,1860 misc_subtag_offset),1861 D_RT_IMM_MASK,1862 where);1863 if (instr) {1864 ra = RA_field(instr);1865 if (lisp_reg_p(ra)) {1866 error_msg = "value %08X is not of the expected header type %02X";1867 err_arg1 = xpGPR(xp, ra);1868 fn_reg = fn;1869 }1870 }1871 } else {1872 /* Not a header type, look for rlwinm whose RA field matches the_trap's */1873 instr = scan_for_instr((OP(major_opcode_RLWINM) | (the_trap & RA_MASK)),1874 (OP_MASK | RA_MASK),1875 where);1876 if (instr) {1877 rs = RS_field(instr);1878 if (lisp_reg_p(rs)) {1879 error_msg = "value %08X is not of the expected type %02X";1880 err_arg1 = xpGPR(xp, rs);1881 fn_reg = fn;1882 }1883 }1884 }1885 break;1886 }1887 }1888 } else {1889 /* a "TW <to>,ra,rb" instruction."1890 twltu sp,rN is stack-overflow on SP.1891 twgeu rX,rY is subscript out-of-bounds, which was preceded1892 by an "lwz rM,misc_header_offset(rN)" instruction.1893 rM may or may not be the same as rY, but no other header1894 would have been loaded before the trap. */1895 switch (TO_field(the_trap)) {1896 case TO_LO:1897 if (RA_field(the_trap) == sp) {1898 fn_reg = fn;1899 error_msg = "Stack overflow! Run away! Run away!";1900 }1901 break;1902 1903 case (TO_HI|TO_EQ):1904 instr = scan_for_instr(OP(major_opcode_LWZ) | (D_MASK & misc_header_offset),1905 (OP_MASK | D_MASK),1906 where);1907 if (instr) {1908 ra = RA_field(instr);1909 if (lisp_reg_p(ra)) {1910 error_msg = "Bad index %d for vector %08X length %d";1911 err_arg1 = unbox_fixnum(xpGPR(xp, RA_field(the_trap)));1912 err_arg2 = xpGPR(xp, ra);1913 err_arg3 = unbox_fixnum(xpGPR(xp, RB_field(the_trap)));1914 fn_reg = fn;1915 }1916 }1917 break;1918 }1919 }1920 1921 1922 if (!error_msg) {1923 return -1;1924 }1925 1926 fprintf( stderr, "\nError: ");1927 fprintf( stderr, error_msg, err_arg1, err_arg2, err_arg3 );1928 fprintf( stderr, "\n");1929 if (fn_reg && exception_fn_name( xp, fn_reg, name, kNameBufLen )) {1930 fprintf( stderr, "While executing: %s.\n", name );1931 }1932 fflush( stderr );1933 switch( error_action() ) {1934 case kDebugger:1935 return(-1);1936 break;1937 case kContinue:1938 adjust_exception_pc(xp, 4);1939 return(noErr);1940 break;1941 case kExit:1942 default:1943 terminate_lisp();1944 break;1945 }1946 1788 return -1; 1947 1789 } … … 1967 1809 } 1968 1810 1969 /* Copy function name to name & terminate, return # chars */1970 size_t1971 exception_fn_name( ExceptionInformation *xp, int fn_reg, char *name, size_t name_len )1972 {1973 unsigned the_fn = xpGPR(xp, fn_reg);1974 1975 if ((fulltag_of(the_fn) != fulltag_misc) ||1976 (header_subtag(header_of(the_fn)) != subtag_function)) {1977 non_fatal_error( "exception_fn_name: bogus fn" );1978 name[0] = 0;1979 return 0;1980 }1981 1982 if (named_function_p(the_fn)) {1983 unsigned the_sym = named_function_name(the_fn);1984 /* trust it - if ((fulltag_of(the_sym) == fulltag_misc) &&1985 (header_subtag(header_of(the_sym)) == subtag_symbol)) */1986 1987 return symbol_name( the_sym, name, name_len );1988 1989 } else { /* unnamed function */1990 strcpy( name, "<Anonymous Function>" );1991 return strlen(name);1992 }1993 }1994 1995 /* Make name a c-string of symbol's pname, return length */1996 size_t1997 symbol_name( unsigned the_sym, char *name, size_t name_len )1998 {1999 unsigned the_pname = ((lispsymbol *)(untag(the_sym)))->pname;2000 /* trust it - if (the_pname) */2001 2002 size_t length = header_element_count(header_of(the_pname));2003 if (length >= name_len) length = name_len - 1;2004 memcpy( (void *)name,2005 (const void *)(the_pname + misc_data_offset),2006 length );2007 name[length] = 0;2008 return length;2009 }2010 1811 2011 1812 void non_fatal_error( char *msg ) … … 2061 1862 } 2062 1863 2063 switch (errnum) {2064 case error_udf_call:2065 rb = xpGPR(xp, fname);2066 if ((fulltag_of(rb) == fulltag_misc) &&2067 (header_subtag(header_of(rb)) == subtag_symbol)) {2068 pname = ((lispsymbol *)(untag(rb)))->pname;2069 } else {2070 pname = (LispObj)NULL;2071 }2072 2073 fprintf(stderr, "\nERROR: undefined function call: ");2074 if (pname) {2075 fwrite((const void *)(pname+misc_data_offset),2076 1,2077 header_element_count(header_of(pname)),2078 stderr);2079 } else {2080 fprintf(stderr, "[can't determine symbol name.]");2081 }2082 putc('\n',stderr);2083 fflush(stderr);2084 switch( error_action() ) {2085 case kExit:2086 terminate_lisp();2087 break;2088 case kDebugger:2089 default:2090 return(-1);2091 break;2092 }2093 break;2094 default:2095 break;2096 }2097 1864 return(-1); 2098 1865 } 2099 1866 2100 ErrAction2101 error_action( void )2102 {2103 /* getchar reads from line start, so end message with \n */2104 fprintf( stderr, "\nContinue/Debugger/eXit <enter>?\n" );2105 fflush( stderr );2106 2107 do {2108 int c = toupper( getchar() );2109 switch( c ) {2110 case 'X':2111 return( kExit );2112 break;2113 case 'D':2114 return( kDebugger );2115 break;2116 case 'C':2117 return( kContinue );2118 break;2119 }2120 } while( true );2121 }2122 1867 2123 1868 /* … … 2430 2175 } 2431 2176 2432 Boolean 2433 exception_filter_installed_p() 2434 { 2435 return true; 2436 #if 0 2437 return installed_exception_filter == PMCL_exception_filter; 2438 #endif 2439 } 2177 2440 2178 2441 2179
Note:
See TracChangeset
for help on using the changeset viewer.
