Compare commits

...

6 Commits

Author SHA1 Message Date
Øyvind Skaaden 45bec71687 Finish all videoes 2021-05-18 19:29:40 +02:00
Øyvind Skaaden 278d2975c9 Testing 2021-05-18 17:21:29 +02:00
Øyvind Skaaden 854ed6508a Fixed post-recieve 2021-05-18 17:18:02 +02:00
Øyvind Skaaden e4131cbcaa Update last updated 2021-05-18 17:16:11 +02:00
Øyvind Skaaden a552d38111 Update gem 2021-05-18 16:59:51 +02:00
Øyvind Skaaden 757b0a5799 Added some from video 12 and Start video 13 2021-05-15 16:35:26 +02:00
4 changed files with 174 additions and 12 deletions

View File

@ -7,7 +7,7 @@ source "https://rubygems.org"
#
# This will help ensure the proper Jekyll version is running.
# Happy Jekylling!
gem "jekyll", "~> 4.1.1"
gem "jekyll", "~> 4.2.0"
# This is the default theme for new Jekyll sites. You may change this to anything you like.
# If you want to use GitHub Pages, remove the "gem "jekyll"" above and

View File

@ -36,8 +36,6 @@ author:
collections:
posts:
excerpt_separator: <!--more-->
markdown: kramdown

View File

@ -14,7 +14,7 @@
-
course: ttk4145
desc: Sanntidsprogrammering, våren 2021.
updated: 2021-05-04
updated: 2021-05-18
-
course: tiø4252
desc: Teknologiledelse, våren 2021.

View File

