Read from console in VS Code

I moved to Apple Mac late last year because of different set of technologies now I work in. As shared in one of my previous posts, I use Visual Studio Code for programming in Python exploring Machine Learning. Though, for anything in .NET, I switch to a Windows VM and use Visual Studio.

For quick console apps, it feels painful to switch to a VM and work. Thus, I looked and installed C# extension in VS Code to try of. Details are here.

While running a console app, I got stuck to read any value from Console. In debug mode, IDE would stop on the Console.ReadLine() but whatever I type in Console would not go through.

I looked around and found that there are few settings for Console in VS Code. The console setting controls what console (terminal) window the target app is launched into.

"internalConsole" (default) : This does NOT work for applications that want to read from the console (ex: Console.ReadLine).

How to Solve it?

Suggested way to take input is to set the console setting as integratedTerminal. This is a configuration setting in the launch.json file under .vscode folder.

"integratedTerminal" : the target process will run inside VS Code’s integrated terminal (Terminal tab in the tab group beneath the editor). Alternatively add "internalConsoleOptions": "neverOpen" to make it so that the default foreground tab is the terminal tab.

Change the default setting like below:

vscode-read-console

With above change, the input and output will happen through integrated terminal like:

vscode-read-console-2

So far, it looks good and seems I will stick to Visual Studio Code on Mac for quick console applications.

Reference here.


Keep learning!

LearnByInsight
GitHub Profile Readme Samples

“Unable to evaluate expression because the code is optimized or a native frame is on top of the call stack”

This is one of the common runtime error reported by a lot of ASP.NET users.

Problem description

A successfully compiled code at runtime throws the following error during an operation:

“Unable to evaluate expression because the code is optimized or a native frame is on top of the call stack.”

Typically, this happens when the Response.EndResponse.Redirect, or Server.Transfer method is used.

Assessment

This happens because current page execution is stopped and execution is sent to the Application_EndRequest event in the application’s event pipeline.

The duty of Response.End method is to stop the page execution and raise the EndRequest event. Thus, the line of code that follows Response.End is not executed. Error occurs with Response.Redirect and Server.Transfer methods too because both the methods call Response.End internally.

When a call is made to the Abort method to destroy a thread, the CLR throws a ThreadAbortException. It is a special exception that can be caught, but will automatically be raised again at the end of the catch block. When this exception is re-raised, the CLR executes all the finally blocks before ending the thread.

Using Visual Studio debugger, we can see the internal message for the exception as “Thread was being aborted.”

Resolution

Try one of the following that suits your workflow:

  • Use a try-catch statement to catch the exception if needed
try { 
  // your code here
} 
catch (System.Threading.ThreadAbortException ex){ 
  // log/handle it
}
  • For Response.End:
    Invoke HttpContext.Current.ApplicationInstance.CompleteRequest method instead of Response.End to bypass the code execution to the Application_EndRequest event
  • For Response.Redirect
    Use an overload,  Response.Redirect(String url, bool endResponse) that passes false for endResponse parameter to suppress the internal call to Response.End
Response.Redirect ("mynextpage.aspx", false);
  • For Server.Transfer
    Use Server.Execute method to bypass abort. When Server.Execute is used, execution of code happens on the new page, post which the control returns to the initial page, just after where it was called.

Refer:
Microsoft Support Article – 312629
MSDN: HttpResponse.Redirect Method
MSDN: HttpResponse.End Method
MSDN: ThreadAbortException Class
MSDN: HttpServerUtility.Execute Method

Conclusion

This is as designed. This exception has bad effect on Web application performance, which is why handling the scenario correctly is important.

Keep learning!

“Cannot evaluate expression because the code of the current method is optimized”

This is one the common error faced by a lot of Visual Studio users.

Problem description

Typically, they get the below error message during debugging:

“Cannot evaluate expression because the code of the current method is optimized.”

Assessment

In .NET, “Function Evaluation (funceval)” is the ability of CLR to inject some arbitrary call while the debuggee is stopped somewhere. Funceval takes charge of the debugger’s chosen thread to execute requested method. Once funceval finishes, it fires a debug event. Technically, CLR have defined ways for debugger to issue a funceval.

CLR allows to initiate funceval only on those threads that are at GC safe point (i.e. when the  thread will not block GC) and Funceval Safe (FESafe) point (i.e. where CLR can actually do the hijack for the funceval.) together.

Thus, possible scenarios for CLR, a thread must be:
1. stopped in managed code  (and at a GC safe point): This implies that we cannot do a funceval in native code. Since, native code is outside the CLR’s control, it is unable to setup the funceval.
2. stopped at a 1st chance or unhandled managed exception (and at a GC safe point): i.e at time of exception, to inspect as much as possible to determine why that exception occurred. (e.g: debugger may try to evaluate and see the Message property on raised exception.)

Overall, common ways to stop in managed code include stopping at a breakpoint, step, Debugger.Break call, intercepting an exception, or at a thread start. This helps in evaluating the method and expressions.
Refer: MSDN Blog: Rules of Funceval

Possible resolutions

Based on the assessment, if thread is not at a FESafe and GCSafe points, CLR will not be able to hijack the thread to initiate funceval. Generally, following helps to make sure funceval initiates when expected:

Step #1:
Make sure that you are not trying to debug a “Release” build. Release is fully optimized and thus will lead to the error in discussion. By using the Standard toolbar or the Configuration Manager, you can switch between Debug & Release.
For more details about it: How to: Set Debug and Release Configurations

Step #2:
If you still get the error, “Debug option” might be set for optimization. Verify & Uncheck the “Optimize code” property under Project “Properties”:

  • Right click the Project
  • Select option “Properties”
  • Go to “Build” tab
  • Uncheck the checkbox “Optimize code”

Step #3:
If you still get the error, “Debug Info” mode might be incorrect. Verify & set it to “full” under “Advanced Build Settings”:

  • Right click the Project
  • Select option “Properties”
  • Go to “Build” tab
  • Click “Advanced” button
  • Set “Debug Info” as “full”

Step #4:
If you still face the issue, try the following:

  • Do a “Clean” & then a “Rebuild” of your solution file
  • While debugging:
    1. Go to modules window (VS Menu -> Debug -> Windows -> Modules)
    2. Find your assembly in the list of loaded modules.
    3. Check the Path listed against the loaded assembly is what you expect it to be
    4. Check the modified Timestamp of the file to confirm that the assembly was actually rebuilt
    5. Check whether or not the loaded module is optimised or not
  • Remote chance could be that your call stack is getting optimized because your method signature is too large (more than 256 argument bytes). Read more about it at this MSDN blog

Conclusion

It’s not an error but an information based on certain settings and as designed based on how .NET runtime works.

Keep learning!