THREADING
- Generally a code block is R/W from motherboard memory to CPU cache this block is called "Cache Line"
- In Hyper-threaded CPU - logical CPU share single CPU cache so their is no visible impact.
- On multi-CPU each CPU has it's own cache so problem arises when these cache access same block of memory.
- Flushing changes from CPU cache to memory is done at later stage and can't predicted.Moreover CPU execute the instructions out of program order but in last it make sure that given code executes as per expectations.
- Issue is known as - Cache Coherency
- Cache Coherency hurt performance so try to write code to avoid shared data access like Try to implement method that access local variables and parameters
- Thread class provide VolatileRead and VolatileWrite static methods. - cumbersome
- C# provide volatile keyword for some datatype so that when those variables are read/write it doesn't cache the value on CPU register.
- Volatile can be applied on Byte,Int,Char,Single and boolean.Reftype and enum of these types.
- C# doesn't support passing volatile field by Reference.
- Interlocked uses cache coherency so no need to worry about membory model. All thread Synchronization locks call interlocked internally.
- Thread syn locks are: Monitor, Mutex, Semaphore, ReaderWriterLock, AutoResetEvent, ManualResetEvent.
- MONITOR or LOCK we can use the Monitor class to acquire a lock on that object by calling Monitor.Enter(object). Any other thread wanting to execute the same code would need to acquire the same lock and will be paused until the first thread releases the lock by calling Monitor. Exit(object). if lock keyword is uses enter and exit code is emmited automatically.
- READERWRITER LOCK: not recommended due to performance,Recursion etc; Recursion - Thread that enters the lock must be the thread to exit the lock.
- So in Asynchronus programming model, lock with recursion wouldn't work.(Monitor and READERWRITER support recursion)
- Windows also offer some kernel object for thread synchronization like Mutexes,Semaphores and Events. Threading.WaitHandle is an FCL abstract class that wraps these windows kernel object.
- Derived Classes of Mutex,Semaphore,EventWaithandle (base) are AutoResetEvent, ManualResetEvent (concreate)
- Monitor and ReaderWriter allow synchronization of thread running in single appdomain.
- Kernel object use to synchronize threads running in diff appdomains or in different processes.So they have security rights associated with them
- When thread waits on kernel object, the thread must always transition from user mode to kernel mode so very slow compare to Monitor and ReaderWriter lock.
System.Threading.
static readonly object locker = new
object();
lock (locker)
{
if (!done)
{ Console.WriteLine ("Done"); done = true; }
}
Public delegate void ThreadStart();
Thread t = new Thread (new ThreadStart (Go));
Thread t = new Thread (Go);
Thread t = new Thread ( () => Console.WriteLine ("Hello!") );
THREAD POOL:
Synchronization can be achieved in following four
ways: These categories are not very clearly segregated many of the construct fall in one or all categories.
Monitor.Enter
(_locker);
try
{
if (_val2 != 0)
Console.WriteLine (_val1 / _val2);
_val2 = 0;
}
finally { Monitor.Exit (_locker); }
{
static SemaphoreSlim _sem = new SemaphoreSlim (3); // Capacity of 3
static void Main()
{ for (int i = 1; i <= 5; i++) new Thread (Enter).Start (i); } static void Enter (object id) { Console.WriteLine (id + " wants to enter"); _sem.Wait(); Console.WriteLine (id + " is in!"); // Only three threads Thread.Sleep (1000 * (int) id); // can be here at Console.WriteLine (id + " is leaving"); // a time. _sem.Release(); } } 1 wants to enter 1 is in! 2 wants to enter 2 is in! 3 wants to enter 3 is in! 4 wants to enter 5 wants to enter 1 is leaving 4 is in! 2 is leaving 5 is in!
class Test
{
// The same
LocalDataStoreSlot object can be used across all threads.
LocalDataStoreSlot
_secSlot = Thread.GetNamedDataSlot ("securityLevel");
// This property
has a separate value on each thread.
int SecurityLevel
{
get
{
object data =
Thread.GetData (_secSlot);
return data == null
? 0 : (int) data; // null == uninitialized
}
set {
Thread.SetData (_secSlot, value); }
}
·
ThreadLocal
·
New to framework 4.0
·
Work with instance field as well as default in
initialization for static field.
·
Use full in instance field ex we have to generate
Random# in a type using Random class, which is not thread safe.
·
If you have to execute some method repeatedly at
regular interval the easiest way is with the timers.
·
System.Threading .Timer – Multithreaded
·
System.Timers.Timer – Multithreaded. It wraps
System.Threading.Timer
·
System.Windows.Forms.Timer Single threaded
windows form timer
·
System.Windows.Threading.DispatcherTimer – Single
Threaded WPF timer
·
Multitheraded timers use thread pool so that few
threads serve many timers
·
This means
that the callback method or Elapsed event may fire on a different thread each
time it is called.
·
Furthermore, Elapsed always fires (approximately)
on time—regardless of whether the previous Elapsed has finished executing.
Hence, callbacks or event handlers must be thread-safe.
·
The precision of multithreaded timers depends on
the operating system, and is typically in the 10–20 ms region.
·
The single-threaded timers are not designed to
work outside their respective environments. If you use a Windows Forms timer in a Windows Service
application, for instance, the Timer event won’t fire!
·
Single Threaded times has following advantages:
·
Thread Safe
·
Tick will fire only when previous tick completed
it’s execution
·
Since event is fired on same thread, UI elements
can be updated from the Tick event handler without calling Control.Invoke or
Dispatcher.Invoke.
8.
Non Blocking Synchronization
·
Although these constructs are simple, chances of
going it wrong is high. Also acquiring and releasing uncontended lock takes
only 10-20ns.
·
Non blocking constructs also works across multi
processes.
Questions:
1.
Explain work stealing in TPL. How it works and
why? Expected answer: Explain how the core that owns the queue extracts items
on one side while a core that does not own the queue "steals" from
the other side in order to preserve CPU cache lines.
2.
I would also inquire how one might end up with an
application that is multi-threaded without ever explicitly creating a thread.
·
Event handlers can run in another thread
(SerialPort.DataReceived comes to mind, as does one or two of the three Timers
in .Net).
3.
Reentrnat:
In general, a
re-entrant block of code is one that can be entered by another actor before an
earlier invocation has finished, without affecting the path that the first
actor would have taken through the code. That is, it is possible to re-enter
the code while it's already running and still produce correct results.
In most cases, the
"actors" are threads of the same process, but the concepts of thread safety and re-entrant are
subtly different: not every thread-safe block is re-entrant, but every
re-entrant block is thread-safe. That is, re-entrancy is a stronger property
than thread safety. Here's a good
example
from Raymond Chen of how a block of code might be thread-safe but not
re-entrant.
There's a special
case when the code is recursive: the same actor is calling into the code before
its own invocation is finished, as Marc Gravell points out. All correct
recursive blocks are re-entrant; of course, not every re-entrant block is
recursive.
Wednesday, May 22, 2013
12:53 PM
Func
Encapsulates a
method that has no parameters and returns a value of the type specified by the
TResult parameter.
public delegate
TResult Func<out TResult>()
Func<bool>
methodCall = output.SendToFile;
Func<bool>
methodCall = delegate() { return output.SendToFile(); };
Func<bool>
methodCall = () => output.SendToFile();
1. IEnumerable
Pasted from <http://msdn.microsoft.com/en-us/library/bb546142.aspx>
LINQ can only worked on
IEnumerable types or it's inherit type.+
http://msdn.microsoft.com/en-us/library/7a2f3ay4(v=vs.90).aspx
|
No comments:
Post a Comment