Can't resolve Log Forging Fortify issue - java
I am having trouble fixing a Log Forging issue in Fortify. The issue, "writes unvalidated user input to the log", is being raised from both of the logging calls in the getLongFromTimestamp() method.
public long getLongFromTimestamp(final String value) {
LOGGER.info("getLongFromTimestamp(" + cleanLogString(value) + ")");
long longVal = 0;
Date tempDate = null;
try {
tempDate = new SimpleDateFormat(FORMAT_YYYYMMDDHHMMSS, Locale.US).parse(value);
} catch (ParseException e) {
LOGGER.warn("Failed to convert to Date: " + cleanLogString(value) + " Exception: " + cleanLogString(e.getMessage()));
throw new Exception(e);
}
if (tempDate != null) {
longVal = tempDate.getTime();
}
return longVal;
}
private cleanLogString(String logString) {
String clean = logString.replaceAll("[^A-Za-z0-9]", "");
if(!logString.equals(clean)) {
clean += " (CLEANED)";
}
return clean;
}
The cleanLogString() method has fixed other Log Forging Fortify issues in my project, however it has no effect on the 2 above.
Any help would be appreciated!
It is possible to use fortify Java annotations to tell Fortify that the data returned from a sanitizing function is now safe.
When looking at my log forging problems I had strings coming in through a web API and thus had the flags XSS and WEB on my strings. I tried to find annotations that would only remove these flags, but couldn't find any way to remove the WEB flag. The only documentation I've found is the Samples/advanced/javaAnnotation directory.
Since my sanitation method does sanitize strings, I choose to remove all flags. This could be a problem though, as it could hide privacy violations.
#FortifyValidate("return")
private String sanitizeString(String taintedString) {
return doSomethingWithTheString(taintedString);
}
Originally when this question was written our team was using log4j v1.2.8, however we noticed that all the log forging issues disappeared after upgrading to log4j v2.6.2.
Once the log4j version is upgraded the Fortify log forging issues should go away. The cleanLogString() method form the question above is also unnecessary. For example:
LOGGER.info("getLongFromTimestamp(" + value + ")");
I know I have run into situations where the complexity of my application would stop any malicious input from working as intended; Fortify does not consider this to be secure. I bet you are running into the same thing.
You are stripping any really useful characters out of the log message, but see what happens if you do some encoding on the output prior to writing to the log.
http://www.jtmelton.com/2010/09/21/preventing-log-forging-in-java/
// ensure no CRLF injection into logs for forging records
String clean = message.replace( '\n', '_' ).replace( '\r', '_' );
if ( ESAPI.securityConfiguration().getLogEncodingRequired() ) {
clean = ESAPI.encoder().encodeForHTML(message);
if (!message.equals(clean)) {
clean += " (Encoded)";
}
}
Use reflect or try-catch.
Its easy to cheat fortify.
Related
Non-Terminating Z3Str3 from z3-4.8.9-x64-ubuntu-16.04
I am having a problem when trying to use the Z3Str3 from z3-4.8.9-x64-ubuntu-16.04 notably if I substitute the com.microsoft.z3.jar to the one in z3-4.8.8-x64-ubuntu-16.04 I no longer have that issue. The problem is that the Z3 process never comes back with a result, despite the simplicity of the query. I noticed though that it returns the valid answer when I kill my program. I am not noticing that behavior when I am trying to run the same query on the executable, so I am guessing there is something about using the jar file that I might need to tweak one way or the other. Here is my code. I am using Ubuntu 16.04 LTS, and IntelliJ version ultimate 2020.3. Many thanks! import com.microsoft.z3.*; public class Z3String3Processor_reduced { public static void main(String[] args) { StringBuilder currentQuery = new StringBuilder("\n" + "(declare-const string0 String)\n" + "(assert (= (str.indexof string0 \"a\" 1) 6))\n" + "(check-sat)\n" + "(get-model)\n" + "\n"); Context context1 = new Context(); Solver solver1 = context1.mkSolver(); Params params = context1.mkParams(); params.add("smt.string_solver", "z3str3"); solver1.setParameters(params); StringBuilder finalQuery = new StringBuilder(currentQuery.toString()); // attempt to parse the query, if successful continue with checking satisfiability try { // throws z3 exception if malformed or unknown constant/operation BoolExpr[] assertions = context1.parseSMTLIB2String(finalQuery.toString(), null, null, null, null); solver1.add(assertions); // check sat, if so we can go ahead and get the model.... if (solver1.check() == Status.SATISFIABLE) { System.out.println("sat"); } else System.out.println("not sat"); context1.close(); } catch (Z3Exception e) { System.out.println("Z3 exception: " + e.getMessage()); } } }
I don't think this has anything to do with Java. Let's extract your query and put it in a file named a.smt2: $ cat a.smt2 (declare-const string0 String) (assert (= (str.indexof string0 "a" 1) 6)) (check-sat) (get-model) Now, if I run: $ z3 a.smt2 sat ( (define-fun string0 () String "FBCADEaGaa") ) That's good. But if I run: $ z3 smt.string_solver=z3str3 a.smt2 ... does not terminate .. So, bottom line, your query (as simple as it looks), gives hard time to the z3str3 solver. I see that you already reported this as a bug at https://github.com/Z3Prover/z3/issues/5673 Given that the default string-solver can handle the query just fine, why not just use that one? If you have to use z3str3 for some other reason, then you've found a case where it doesn't handle this query well; I'm not sure how inclined the z3 folks will be to fix this given the query is handled by the default solver rather quickly. Please report what you find out!
java.lang.NullPointerException trying to get specific values from hashmap
I've spent several frustrating days on this now and would appreciate some help. I have a Java agent in Lotus Domino 8.5.3 which is activated by a cgi:POST from my Lotusscript validation agent which is checking that customer has filled in the Billing and delivery address form. This is the code that parses the incoming data into a HashMap where field names are mapped to their respective values. HashMap hmParam = new HashMap(); //Our Hashmap for request_content data //Grab transaction parameters from form that called agent (CGI: request_content) if (contentDecoded != null) { String[] arrParam = contentDecoded.split("&"); for(int i=0; i < arrParam.length; i++) { int n = arrParam[i].indexOf("="); String paramName = arrParam[i].substring(0, n); String paramValue = arrParam[i].substring(n + 1, arrParam[i].length()); hmParam.put(paramName, paramValue); //Old HashMap if (paramName.equalsIgnoreCase("transaction_id")) { transactionID = paramValue; description = "Order " + transactionID + " from Fareham Wine Cellar"; //System.out.println("OrderID = " + transactionID); } if (paramName.equalsIgnoreCase("amount")) { orderTotal = paramValue; } if (paramName.equalsIgnoreCase("deliveryCharge")) { shipping = paramValue; } } } The block of code above dates back over a year to my original integration of shopping cart to Barclays EPDQ payment gateway. In that agent I recover the specific values and build a form that is then submitted to EPDQ CPI later on in the agent like this; out.print("<input type=\"hidden\" name=\"shipping\" value=\""); out.println(hmParam.get("shipping") + "\">"); I want to do exactly the same thing here, except when I try the agent crashes with a null pointer exception. I can successfully iterate through the hashMap with the snippet below, so I know the data is present, but I can't understand why I can't use myHashMap.Get(key) to get each field value in the order I want them for the html form. The original agent in another application is still in use so what is going on? The data too is essentially unchanged String fieldnames mapped to String values. Iterator it = cgiData.entrySet().iterator(); while (it.hasNext()) { Map.Entry pairs = (Map.Entry)it.next(); out.println("<br />" + pairs.getKey() + " = " + pairs.getValue()); //System.out.println(pairs.getKey() + " = " + pairs.getValue()); }
I did two things that may have had an impact, in the process of trying to debug what was going on I needed these further imports; import java.util.Iterator; import java.util.Map; Although I'm not iterating over the hashMap, I've left them in in case which gives me the option of dumping the hashMap out to my system audit trail when application is in production. In variations of the snippet below after it started working I was able to get to any of the data I needed, even if the value was Null, and toString() also seemed to be optional again, as it made no difference to the output. String cgiValue = ""; cgiValue = hmParam.get("ship_to_lastname").toString(); out.println("<br />Lastname: " + cgiValue); out.println("<br />Company name: " + hmParam.get("bill_to_company")); out.println("<br />First name: " + hmParam.get("ship_to_firstname")); The second thing I did, while trying to get code to work was I enabled the option "Compile Java code with debugging information" for the agent, this may have done something to the way the project was built within the Domino Developer client. I think I have to put this down to some sort of internal error created when Domino Designer compiled the code. I had a major crash last night while working on this which necessitated a cold boot of my laptop. You also may find that when using Domino Designer 8.5.x that strange things can happen if you don't completely close down all the tasks from time to time with KillNotes
Strange behaviour with indexOf method
We have deployed our Java EE web application in jboss 4.0.2 (we are using JDK 1.6.0_18). In our code we are iterating through the Collection and doing string concatenation of userids in collection (refer below code). On production server, it behaves inconsistently. The userid (2044157) is not found in final string (refer ServerLog line3). If we restart the production jboss server, then it works perfectly fine and it prints all users correctly in final string log. But the problem again reappears after heavy usage (after 5-6 hours). We are not able to replicate the issue on our QA environment. When problem happens, Looks like the indexOf method incorrectly returns that 2044157 is there in strUsers string (even though 2044157 is not there) and hence it goes into else part and printed it in else part log(refer ServerLog line2 - highlighted in bold font). What could be reason for such inconsistent behavior? Code: public class UsersEJB implements SessionBean{ private void processSelectionData{ StringBuilder strUsers = new StringBuilder(""); Collection userVoCollection = dc.retProjectOrgUsers(projectID, strDistributionCompID, porjectDataSource); // This is returning List of 626 UserVO if(log.isDebugEnabled()) log.debug("UserList Size="+userVoCollection.size()+",B4 strUsers="+strUsers.toString()); Iterator it = userVoCollection.iterator(); while(it.hasNext()) { UserVO uVO = (UserVO)it.next(); if(!(strUsers.toString().indexOf("," + uVO.userID.toString() + ",") > -1)) { strUsers.append(uVO.userID.toString()).append(","); loopCntPos++; } else { loopCntNeg++; if(log.isDebugEnabled()) log.debug("UserId="+uVO.userID.toString()+",strUsers="+loopCnt+"="+strUsers.toString()); } loopCnt++; } if(log.isDebugEnabled()) log.debug("COMPANIES_ID1 strUsers="+strUsers.toString() + ",### loopCnt="+loopCnt + ",loopCntPos="+loopCntPos + ",loopCntNeg="+loopCntNeg); } } ServerLog UserList Size=626,B4 strUsers=,1732286,2066065,2096854,1952590,1731333,1732065,1734828,1852547,1732020,1733653,1731278,2079012,1733299,1765873,1733431,1960010,1828681,2047672,1731752,1733172,1784314,1989311,1734795,1732658,1731415,1785285,1785185,1738446,1733139,1732526,1733549,1731078,1804055,1732939,1663167,1732768,1732029,1732504,1989185,1882746,1785428,1731213,1732931,1731296,1733503,1753435,1731667,1936166,1747699,2099764,1482144,1747707,1732953,1771653,1731251,1989303,1755297,1731160,1901283,1782751,1733543,1882693,1733354,1974270,2044300,1732082,1907188,1731872,1955156,1732153,1733260,1731096,1604035,1731914,1731169,1732418,1731240,1989180,1731306,1733533,1882684,1821306,1731178,1731389,1733309,1733104,2078768,1989277,1732542,1733513,1733082,1732630,1733289,1733361,2077522,1733252,1732493,1978847,1733071, UserId=2044157,strUsers=440=,1732286,2066065,2096854,1952590,1731333,1732065,1734828,1852547,1732020,1733653,1731278,2079012,1733299,1765873,1733431,1960010,1828681,2047672,1731752,1733172,1784314,1989311,1734795,1732658,1731415,1785285,1785185,1738446,1733139,1732526,1733549,1731078,1804055,1732939,1663167,1732768,1732029,1732504,1989185,1882746,1785428,1731213,1732931,1731296,1733503,1753435,1731667,1936166,1747699,2099764,1482144,1747707,1732953,1771653,1731251,1989303,1755297,1731160,1901283,1782751,1733543,1882693,1733354,1974270,2044300,1732082,1907188,1731872,1955156,1732153,1733260,1731096,1604035,1731914,1731169,1732418,1731240,1989180,1731306,1733533,1882684,1821306,1731178,1731389,1733309,1733104,2078768,1989277,1732542,1733513,1733082,1732630,1733289,1733361,2077522,1733252,1732493,1978847,1733071,1893797,2137701,2025815,1522850,2027582,1732833,1984513,2037965,1900381,1731514,2044357,2042751,1785407,2118267,2050509,2062445,1934909,1912411,1733673,1731956,1694916,1731951,2048024,1735552,2115155,1732777,2120796,2048007,1845970,1738356,1841988,2101099,2027667,2067876,1734628,1731739,1731893,2051612,1819645,1803654,2037906,1732047,1478544,2073677,2012435,2067977,2073669,1981390,1731124,15916,6766,1978916,1732750,1936298,1891936,1747650,1949484,2101161,1928883,1948164,2013726,1750718,1732164,1733700,1639298,1734968,1732007,1734723,1949403,2137692,1990151,1734617,2101130,1928888,2044163,1732042,1819543,2137672,1735463,1732716,1950975,2025826,1984507,2017645,1372949,1928719,1732684,1952358,1581015,2026878,1731622,1734036,2000528,1734611,2052691,1961286,2107121,1733335,1868846,2000469,1734771,1841953,2118224,2038924,1731609,1735396,2026033,1805573,2107214,1638397,1731502,1731581,2115171,2120903,1892076,2060862,2017603,2002514,1731351,1901274,1760679,1821298,1884485,1777244,1731204,1934917,2000497,1737101,2115043,2121909,2097818,1506144,1953947,1753401,1594875,2135263,1900276,1907168,1851867,1940057,1897000,1765857,2037953,1907085,2037911,2062548,1650062,1801180,1953696,2119602,1605403,1804076,1669286,1844334,1542596,2048001,1938656,1757959,1529666,2070447,1565121,1907065,1944060,2097808,2077490,1843170,1957289,1690800,1823148,1788987,1912477,1738344,1845866,2047996,1962156,1483244,2071932,2127277,1912419,1756748,1999518,1908161,1722312,1548164,1584044,2047896,1856844,1762432,2073439,1861949,1530755,1989292,1852455,2027658,1738380,2067996,1981507,1998543,1958859,1620837,1852555,2012357,1895444,2050380,1789210,1932156,1898948,2046841,2098171,1625335,2138533,2046655,1785464,2105080,2024935,1852446,2073682,1478644,2103660,1751154,1863254,1478332,1849259,1593399,1895334,2075182,2134365,2136657, COMPANIES_ID1 strUsers=,1732286,2066065,2096854,1952590,1731333,1732065,1734828,1852547,1732020,1733653,1731278,2079012,1733299,1765873,1733431,1960010,1828681,2047672,1731752,1733172,1784314,1989311,1734795,1732658,1731415,1785285,1785185,1738446,1733139,1732526,1733549,1731078,1804055,1732939,1663167,1732768,1732029,1732504,1989185,1882746,1785428,1731213,1732931,1731296,1733503,1753435,1731667,1936166,1747699,2099764,1482144,1747707,1732953,1771653,1731251,1989303,1755297,1731160,1901283,1782751,1733543,1882693,1733354,1974270,2044300,1732082,1907188,1731872,1955156,1732153,1733260,1731096,1604035,1731914,1731169,1732418,1731240,1989180,1731306,1733533,1882684,1821306,1731178,1731389,1733309,1733104,2078768,1989277,1732542,1733513,1733082,1732630,1733289,1733361,2077522,1733252,1732493,1978847,1733071,1893797,2137701,2025815,1522850,2027582,1732833,1984513,2037965,1900381,1731514,2044357,2042751,1785407,2118267,2050509,2062445,1934909,1912411,1733673,1731956,1694916,1731951,2048024,1735552,2115155,1732777,2120796,2048007,1845970,1738356,1841988,2101099,2027667,2067876,1734628,1731739,1731893,2051612,1819645,1803654,2037906,1732047,1478544,2073677,2012435,2067977,2073669,1981390,1731124,15916,6766,1978916,1732750,1936298,1891936,1747650,1949484,2101161,1928883,1948164,2013726,1750718,1732164,1733700,1639298,1734968,1732007,1734723,1949403,2137692,1990151,1734617,2101130,1928888,2044163,1732042,1819543,2137672,1735463,1732716,1950975,2025826,1984507,2017645,1372949,1928719,1732684,1952358,1581015,2026878,1731622,1734036,2000528,1734611,2052691,1961286,2107121,1733335,1868846,2000469,1734771,1841953,2118224,2038924,1731609,1735396,2026033,1805573,2107214,1638397,1731502,1731581,2115171,2120903,1892076,2060862,2017603,2002514,1731351,1901274,1760679,1821298,1884485,1777244,1731204,1934917,2000497,1737101,2115043,2121909,2097818,1506144,1953947,1753401,1594875,2135263,1900276,1907168,1851867,1940057,1897000,1765857,2037953,1907085,2037911,2062548,1650062,1801180,1953696,2119602,1605403,1804076,1669286,1844334,1542596,2048001,1938656,1757959,1529666,2070447,1565121,1907065,1944060,2097808,2077490,1843170,1957289,1690800,1823148,1788987,1912477,1738344,1845866,2047996,1962156,1483244,2071932,2127277,1912419,1756748,1999518,1908161,1722312,1548164,1584044,2047896,1856844,1762432,2073439,1861949,1530755,1989292,1852455,2027658,1738380,2067996,1981507,1998543,1958859,1620837,1852555,2012357,1895444,2050380,1789210,1932156,1898948,2046841,2098171,1625335,2138533,2046655,1785464,2105080,2024935,1852446,2073682,1478644,2103660,1751154,1863254,1478332,1849259,1593399,1895334,2075182,2134365,2136657,2041203,2043944,2040358,2093521,1913544,2082455,2024959,2045812,1973980,1494485,1986446,1525605,2046849,1785194,1822210,2053401,1918823,2001794,1785258,2064339,1986338,1710198,1521244,1822292,1931276,2134370,2075073,2134300,2075068,1521210,2131493,1951008,1914649,1774999,1601557,1485584,2078975,1986330,1612190,2064410,2066054,1985760,1685075,1930273,2032161,1955161,,### loopCnt=626,loopCntPos=274,loopCntNeg=352
As it stands, your search won't pick up the first user as there won't be a preceding comma. However, I would suggest solving the problem in a far simpler manner, by using a set: public class UsersEJB implements SessionBean { private void processSelectionData { Collection userVoCollection = dc.retProjectOrgUsers(projectID, strDistributionCompID, porjectDataSource); // This is returning List of 626 UserVO Set<String> usersSet = new HashSet<String>(userVoCollection.size()); if(log.isDebugEnabled()) log.debug("UserList Size="+userVoCollection.size()+",B4 strUsers="+strUsers.toString()); for (UserVO uVO : userVoCollection) { if (usersSet.add(uVO.userID.toString()) loopCntPos++; else { loopCntNeg++; if(log.isDebugEnabled()) log.debug("UserId="+uVO.userID.toString()+",strUsers="+loopCnt+"="+strUsers.toString()); } if(log.isDebugEnabled()) log.debug("COMPANIES_ID1 strUsers=" + usersSet + ",### loopCnt="+loopCnt + ",loopCntPos="+loopCntPos + ",loopCntNeg="+loopCntNeg); } }
Leading zero for outbound asterisk call
Hy all, I am a newbie in asterisk so don't know much about it. I am currently tangled in an application which makes an outbound call. Previously it wasn't working due to some provisioning issues and then ANI was showing NULL value. But now it's working fine because I used setCallerID function of java. The problem is that an outbound call is generated successfully to the users for a number say 123, but a leading zero '0' is attached to it and becomes '0123', I am assuming that '0' is for national number which asterisk attached as per defined in asterisk, and my required number is '123', which I want to change from the java code. I searched a lot of forums/sites including the leading site of voip-info but didn't get success yet. I want to resolve it through java code if possible. Any help would be greatly appreciated. Update: Note: asterisk version is 1.8 , chain ss7 is 2.1 extensions.conf [gu] exten =>007775,1,Answer(); this will answer the call exten =>007775,2,Wait(1); will wait for 1 second exten =>007775,3,NoOp(Call from ${CALLERID(all)}) exten =>007775,4,AGI(agi://localhost:4573/com.digitania.ivr.gu.domain.ServiceImplDelegate?uniqueId=${UNIQUEID}&isOutbound=${isOutbound}&msisdn=${MSISDN}) exten =>007775,5,Hangup(); end the call My java code private static final String PARAM_MSISDN = "MSISDN"; private static final String PARAM_ISOUTBOUND = "isOutbound"; private static final String EXTENSION = "007775"; private static final String CALLER_ID = "7775"; public static int callCount = 0; public void call(String msisdn, CallListener listener) { try { { OriginateAction originateAction = new OriginateAction(); originateAction.setChannel((new StringBuilder("SS7/").append(msisdn).toString())); originateAction.setContext("gu"); originateAction.setPriority(new Integer(1)); originateAction.setExten(EXTENSION); originateAction.setCallerId(CALLER_ID); originateAction.setVariable(PARAM_MSISDN, msisdn); originateAction.setVariable(PARAM_ISOUTBOUND, "true"); ManagerResponse originateResponse = managerConnection .sendAction(originateAction, 30000L); System.out.println((new StringBuilder("RESPONSE: \n")).append( originateResponse.getResponse()).toString()); System.out.println(originateResponse.getMessage()); } } catch (TimeoutException e) { listener.callTimeOutException(); } catch (Exception e) { e.printStackTrace(); } callCount++; }
It's been a while for me using libss7, but have you tried looking at these options in chan_dahdi.conf? ss7_called_nai ss7_calling_nai ss7_internationalprefix ss7_nationalprefix ss7_subscriberprefix ss7_unknownprefix networkindicator Playing a bit with them (and also talking to your provider) should allow you to send the correct numbers. Hope it helps.
Android application exits without any exception
I'm building an application that shows in a WebView some remote data that is cached in SQLite db. The data is being requested by JavaScript function from WebView via JavaScript interface. When user types into an input element on the page, JavaScript function requests search result by calling Java function, which in turn fires a sql query. Results are then packaged in suitable JSON format and returned. Fetching data works OK unless you type very quickly. If you type quick enough after few key presses the app quits WITHOUT any exceptions being thrown, it just goes back to home screen. I have managed to narrow down the cause - commenting out the call to .query method prevents crashing, but renders app useless. Is there a way to check what caused application to quit, another log or tool that could help? Java function code: public Lot[] getLotList(String query, int limitCount) { ... ... String[] resultColumns = new String[] { LotsSearch._ID }; String queryWhere = LotsSearch.TABLE_NAME + " MATCH ?"; String[] queryArgs = new String[] { query + "*" }; String sortOrder = LotsSearch.COLUMN_NAME_NUMBER + " ASC, " + LotsSearch.COLUMN_NAME_TITLE + " ASC"; String limit = null; Cursor cursor = null; if (limitCount != -1) limit = "0," + limitCount; try { cursor = mDb.query(LotsSearch.TABLE_NAME, resultColumns, queryWhere, queryArgs, null, null, sortOrder, limit); if (cursor != null && cursor.moveToFirst()) { result = new Lot[cursor.getCount()]; try { int idColumnIndex = cursor.getColumnIndexOrThrow(LotsSearch._ID); int lotId; Lot lot; do { lotId = cursor.getInt(idColumnIndex); lot = mLots.get(lotId); if (lot != null) result[index++] = lot; } while (cursor.moveToNext()); } catch (IllegalArgumentException e) { e.printStackTrace(); } } } catch (SQLiteException e) { e.printStackTrace(); } finally { if (cursor != null) cursor.close(); } ... ... return result; } UPDATE: I have discovered that there is another log that could be accessed by issuing logcat -b events when the app crashes there is just one entry I/am_proc_died( 59): [11473,com.example.app] and when the app exits gracefuly this log shows set of entries: I/am_finish_activity( 59): [1157978656,22,com.example.app/.MainActivity,app-request] I/am_pause_activity( 59): [1157978656,com.example.app/.MainActivity] I/am_on_paused_called(11473): com.example.app.MainActivity I/am_destroy_activity( 59): [1157978656,22,com.example.app/.MainActivity]
I'd make a change to my auto search function. Namely, only perform the search if the user hasn't pressed a key for about 1/2 a second. If you are typing fast, then this function is being executed several times right on top of itself, before the results are even able to come back. Meanwhile you are probably have too many cursor resources going at once causing the app to just completely fail. update. If you consider it, typing 10 keys fairly quickly in a row could potentially mean that you have 10 different queries executing and parsing results... There could certainly be some deadlocking issues with the code that actually calls the getLotList method if it's spun multiple threads to try and update the UI. This can lead to some programs simply giving up the ghost not knowing what to do or even what thread to report the issue on. Of course, all of that's hard to tell from the small snippet we have.