When unity crashes debug.log s from the previous event don't render. Which happens to be the very event that crashed unity (probably via a loop)
So far, I've found Application.Quit(), but obviously, I can only use that if I know precisely when unity would crash (for example for finding out which of some (non nested) loops crashes)
(I also found a lot of info that didn't actually do anything, like opening the console window before starting the game. not listing all of that though)
I guess this example code should describe the problem well enough:
while (condition) {
DoSomething(); //contains a loop too
Debug.Log (value);
Application.Quit ();
}
obviously, only the first iteration happens.
But the inner loop usually won't crash for the first few times. So I'd like to log some values every time the inner loop terminates.
You can add a listener to log message's event (Application.logMessageReceived) in unity and store it in a file or send it via the network to prevent losing them.
void Awake()
{
DontDestroyOnLoad(this);
Application.logMessageReceived += HandleLog;
}
void OnApplicationQuit()
{
Application.logMessageReceived -= HandleLog;
}
void HandleLog(string logString, string stackTrace, LogType type)
{
File.AppendAllText ("D:/Log.txt" /*Path to your log folder*/, logString + stackTrace);
}
You can use Adb logs in cmd.
If you're using Unity with android, you must have already installed adb through Android SDK. Given that, yeah, it should be simple and obvious. And Ben is right. You didn't seem to google enough or take any effort here... But I just hate simple unanswered questions.
There are just a couple things to assure:
Make sure USB debugging is enabled on the Android device (check under Settings -> Development). - Run adb through the command prompt (with command line argument logcat) that comes with the Android SDK while running the game on the Android, still connected via USB to the computer.
adb logcat -s Unity ActivityManager PackageManager dalvikvm DEBUG
Finally, if the Android Debug Bridge can't help you, I'm not sure what could. There was this one time, actually, it couldn't help me... But I was ignoring a unity warning, so I did the debugging checklist in the wrong order.
Source of the answer
You could surround the block in question with a try catch. If it throws an error, you can log it in the catch block.
try
{
while (condition) {
DoSomething(); //contains a loop too
Debug.Log (value);
}
}
catch
{
Debug.Log(value);
}
Related
(Sorry for bad english i´m german)
I´m writing a service for a bigger project, the task for it is to check a folder for files and then call a Powershell-Script and give it the name of the file. This part is a bit unclean because i use a Powershellinstance to open a Powershell-Script. The Service itself is working, i tested it with different code to execute and the code to call the Script works when executed by a normal program, but when i let the service call the Script it seems like he just skips that part. The executionpolicy of the Script isn´t the problem. I post the part of the code that is supposed to open the Script. Any ideas?
static void Do()
{
Thread.Sleep(5000);
DirectoryInfo dir = new DirectoryInfo(#"C:\RecosDienstTest"); // Anpassen (json)
try
{
foreach (var datei in dir.EnumerateFiles())
{
using (PowerShell PowerShellInstance = PowerShell.Create())
{
PowerShellInstance.AddScript("C:\\Users\\ZO066\\Desktop\\test.ps1 " + datei.FullName); // Anpassen (PS-Script)
PowerShellInstance.Invoke();
if (PowerShellInstance.Streams.Error.Count > 0) { break; }
}
File.Move(datei.FullName, #"C:\RecosDienstTest2\" + datei.Name); // Anpassen
}
} catch {}
Do();
}
Boys, I finally got it! And I feel so stupid now... In the act of fixing this I changed the code so often, used different methods to open the script, I even destroyed my Visual Studio and had to reinstall it. At some point i decided to open txt-files instead of PS-Scripts but had exactly the same problem: Nothing happend and no Errors what-so-ever. The reason is that when a Service opens something, it just runs in the background no matter what it is(I had a few hundred Notepadinstances opened). The strange thing about this, and the reason why I didn´t thought of it: That happens to the whole chain. The service opened a script that opened a txt-file, but because the script was started by the service the txt-file is also opened in the background. I dont know why that is but I´m glad that I atleast found out why the fck nothing happened.
I'm writing a C# program that sends some simple commands to Arduino. via USB serial virtual port.
Sometimes happen that the program hangs, even if the code is protected by a try/catch block.
When I saw the problem the problem seem to be in closing the port.
The function is very simple:
void Send() {
try {
Debug.WriteLine("SR1 "+rel+" "+status);
_serialArduino.Open();
Debug.WriteLine("SR2");
_serialArduino.WriteLine(string.Format("switch {0} {1}\n", rel, Convert.ToSByte(status)));
Debug.WriteLine("SR3 '"+_serialArduino.ReadLine()+"'");
_serialArduino.Close();
Debug.WriteLine("SR4");
Thread.Sleep(400);
} catch (Exception e) {
LogManager.Write(string.Format("ERR SwitchRel({0}, {1}) - {2}", rel, status, e.Message));
}
}
I read about a problem during the Close function but in this case no DataReceived event handler is defined (==null).
Any idea?
* Edited to add some details *
After days of debugging and log analysis I discovered the following:
I'm working on a device running Win7Embedded Standard
The application is written in C#
after some time (or maybe caused from something unknown, so far) the port connecting Arduino disappeared from the list of the enumerated ports
the program initially reports on my log 'Device disconnected' and then 'Port COM9 does not exist' messages
The device manager reports COM9 on the 'Ports' tree (!!)
If I shut the program and re-run it, it reports 'COM9 does not exist' and if I list the ports the COM9 does not appear
My guess is that the usbser driver is in a mess.
The only solution, so far, is reset the board.
Is there a way to reset the driver without reboot and check if it returns in a known state?
Or maybe is the DotNet Framework that does not detect the port ?
Lately I'm having some issues in different applications that I have made. All of these applications use a Midi-controller to send midi-notes to a lighting desk. The issue is the same for all of these applications.
In runtime, when I'm working on the application, it sometimes occurs that my complete application freezes. I don't get any warningmessages, nor is the debugger popping up to tell me what's wrong. It always occurs when I want to play a midi-note. The only thing I can do at that point, is to reboot the entire machine, which is not that funny.
Because the application hangs and I don't get any debugging information, I'm certain it has to do with the DLL I use to send Midi-notes and that there's an issue there or in the way I have implemented the dll.
I've posted the code below and I would appreciate it, if someone could tell me what I'm doing wrong?
This is de code in the mainform initializing the Midi
MidiTools midi;
private void initMidi()
{
midi = new MidiTools();
midi.Enabled = true;
}
The initMidi() is called from inside the Form_Load-function.
The code to play a Midi-note is:
midi.playNote(22,0)
Below is the code inside the MidiTools-class file
using Midi;
namespace MidiTest
{
class MidiTools
{
public bool Enabled { get; set; }
OutputDevice outputDevice = OutputDevice.InstalledDevices[1];
Channel selectedChannel = Channel.Channel16;
int velocity = 127;
private void playNote(int noteNumber, int delay)
{
// CONVERT THE NOTE
Note selectedNote = (Note)noteNumber;
if (Enabled)
{
Thread.Sleep(delay);
Console.WriteLine(DateTime.Now.ToString("hh:mm:ss NOTE: ") + selectedNote.ToString());
outputDevice.Open();
outputDevice.SendNoteOn(selectedChannel, selectedNote, velocity);
outputDevice.Close();
}
}
}
}
The Midi-library itself was downloaded from this link:
https://midi-dot-net.googlecode.com/files/midi-dot-net_src_1.0.5.zip
In the past I've tried multiple ways of fixing this problem. I've tried inserting a bigger delay, I've tried cueing the messages in a list and processing them one by one to prevent a midinote from being asked to play wile another note is still being sent, but none of those helped.
In 98% of the cases it works, it's just occasionally that it freezes on me.
I'm using the M-Audio Midisport controller. (http://www.m-audio.com/products/view/midisport-4x4-anniversary-edition) but it has also happened on other controllers.
So any help is greatly appreciated.
Best regards,
Kenneth
I am using PcapDot.Net project Dlls to send packets (using Pcap file).
my question is if i want to stop the transmit in the middle i try PacketCommunicator.Break() and i can see with Wireshark that it still continue to send packets.
I also try PacketCommunicator.Dispose() and in this case i only get an crash: vshots.exe has stopped working.
PacketCommunicator.Break() will not help here. It's meant to stop a capture, not a transmission. As far as I see, there is no clear way to do what you wish from the Library, so I only propose workarounds. See if they help you, if not - contact the developer and ask for this feature.
Option 1 - You can send each packet separately in a loop, using PacketCommunicator.SendPacket(). This will be slower but will allow you to stop after each packet by modifying the loop's condition.
Option 2 - You can send use PacketCommunicator.Transmit but with smaller batches of packets
Change
while (inputCommunicator.ReceivePacket(out packet) == PacketCommunicatorReceiveResult.Ok)
{
sendBuffer.Enqueue(packet);
++numPackets;
}
into something like
int packetsInBatch = MAX_PACKETS_IN_BATCH;
while (inputCommunicator.ReceivePacket(out packet) == PacketCommunicatorReceiveResult.Ok && packetsInBatch > 0)
{
sendBuffer.Enqueue(packet);
++numPackets;
--packetsInBatch;
}
and put everything in another for loop. This will allow you to stop the loop after the end of the batch and is a trade-off between speed and delay after you signal to stop.
Option 3 - Mercilessly kill the send buffer. Call sendBuffer.Dispose() and handle the consequences.
[HandleProcessCorruptedStateExceptions]
private static void Transmit(PacketCommunicator outputCommunicator, PacketSendBuffer sendBuffer, bool isSync)
{
try
{
outputCommunicator.Transmit(sendBuffer, isSync);
}
catch (Exception e)
{
Console.WriteLine(e);
}
}
You'll have to handle AccessViolationException. I have done this by adding the HandleProcessCorruptedStateExceptions attribute to a new method I created which performs the transmit (see How to handle AccessViolationException). It seems to work on my machine, but this is really a last resort solution. I wouldn't use it in anything but the simplest command line utilities without a (very) through testing. There's work with unmanaged code going on and I don't know what happens to resources when we pull this trick.
Or not!
I have a fairly simple application timer program. The program will launch a user selected (from file dialog) executable and then terminate the process after the user specified number of minutes. During testing I found that a crash occurs when I call the Process.Kill() method and the application is minimized to the system tray.
The executable in question is Frap.exe which I use frequently and is the reason I wrote the app timer in the first place. I always minimize fraps to the tray, and this is when the crash occurs.
My use of Kill() is straight forward enough...
while (true)
{
//keep checking if timer expired or app closed externally (ie. by user)
if (dtEndTime <= DateTime.Now || p.HasExited)
{
if (!p.HasExited)
p.Kill();
break;
}
System.Threading.Thread.Sleep(500);
}
In searching for alternatives methods to close an external application programmatically, I found only Close() and Kill() (CloseMainWindow is not helpful to me at all). I tried using Close(), which works providing the application is minimized the tray. If the app is minimized, Close() doesn't cause a crash but the app remains open and active.
One thing I noticed in a few posts posts regarding closing external applications was the comment: "Personally I'd try to find a more graceful way of shutting it down though." made in THIS thread found here at stack flow (no offense to John). Thing is, I ran across comments like that on a few sites, with no attempt at what a graceful or elegant (or crash-free!!) method might be.
Any suggestions?
The crash experienced is not consistant and I've little to offer as to details. I am unable to debug using VS2008 as I get message - cant debug crashing application (or something similar), and depending on what other programs I have running at the time, when the Kill() is called some of them also crash (also programs only running in the tray) so I'm thinking this is some sort of problem specifically related to the system tray.
Is it possible that your code is being executed in a way such that the Kill() statement could sometimes be called twice? In the docs for Process.Kill(), it says that the Kill executes asynchronously. So, when you call Kill(), execution continues on your main thread. Further, the docs state that Kill will throw a Win32Exception if you call it on an app that is already in the process of closing. The docs state that you can use WaitForExit() to wait for the process to exit. What happens if you put a call to WaitForExit() immediately following the call to Kill(). The loop looks ok (with the break statement). Is it possible that you have code entering that loop twice?
If that's not the problem, maybe there is another way to catch that exception:
Try hooking the AppDomain.CurrentDomain.UnhandledException event
(currentDomain is a static member)
The problem is that Kill runs asynchronously, so if it's throwing an exception, it's occurring on a different thread. That's why your exception handler doesn't catch it. Further (I think) that an unhandled async exception (which is what I believe you have) will cause an immediate unload of your application (which is what is happening).
Edit: Example code for hooking the UnhandledExceptionEvent
Here is a simple console application that demonstrates the use of AppDomain.UnhandledException:
using System;
public class MyClass
{
public static void Main()
{
System.AppDomain.CurrentDomain.UnhandledException += MyExceptionHandler;
System.Threading.ThreadPool.QueueUserWorkItem(DoWork);
Console.ReadLine();
}
private static void DoWork(object state)
{
throw new ApplicationException("Test");
}
private static void MyExceptionHandler(object sender, System.UnhandledExceptionEventArgs e)
{
// get the message
System.Exception exception = e.ExceptionObject as System.Exception;
Console.WriteLine("Unhandled Exception Detected");
if(exception != null)
Console.WriteLine("Message: {0}", exception.Message);
// for this console app, hold the window open until I press enter
Console.ReadLine();
}
}
My first thought is to put a try/catch block around the Kill() call and log the exception you get, if there is one. It might give you a clue what's wrong. Something like:
try
{
if(!p.HasExited)
{
p.Kill();
}
break;
}
catch(Exception ex)
{
System.Diagnostics.Trace.WriteLine(String.Format("Could not kill process {0}, exception {1}", p.ToString(), ex.ToString()));
}
I dont think I should claim this to be "THE ANSWER" but its a decent 'work around'. Adding the following to lines of code...
p.WaitForInputIdle(10000);
am.hWnd = p.MainWindowHandle;
...stopped the crashing issue. These lines were placed immediately after the Process.Start() statement. Both lines are required and in using them I opened the door to a few other questions that I will be investigating over the next few days. The first line is just an up-to 10 second wait for the started process to go 'idle' (ie. finish starting). am.hWnd is a property in my AppManagement class of type IntPtr and this is the only usage of both sides of the assignment. For lack of better explaination, these two lines are analguous to a debouncing method.
I modified the while loop only slightly to allow for a call to CloseMainWindow() which seems to be the better route to take - though if it fails I then Kill() the app:
while (true)
{
//keep checking if timer expired or app closed externally (ie. by user)
if (dtEndTime <= DateTime.Now || p.HasExited) {
try {
if (!p.HasExited) // if the app hasn't already exitted...
{
if (!p.CloseMainWindow()) // did message get sent?
{
if (!p.HasExited) //has app closed yet?
{
p.Kill(); // force app to exit
p.WaitForExit(2000); // a few moments for app to shut down
}
}
p.Close(); // free resources
}
}
catch { // blah blah }
break;
}
System.Threading.Thread.Sleep(500);
}
My initial intention for getting the MainWindowHandle was to maximize/restore an app if minimized and I might implement that in the near future. I decided to see if other programs that run like Fraps (ie, a UI but mostly run in the system tray (like messanger services such as Yahoo et al.)). I tested with XFire and nothing I could do would return a value for the MainWindowHandle. Anyways, this is a serperate issue but one I found interesting.
PS. A bit of credit to JMarsch as it was his suggestion RE: Win32Exception that actually lead me to finding this work around - as unlikely as it seems it true.