@ -26,7 +26,7 @@ Hard to capture faults.
### Traditional error handeling
{% highlight c %}
{% highlight java %}
FILE *
openConfigFile(){
FILE * f = fopen("/path/to/config.conf");
@ -248,7 +248,7 @@ Controlling a pump filling a tank.
#### A trivial solution: "Cyclic Exectutive"
{% highlight c %}
{% highlight java %}
oldTime = now();
i = 0;
while(true) {
@ -282,7 +282,7 @@ while(true) {
* Scheduler often inculuded in OSes
* Introducing priorities
{% highlight c %}
{% highlight java %}
/**
* scheduler_registerThread(function, time, priority)
* Higher priority numer means higher priority in scheduler
@ -331,11 +331,11 @@ main() {
* Make a handler for a timer interrupt
* Store all registers (including IP & SP) in a "thread object"
* Organize queue of processes (Round Robin e.g. - a collection of thread objects?)
* Can synchronize by: while(!ready); (busy wating, "spin locks")
* Can synchronize by: `while(!ready);` (busy wating, "spin locks")
**Bad solution**
{% highlight c%}
{% highlight java%}
while(lock==1) {}
lock = 1;
// We may run
@ -344,7 +344,7 @@ lock = 0;
**Better solution**
{% highlight c%}
{% highlight java%}
void t1() {
flag1 = 1; // Declare my intention
turn = 2; // But try to be polite
@ -371,6 +371,170 @@ void t1() {
**Let us introduce another queue; the collection of threads not running, waiting for something**
* Fixes the bad performance of spin locks. Is conceptually better.
* "Suspend" moves a thread object from "run" queue to "blocked" queue
* "Resume" moves it back.
* `suspend` moves a thread object from "run" queue to "blocked" queue
* `resume` moves it back.
##### Two bad solutions
{% highlight java%}
t1(){
while(busy == 1) suspend();
busy = 1; // It is free; tak it - No
// Run
busy = 0; // Release resource
resume t2 // No
}
{% endhighlight %}
or
{% highlight java%}
t1(){
while(TestNSet(busy, 1) == 1) suspend();
// We own resource
// Run
busy = 0;
resume t2 // No
}
{% endhighlight %}
##### The suspend/resume problem
{% highlight java%}
// Global variables
bool g_initDone = False;
// Threads
t1(){ t2(){
/* Do init */ if (g_initDone == False) {
g_initDone = True; Suspend();
resume(t2) }
// Continue executing // Continue exectuting
} }
{% endhighlight %}
#### Priorities
* Threads mey have different *priorities*. (A sortet run-queue, or more of them.)
* Only if there are no running threads on a higher priority, a thread will run.
* We are not aiming for some sens of fairness (!). But predictability.
* And priorities supports schedulability proofs.
* But we open ourselves up to *starvation*. A thread may not ever get to run, even if it is runnable.
#### Application-level syncronization
**SO, the application programmer needs some syncronozation primitives...**
* `sleep()`? - Ok
* Publish `suspend` and `resume` - No
* Events (`wait` and `signal`) - Just named versions of suspend & resume semantics.
* Fixes the need to know aboud "thread objects". But no
* ...or "Condition variables" - same
### Semaphores
**A counting semaphore**
* `signal(SEM)` increases the counter (possibly resuming a thread waiting for the semaphore)
* `wait(SEM)` decrements the counter - will block (be suspended) `if SEM == 0`
* The semaphores value can not be negative
* Of course; These calls are protected from interleaving by disabling the timer interrupt
**We solve beautifully:**
* Mutual Exclusion
* Conditional Synchronization (ref `suspend`/`resume`)
* Basic resource allocation
**Semaphore variations**
* `wait` and `signal` nay take parameter value to add or subtract
* `getValue(SEM)` returning the value of the semaphore. (Fishy)
* BInary semaphores (`signal` will fail `if SEM == 1`)
* Who is woken at `signal` (FIFO, Arbitrary, Highest priority)
* The mutex
* binary
* ownership
* allows mulitple waits by owner
* regions (may be released by Javas `wait` or POSIX condition variables)
* RTFM
**Semaphore challenges**
* Breaks modules (both ways)
* Does not scale!
* Deadlocks
* Global analysis --> Does not scale
* Can not release "temporarily
* "Limited expressive power". Some reasonalbe problems are hard to solve
* Ref ["The Little Book of Semaphores"](https://greenteapress.com/semaphores/LittleBookOfSemaphores.pdf)
### Why shared-variable synchronization
**Why not?**
* "Shared variables" is bad code quality
* Ref global variables, and data members in module interfaces
* An obvious bottleneck? Scales terribly
* "Variables" are passive objects
* They can not protect themselves
* Why use synchronization when it is communication we need?
* Technology transfers badly to distibuted systems
* ... and this is before we start discussing how hard it is
**Why?**
* Part of the "real-time" design pattern
* "One thread per timing demand"
* We do have scheduling proofs and best practises
* Timing analysis is global anyway
* Scalability and deadlock analysis may not be the limiting constraint
* HW is shared memory architecture
* Infrastucture is avalible
* Communication systems requires infrastucture that we may not have
#### *All* resources are shared!
* Memory, certainly
* "Hidden" memory used by libraries (.. your own modules and the kernel)
* If the library takes care of this itself, it is called *"reentrant"*
* Sensors and actuators
* "CPU" - Computing capacity
* *This* is real-time programming; We solve it by *Scheduling*
* ... any other interface
#### Some standard problems/pit-falls
* **Race condition**: A bug that surfaces by unfortunate timing or order of events
* **Deadlock:** system in circular wait
* Special case of livelock
* Does not use CPU
* **Livelock:** system locked in a subset of states
* like deadlock, but we use CPU
* Busy-Waiting is a livelock
* **Starvation:** A thread does "by accident" not get the necessary resources
#### Features in syncronization
* Critical Section - Code that must not be interupted
* Mutual Exclusion - More piecesof code that must not interrupt each other
* Bounded buffer - Buffer with full/empty synchronization
* Read/Write Locks
* Readers can interleave eachother
* Writers have mutual exclusion
* Condition Syncronization - Blocking on event or status
* Guards etc.
* Resource allocation
* More than mutual exclution!
* Ref: The lock manager
* Rendezvouz/barriere - Synchronization point
* Ref: AA "end boundary"
* Communication
* Broadcast
* ...