Compare commits
3 Commits
d6e0fb978e
...
final-subm
| Author | SHA1 | Date | |
|---|---|---|---|
|
075c605778
|
|||
|
3408d090f0
|
|||
|
820e2d24b8
|
165
LICENSE
Normal file
165
LICENSE
Normal file
@@ -0,0 +1,165 @@
|
|||||||
|
GNU LESSER GENERAL PUBLIC LICENSE
|
||||||
|
Version 3, 29 June 2007
|
||||||
|
|
||||||
|
Copyright (C) 2007 Free Software Foundation, Inc. <https://fsf.org/>
|
||||||
|
Everyone is permitted to copy and distribute verbatim copies
|
||||||
|
of this license document, but changing it is not allowed.
|
||||||
|
|
||||||
|
|
||||||
|
This version of the GNU Lesser General Public License incorporates
|
||||||
|
the terms and conditions of version 3 of the GNU General Public
|
||||||
|
License, supplemented by the additional permissions listed below.
|
||||||
|
|
||||||
|
0. Additional Definitions.
|
||||||
|
|
||||||
|
As used herein, "this License" refers to version 3 of the GNU Lesser
|
||||||
|
General Public License, and the "GNU GPL" refers to version 3 of the GNU
|
||||||
|
General Public License.
|
||||||
|
|
||||||
|
"The Library" refers to a covered work governed by this License,
|
||||||
|
other than an Application or a Combined Work as defined below.
|
||||||
|
|
||||||
|
An "Application" is any work that makes use of an interface provided
|
||||||
|
by the Library, but which is not otherwise based on the Library.
|
||||||
|
Defining a subclass of a class defined by the Library is deemed a mode
|
||||||
|
of using an interface provided by the Library.
|
||||||
|
|
||||||
|
A "Combined Work" is a work produced by combining or linking an
|
||||||
|
Application with the Library. The particular version of the Library
|
||||||
|
with which the Combined Work was made is also called the "Linked
|
||||||
|
Version".
|
||||||
|
|
||||||
|
The "Minimal Corresponding Source" for a Combined Work means the
|
||||||
|
Corresponding Source for the Combined Work, excluding any source code
|
||||||
|
for portions of the Combined Work that, considered in isolation, are
|
||||||
|
based on the Application, and not on the Linked Version.
|
||||||
|
|
||||||
|
The "Corresponding Application Code" for a Combined Work means the
|
||||||
|
object code and/or source code for the Application, including any data
|
||||||
|
and utility programs needed for reproducing the Combined Work from the
|
||||||
|
Application, but excluding the System Libraries of the Combined Work.
|
||||||
|
|
||||||
|
1. Exception to Section 3 of the GNU GPL.
|
||||||
|
|
||||||
|
You may convey a covered work under sections 3 and 4 of this License
|
||||||
|
without being bound by section 3 of the GNU GPL.
|
||||||
|
|
||||||
|
2. Conveying Modified Versions.
|
||||||
|
|
||||||
|
If you modify a copy of the Library, and, in your modifications, a
|
||||||
|
facility refers to a function or data to be supplied by an Application
|
||||||
|
that uses the facility (other than as an argument passed when the
|
||||||
|
facility is invoked), then you may convey a copy of the modified
|
||||||
|
version:
|
||||||
|
|
||||||
|
a) under this License, provided that you make a good faith effort to
|
||||||
|
ensure that, in the event an Application does not supply the
|
||||||
|
function or data, the facility still operates, and performs
|
||||||
|
whatever part of its purpose remains meaningful, or
|
||||||
|
|
||||||
|
b) under the GNU GPL, with none of the additional permissions of
|
||||||
|
this License applicable to that copy.
|
||||||
|
|
||||||
|
3. Object Code Incorporating Material from Library Header Files.
|
||||||
|
|
||||||
|
The object code form of an Application may incorporate material from
|
||||||
|
a header file that is part of the Library. You may convey such object
|
||||||
|
code under terms of your choice, provided that, if the incorporated
|
||||||
|
material is not limited to numerical parameters, data structure
|
||||||
|
layouts and accessors, or small macros, inline functions and templates
|
||||||
|
(ten or fewer lines in length), you do both of the following:
|
||||||
|
|
||||||
|
a) Give prominent notice with each copy of the object code that the
|
||||||
|
Library is used in it and that the Library and its use are
|
||||||
|
covered by this License.
|
||||||
|
|
||||||
|
b) Accompany the object code with a copy of the GNU GPL and this license
|
||||||
|
document.
|
||||||
|
|
||||||
|
4. Combined Works.
|
||||||
|
|
||||||
|
You may convey a Combined Work under terms of your choice that,
|
||||||
|
taken together, effectively do not restrict modification of the
|
||||||
|
portions of the Library contained in the Combined Work and reverse
|
||||||
|
engineering for debugging such modifications, if you also do each of
|
||||||
|
the following:
|
||||||
|
|
||||||
|
a) Give prominent notice with each copy of the Combined Work that
|
||||||
|
the Library is used in it and that the Library and its use are
|
||||||
|
covered by this License.
|
||||||
|
|
||||||
|
b) Accompany the Combined Work with a copy of the GNU GPL and this license
|
||||||
|
document.
|
||||||
|
|
||||||
|
c) For a Combined Work that displays copyright notices during
|
||||||
|
execution, include the copyright notice for the Library among
|
||||||
|
these notices, as well as a reference directing the user to the
|
||||||
|
copies of the GNU GPL and this license document.
|
||||||
|
|
||||||
|
d) Do one of the following:
|
||||||
|
|
||||||
|
0) Convey the Minimal Corresponding Source under the terms of this
|
||||||
|
License, and the Corresponding Application Code in a form
|
||||||
|
suitable for, and under terms that permit, the user to
|
||||||
|
recombine or relink the Application with a modified version of
|
||||||
|
the Linked Version to produce a modified Combined Work, in the
|
||||||
|
manner specified by section 6 of the GNU GPL for conveying
|
||||||
|
Corresponding Source.
|
||||||
|
|
||||||
|
1) Use a suitable shared library mechanism for linking with the
|
||||||
|
Library. A suitable mechanism is one that (a) uses at run time
|
||||||
|
a copy of the Library already present on the user's computer
|
||||||
|
system, and (b) will operate properly with a modified version
|
||||||
|
of the Library that is interface-compatible with the Linked
|
||||||
|
Version.
|
||||||
|
|
||||||
|
e) Provide Installation Information, but only if you would otherwise
|
||||||
|
be required to provide such information under section 6 of the
|
||||||
|
GNU GPL, and only to the extent that such information is
|
||||||
|
necessary to install and execute a modified version of the
|
||||||
|
Combined Work produced by recombining or relinking the
|
||||||
|
Application with a modified version of the Linked Version. (If
|
||||||
|
you use option 4d0, the Installation Information must accompany
|
||||||
|
the Minimal Corresponding Source and Corresponding Application
|
||||||
|
Code. If you use option 4d1, you must provide the Installation
|
||||||
|
Information in the manner specified by section 6 of the GNU GPL
|
||||||
|
for conveying Corresponding Source.)
|
||||||
|
|
||||||
|
5. Combined Libraries.
|
||||||
|
|
||||||
|
You may place library facilities that are a work based on the
|
||||||
|
Library side by side in a single library together with other library
|
||||||
|
facilities that are not Applications and are not covered by this
|
||||||
|
License, and convey such a combined library under terms of your
|
||||||
|
choice, if you do both of the following:
|
||||||
|
|
||||||
|
a) Accompany the combined library with a copy of the same work based
|
||||||
|
on the Library, uncombined with any other library facilities,
|
||||||
|
conveyed under the terms of this License.
|
||||||
|
|
||||||
|
b) Give prominent notice with the combined library that part of it
|
||||||
|
is a work based on the Library, and explaining where to find the
|
||||||
|
accompanying uncombined form of the same work.
|
||||||
|
|
||||||
|
6. Revised Versions of the GNU Lesser General Public License.
|
||||||
|
|
||||||
|
The Free Software Foundation may publish revised and/or new versions
|
||||||
|
of the GNU Lesser General Public License from time to time. Such new
|
||||||
|
versions will be similar in spirit to the present version, but may
|
||||||
|
differ in detail to address new problems or concerns.
|
||||||
|
|
||||||
|
Each version is given a distinguishing version number. If the
|
||||||
|
Library as you received it specifies that a certain numbered version
|
||||||
|
of the GNU Lesser General Public License "or any later version"
|
||||||
|
applies to it, you have the option of following the terms and
|
||||||
|
conditions either of that published version or of any later version
|
||||||
|
published by the Free Software Foundation. If the Library as you
|
||||||
|
received it does not specify a version number of the GNU Lesser
|
||||||
|
General Public License, you may choose any version of the GNU Lesser
|
||||||
|
General Public License ever published by the Free Software Foundation.
|
||||||
|
|
||||||
|
If the Library as you received it specifies that a proxy can decide
|
||||||
|
whether future versions of the GNU Lesser General Public License shall
|
||||||
|
apply, that proxy's public statement of acceptance of any version is
|
||||||
|
permanent authorization for you to choose that version for the
|
||||||
|
Library.
|
||||||
@@ -3,6 +3,51 @@
|
|||||||
"version": 2,
|
"version": 2,
|
||||||
"source": "https://excalidraw.com",
|
"source": "https://excalidraw.com",
|
||||||
"elements": [
|
"elements": [
|
||||||
|
{
|
||||||
|
"id": "o0TImuY5NBuVnjNlXMAzk",
|
||||||
|
"type": "arrow",
|
||||||
|
"x": 1701.3300555241196,
|
||||||
|
"y": 300.032479332732,
|
||||||
|
"width": 1.3300555241196435,
|
||||||
|
"height": 739.967520667268,
|
||||||
|
"angle": 0,
|
||||||
|
"strokeColor": "#1e1e1e",
|
||||||
|
"backgroundColor": "#b2f2bb",
|
||||||
|
"fillStyle": "hachure",
|
||||||
|
"strokeWidth": 2,
|
||||||
|
"strokeStyle": "dotted",
|
||||||
|
"roughness": 1,
|
||||||
|
"opacity": 100,
|
||||||
|
"groupIds": [],
|
||||||
|
"frameId": null,
|
||||||
|
"index": "b04",
|
||||||
|
"roundness": {
|
||||||
|
"type": 2
|
||||||
|
},
|
||||||
|
"seed": 1454586268,
|
||||||
|
"version": 70,
|
||||||
|
"versionNonce": 1445870372,
|
||||||
|
"isDeleted": false,
|
||||||
|
"boundElements": [],
|
||||||
|
"updated": 1768903438971,
|
||||||
|
"link": null,
|
||||||
|
"locked": false,
|
||||||
|
"points": [
|
||||||
|
[
|
||||||
|
0,
|
||||||
|
0
|
||||||
|
],
|
||||||
|
[
|
||||||
|
-1.3300555241196435,
|
||||||
|
739.967520667268
|
||||||
|
]
|
||||||
|
],
|
||||||
|
"startBinding": null,
|
||||||
|
"endBinding": null,
|
||||||
|
"startArrowhead": null,
|
||||||
|
"endArrowhead": "arrow",
|
||||||
|
"elbowed": false
|
||||||
|
},
|
||||||
{
|
{
|
||||||
"id": "dFrrZb58NASi_ovlDPlr8",
|
"id": "dFrrZb58NASi_ovlDPlr8",
|
||||||
"type": "arrow",
|
"type": "arrow",
|
||||||
@@ -167,51 +212,6 @@
|
|||||||
"autoResize": true,
|
"autoResize": true,
|
||||||
"lineHeight": 1.25
|
"lineHeight": 1.25
|
||||||
},
|
},
|
||||||
{
|
|
||||||
"id": "o0TImuY5NBuVnjNlXMAzk",
|
|
||||||
"type": "arrow",
|
|
||||||
"x": 1701.3300555241196,
|
|
||||||
"y": 300.032479332732,
|
|
||||||
"width": 1.3300555241196435,
|
|
||||||
"height": 739.967520667268,
|
|
||||||
"angle": 0,
|
|
||||||
"strokeColor": "#1e1e1e",
|
|
||||||
"backgroundColor": "#b2f2bb",
|
|
||||||
"fillStyle": "hachure",
|
|
||||||
"strokeWidth": 2,
|
|
||||||
"strokeStyle": "dotted",
|
|
||||||
"roughness": 1,
|
|
||||||
"opacity": 100,
|
|
||||||
"groupIds": [],
|
|
||||||
"frameId": null,
|
|
||||||
"index": "b0B",
|
|
||||||
"roundness": {
|
|
||||||
"type": 2
|
|
||||||
},
|
|
||||||
"seed": 1454586268,
|
|
||||||
"version": 69,
|
|
||||||
"versionNonce": 1608574364,
|
|
||||||
"isDeleted": false,
|
|
||||||
"boundElements": [],
|
|
||||||
"updated": 1768867948553,
|
|
||||||
"link": null,
|
|
||||||
"locked": false,
|
|
||||||
"points": [
|
|
||||||
[
|
|
||||||
0,
|
|
||||||
0
|
|
||||||
],
|
|
||||||
[
|
|
||||||
-1.3300555241196435,
|
|
||||||
739.967520667268
|
|
||||||
]
|
|
||||||
],
|
|
||||||
"startBinding": null,
|
|
||||||
"endBinding": null,
|
|
||||||
"startArrowhead": null,
|
|
||||||
"endArrowhead": "arrow",
|
|
||||||
"elbowed": false
|
|
||||||
},
|
|
||||||
{
|
{
|
||||||
"id": "-casMJtwPjypfg0mk5nHO",
|
"id": "-casMJtwPjypfg0mk5nHO",
|
||||||
"type": "rectangle",
|
"type": "rectangle",
|
||||||
@@ -834,8 +834,8 @@
|
|||||||
"type": 3
|
"type": 3
|
||||||
},
|
},
|
||||||
"seed": 1744692380,
|
"seed": 1744692380,
|
||||||
"version": 45,
|
"version": 47,
|
||||||
"versionNonce": 871659940,
|
"versionNonce": 766960036,
|
||||||
"isDeleted": false,
|
"isDeleted": false,
|
||||||
"boundElements": [
|
"boundElements": [
|
||||||
{
|
{
|
||||||
@@ -843,7 +843,7 @@
|
|||||||
"id": "PgDfZjA4Q7u8kt6vwTGzx"
|
"id": "PgDfZjA4Q7u8kt6vwTGzx"
|
||||||
}
|
}
|
||||||
],
|
],
|
||||||
"updated": 1768867714260,
|
"updated": 1768903373256,
|
||||||
"link": null,
|
"link": null,
|
||||||
"locked": false
|
"locked": false
|
||||||
},
|
},
|
||||||
@@ -906,8 +906,8 @@
|
|||||||
"type": 3
|
"type": 3
|
||||||
},
|
},
|
||||||
"seed": 253023780,
|
"seed": 253023780,
|
||||||
"version": 104,
|
"version": 106,
|
||||||
"versionNonce": 1629844764,
|
"versionNonce": 1020116772,
|
||||||
"isDeleted": false,
|
"isDeleted": false,
|
||||||
"boundElements": [
|
"boundElements": [
|
||||||
{
|
{
|
||||||
@@ -915,7 +915,7 @@
|
|||||||
"id": "utn7zQfYBfbFTRgfoV5GA"
|
"id": "utn7zQfYBfbFTRgfoV5GA"
|
||||||
}
|
}
|
||||||
],
|
],
|
||||||
"updated": 1768867894355,
|
"updated": 1768903372699,
|
||||||
"link": null,
|
"link": null,
|
||||||
"locked": false
|
"locked": false
|
||||||
},
|
},
|
||||||
@@ -1013,11 +1013,11 @@
|
|||||||
"type": 2
|
"type": 2
|
||||||
},
|
},
|
||||||
"seed": 1181892004,
|
"seed": 1181892004,
|
||||||
"version": 163,
|
"version": 164,
|
||||||
"versionNonce": 439755044,
|
"versionNonce": 455788316,
|
||||||
"isDeleted": false,
|
"isDeleted": true,
|
||||||
"boundElements": null,
|
"boundElements": null,
|
||||||
"updated": 1768867969455,
|
"updated": 1768903375842,
|
||||||
"link": null,
|
"link": null,
|
||||||
"locked": false,
|
"locked": false,
|
||||||
"points": [
|
"points": [
|
||||||
@@ -1095,16 +1095,16 @@
|
|||||||
"type": 3
|
"type": 3
|
||||||
},
|
},
|
||||||
"seed": 1182313500,
|
"seed": 1182313500,
|
||||||
"version": 59,
|
"version": 60,
|
||||||
"versionNonce": 2068777508,
|
"versionNonce": 1625923492,
|
||||||
"isDeleted": false,
|
"isDeleted": true,
|
||||||
"boundElements": [
|
"boundElements": [
|
||||||
{
|
{
|
||||||
"type": "text",
|
"type": "text",
|
||||||
"id": "DCXi27QHl9Zsqz5FCQgzM"
|
"id": "DCXi27QHl9Zsqz5FCQgzM"
|
||||||
}
|
}
|
||||||
],
|
],
|
||||||
"updated": 1768867500161,
|
"updated": 1768903353395,
|
||||||
"link": null,
|
"link": null,
|
||||||
"locked": false
|
"locked": false
|
||||||
},
|
},
|
||||||
@@ -1128,11 +1128,11 @@
|
|||||||
"index": "b0UV",
|
"index": "b0UV",
|
||||||
"roundness": null,
|
"roundness": null,
|
||||||
"seed": 1952001436,
|
"seed": 1952001436,
|
||||||
"version": 3,
|
"version": 4,
|
||||||
"versionNonce": 414597916,
|
"versionNonce": 867998876,
|
||||||
"isDeleted": false,
|
"isDeleted": true,
|
||||||
"boundElements": null,
|
"boundElements": null,
|
||||||
"updated": 1768867500581,
|
"updated": 1768903353395,
|
||||||
"link": null,
|
"link": null,
|
||||||
"locked": false,
|
"locked": false,
|
||||||
"text": "1",
|
"text": "1",
|
||||||
@@ -1167,11 +1167,11 @@
|
|||||||
"type": 2
|
"type": 2
|
||||||
},
|
},
|
||||||
"seed": 325594908,
|
"seed": 325594908,
|
||||||
"version": 185,
|
"version": 186,
|
||||||
"versionNonce": 527280036,
|
"versionNonce": 1776276380,
|
||||||
"isDeleted": false,
|
"isDeleted": true,
|
||||||
"boundElements": null,
|
"boundElements": null,
|
||||||
"updated": 1768867917738,
|
"updated": 1768903351390,
|
||||||
"link": null,
|
"link": null,
|
||||||
"locked": false,
|
"locked": false,
|
||||||
"points": [
|
"points": [
|
||||||
@@ -1367,8 +1367,8 @@
|
|||||||
{
|
{
|
||||||
"id": "a1AK0dTA94waRfKIGtjcX",
|
"id": "a1AK0dTA94waRfKIGtjcX",
|
||||||
"type": "rectangle",
|
"type": "rectangle",
|
||||||
"x": 1406,
|
"x": 1500,
|
||||||
"y": 519,
|
"y": 520,
|
||||||
"width": 80,
|
"width": 80,
|
||||||
"height": 80,
|
"height": 80,
|
||||||
"angle": 0,
|
"angle": 0,
|
||||||
@@ -1386,8 +1386,8 @@
|
|||||||
"type": 3
|
"type": 3
|
||||||
},
|
},
|
||||||
"seed": 804000548,
|
"seed": 804000548,
|
||||||
"version": 78,
|
"version": 87,
|
||||||
"versionNonce": 116530980,
|
"versionNonce": 990199460,
|
||||||
"isDeleted": false,
|
"isDeleted": false,
|
||||||
"boundElements": [
|
"boundElements": [
|
||||||
{
|
{
|
||||||
@@ -1395,15 +1395,15 @@
|
|||||||
"id": "TQknVVA73H8eY5J6Q8sd9"
|
"id": "TQknVVA73H8eY5J6Q8sd9"
|
||||||
}
|
}
|
||||||
],
|
],
|
||||||
"updated": 1768867501892,
|
"updated": 1768903357536,
|
||||||
"link": null,
|
"link": null,
|
||||||
"locked": false
|
"locked": false
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
"id": "TQknVVA73H8eY5J6Q8sd9",
|
"id": "TQknVVA73H8eY5J6Q8sd9",
|
||||||
"type": "text",
|
"type": "text",
|
||||||
"x": 1436.1000003814697,
|
"x": 1530.1000003814697,
|
||||||
"y": 536.5,
|
"y": 537.5,
|
||||||
"width": 19.799999237060547,
|
"width": 19.799999237060547,
|
||||||
"height": 45,
|
"height": 45,
|
||||||
"angle": 0,
|
"angle": 0,
|
||||||
@@ -1419,11 +1419,11 @@
|
|||||||
"index": "b0Z",
|
"index": "b0Z",
|
||||||
"roundness": null,
|
"roundness": null,
|
||||||
"seed": 1620658332,
|
"seed": 1620658332,
|
||||||
"version": 3,
|
"version": 12,
|
||||||
"versionNonce": 680017436,
|
"versionNonce": 1554893348,
|
||||||
"isDeleted": false,
|
"isDeleted": false,
|
||||||
"boundElements": null,
|
"boundElements": null,
|
||||||
"updated": 1768867502318,
|
"updated": 1768903357536,
|
||||||
"link": null,
|
"link": null,
|
||||||
"locked": false,
|
"locked": false,
|
||||||
"text": "2",
|
"text": "2",
|
||||||
@@ -1526,7 +1526,7 @@
|
|||||||
{
|
{
|
||||||
"id": "EXd8E-Umx_78sjBL4Ki6W",
|
"id": "EXd8E-Umx_78sjBL4Ki6W",
|
||||||
"type": "rectangle",
|
"type": "rectangle",
|
||||||
"x": 1400,
|
"x": 1500,
|
||||||
"y": 720,
|
"y": 720,
|
||||||
"width": 80,
|
"width": 80,
|
||||||
"height": 80,
|
"height": 80,
|
||||||
@@ -1545,8 +1545,8 @@
|
|||||||
"type": 3
|
"type": 3
|
||||||
},
|
},
|
||||||
"seed": 2140102940,
|
"seed": 2140102940,
|
||||||
"version": 16,
|
"version": 21,
|
||||||
"versionNonce": 1305571492,
|
"versionNonce": 1730875164,
|
||||||
"isDeleted": false,
|
"isDeleted": false,
|
||||||
"boundElements": [
|
"boundElements": [
|
||||||
{
|
{
|
||||||
@@ -1554,14 +1554,14 @@
|
|||||||
"id": "y-9Stf17pe9fWn0kSmWVL"
|
"id": "y-9Stf17pe9fWn0kSmWVL"
|
||||||
}
|
}
|
||||||
],
|
],
|
||||||
"updated": 1768867618260,
|
"updated": 1768903389485,
|
||||||
"link": null,
|
"link": null,
|
||||||
"locked": false
|
"locked": false
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
"id": "y-9Stf17pe9fWn0kSmWVL",
|
"id": "y-9Stf17pe9fWn0kSmWVL",
|
||||||
"type": "text",
|
"type": "text",
|
||||||
"x": 1430.1000003814697,
|
"x": 1530.1000003814697,
|
||||||
"y": 737.5,
|
"y": 737.5,
|
||||||
"width": 19.799999237060547,
|
"width": 19.799999237060547,
|
||||||
"height": 45,
|
"height": 45,
|
||||||
@@ -1578,11 +1578,11 @@
|
|||||||
"index": "b0cV",
|
"index": "b0cV",
|
||||||
"roundness": null,
|
"roundness": null,
|
||||||
"seed": 761306908,
|
"seed": 761306908,
|
||||||
"version": 3,
|
"version": 8,
|
||||||
"versionNonce": 579937436,
|
"versionNonce": 1035127708,
|
||||||
"isDeleted": false,
|
"isDeleted": false,
|
||||||
"boundElements": null,
|
"boundElements": null,
|
||||||
"updated": 1768867618828,
|
"updated": 1768903389485,
|
||||||
"link": null,
|
"link": null,
|
||||||
"locked": false,
|
"locked": false,
|
||||||
"text": "2",
|
"text": "2",
|
||||||
@@ -1598,7 +1598,7 @@
|
|||||||
{
|
{
|
||||||
"id": "Yg-CjxTPXE94lHk3dKGUd",
|
"id": "Yg-CjxTPXE94lHk3dKGUd",
|
||||||
"type": "rectangle",
|
"type": "rectangle",
|
||||||
"x": 1300,
|
"x": 1400,
|
||||||
"y": 720,
|
"y": 720,
|
||||||
"width": 80,
|
"width": 80,
|
||||||
"height": 80,
|
"height": 80,
|
||||||
@@ -1617,8 +1617,8 @@
|
|||||||
"type": 3
|
"type": 3
|
||||||
},
|
},
|
||||||
"seed": 483230628,
|
"seed": 483230628,
|
||||||
"version": 14,
|
"version": 19,
|
||||||
"versionNonce": 1058383268,
|
"versionNonce": 287193244,
|
||||||
"isDeleted": false,
|
"isDeleted": false,
|
||||||
"boundElements": [
|
"boundElements": [
|
||||||
{
|
{
|
||||||
@@ -1626,14 +1626,14 @@
|
|||||||
"id": "Nx15pnUHSCimdfJ5cArXf"
|
"id": "Nx15pnUHSCimdfJ5cArXf"
|
||||||
}
|
}
|
||||||
],
|
],
|
||||||
"updated": 1768867620980,
|
"updated": 1768903391770,
|
||||||
"link": null,
|
"link": null,
|
||||||
"locked": false
|
"locked": false
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
"id": "Nx15pnUHSCimdfJ5cArXf",
|
"id": "Nx15pnUHSCimdfJ5cArXf",
|
||||||
"type": "text",
|
"type": "text",
|
||||||
"x": 1330.1000003814697,
|
"x": 1430.1000003814697,
|
||||||
"y": 737.5,
|
"y": 737.5,
|
||||||
"width": 19.799999237060547,
|
"width": 19.799999237060547,
|
||||||
"height": 45,
|
"height": 45,
|
||||||
@@ -1650,11 +1650,11 @@
|
|||||||
"index": "b0dV",
|
"index": "b0dV",
|
||||||
"roundness": null,
|
"roundness": null,
|
||||||
"seed": 1757256220,
|
"seed": 1757256220,
|
||||||
"version": 3,
|
"version": 8,
|
||||||
"versionNonce": 137101212,
|
"versionNonce": 1652868380,
|
||||||
"isDeleted": false,
|
"isDeleted": false,
|
||||||
"boundElements": null,
|
"boundElements": null,
|
||||||
"updated": 1768867622323,
|
"updated": 1768903391770,
|
||||||
"link": null,
|
"link": null,
|
||||||
"locked": false,
|
"locked": false,
|
||||||
"text": "3",
|
"text": "3",
|
||||||
@@ -1689,16 +1689,16 @@
|
|||||||
"type": 3
|
"type": 3
|
||||||
},
|
},
|
||||||
"seed": 511833380,
|
"seed": 511833380,
|
||||||
"version": 93,
|
"version": 94,
|
||||||
"versionNonce": 76819364,
|
"versionNonce": 315212316,
|
||||||
"isDeleted": false,
|
"isDeleted": true,
|
||||||
"boundElements": [
|
"boundElements": [
|
||||||
{
|
{
|
||||||
"type": "text",
|
"type": "text",
|
||||||
"id": "m6RMkBWOX7Oe1Yb5XJQKL"
|
"id": "m6RMkBWOX7Oe1Yb5XJQKL"
|
||||||
}
|
}
|
||||||
],
|
],
|
||||||
"updated": 1768867581029,
|
"updated": 1768903387547,
|
||||||
"link": null,
|
"link": null,
|
||||||
"locked": false
|
"locked": false
|
||||||
},
|
},
|
||||||
@@ -1722,11 +1722,11 @@
|
|||||||
"index": "b0f",
|
"index": "b0f",
|
||||||
"roundness": null,
|
"roundness": null,
|
||||||
"seed": 1280290980,
|
"seed": 1280290980,
|
||||||
"version": 18,
|
"version": 19,
|
||||||
"versionNonce": 1339496228,
|
"versionNonce": 692059556,
|
||||||
"isDeleted": false,
|
"isDeleted": true,
|
||||||
"boundElements": [],
|
"boundElements": [],
|
||||||
"updated": 1768867581029,
|
"updated": 1768903387547,
|
||||||
"link": null,
|
"link": null,
|
||||||
"locked": false,
|
"locked": false,
|
||||||
"text": "2",
|
"text": "2",
|
||||||
@@ -1796,11 +1796,11 @@
|
|||||||
"type": 2
|
"type": 2
|
||||||
},
|
},
|
||||||
"seed": 1406049828,
|
"seed": 1406049828,
|
||||||
"version": 149,
|
"version": 150,
|
||||||
"versionNonce": 1677336092,
|
"versionNonce": 1672236188,
|
||||||
"isDeleted": false,
|
"isDeleted": true,
|
||||||
"boundElements": [],
|
"boundElements": [],
|
||||||
"updated": 1768867910921,
|
"updated": 1768903382929,
|
||||||
"link": null,
|
"link": null,
|
||||||
"locked": false,
|
"locked": false,
|
||||||
"points": [
|
"points": [
|
||||||
@@ -1913,11 +1913,11 @@
|
|||||||
"type": 2
|
"type": 2
|
||||||
},
|
},
|
||||||
"seed": 966452508,
|
"seed": 966452508,
|
||||||
"version": 140,
|
"version": 141,
|
||||||
"versionNonce": 1302865572,
|
"versionNonce": 1517442724,
|
||||||
"isDeleted": false,
|
"isDeleted": true,
|
||||||
"boundElements": null,
|
"boundElements": null,
|
||||||
"updated": 1768867963536,
|
"updated": 1768903385286,
|
||||||
"link": null,
|
"link": null,
|
||||||
"locked": false,
|
"locked": false,
|
||||||
"points": [
|
"points": [
|
||||||
@@ -1995,16 +1995,16 @@
|
|||||||
"type": 3
|
"type": 3
|
||||||
},
|
},
|
||||||
"seed": 441688228,
|
"seed": 441688228,
|
||||||
"version": 49,
|
"version": 50,
|
||||||
"versionNonce": 261033884,
|
"versionNonce": 1106456092,
|
||||||
"isDeleted": false,
|
"isDeleted": true,
|
||||||
"boundElements": [
|
"boundElements": [
|
||||||
{
|
{
|
||||||
"type": "text",
|
"type": "text",
|
||||||
"id": "CXeyVA3UWQkIqE8L_SeKy"
|
"id": "CXeyVA3UWQkIqE8L_SeKy"
|
||||||
}
|
}
|
||||||
],
|
],
|
||||||
"updated": 1768867720892,
|
"updated": 1768903394836,
|
||||||
"link": null,
|
"link": null,
|
||||||
"locked": false
|
"locked": false
|
||||||
},
|
},
|
||||||
@@ -2028,11 +2028,11 @@
|
|||||||
"index": "b0o",
|
"index": "b0o",
|
||||||
"roundness": null,
|
"roundness": null,
|
||||||
"seed": 1205857316,
|
"seed": 1205857316,
|
||||||
"version": 36,
|
"version": 37,
|
||||||
"versionNonce": 717405212,
|
"versionNonce": 1823691172,
|
||||||
"isDeleted": false,
|
"isDeleted": true,
|
||||||
"boundElements": [],
|
"boundElements": [],
|
||||||
"updated": 1768867720892,
|
"updated": 1768903394836,
|
||||||
"link": null,
|
"link": null,
|
||||||
"locked": false,
|
"locked": false,
|
||||||
"text": "2",
|
"text": "2",
|
||||||
@@ -2048,7 +2048,7 @@
|
|||||||
{
|
{
|
||||||
"id": "zjodJTNahFy_DgdrmZAkO",
|
"id": "zjodJTNahFy_DgdrmZAkO",
|
||||||
"type": "rectangle",
|
"type": "rectangle",
|
||||||
"x": 1400,
|
"x": 1520,
|
||||||
"y": 920,
|
"y": 920,
|
||||||
"width": 80,
|
"width": 80,
|
||||||
"height": 80,
|
"height": 80,
|
||||||
@@ -2067,8 +2067,8 @@
|
|||||||
"type": 3
|
"type": 3
|
||||||
},
|
},
|
||||||
"seed": 618055588,
|
"seed": 618055588,
|
||||||
"version": 47,
|
"version": 53,
|
||||||
"versionNonce": 273105180,
|
"versionNonce": 1123443740,
|
||||||
"isDeleted": false,
|
"isDeleted": false,
|
||||||
"boundElements": [
|
"boundElements": [
|
||||||
{
|
{
|
||||||
@@ -2076,14 +2076,14 @@
|
|||||||
"id": "phHSsWqMJl40hT-lEiI8k"
|
"id": "phHSsWqMJl40hT-lEiI8k"
|
||||||
}
|
}
|
||||||
],
|
],
|
||||||
"updated": 1768867718993,
|
"updated": 1768903396886,
|
||||||
"link": null,
|
"link": null,
|
||||||
"locked": false
|
"locked": false
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
"id": "phHSsWqMJl40hT-lEiI8k",
|
"id": "phHSsWqMJl40hT-lEiI8k",
|
||||||
"type": "text",
|
"type": "text",
|
||||||
"x": 1430.1000003814697,
|
"x": 1550.1000003814697,
|
||||||
"y": 937.5,
|
"y": 937.5,
|
||||||
"width": 19.799999237060547,
|
"width": 19.799999237060547,
|
||||||
"height": 45,
|
"height": 45,
|
||||||
@@ -2100,11 +2100,11 @@
|
|||||||
"index": "b0q",
|
"index": "b0q",
|
||||||
"roundness": null,
|
"roundness": null,
|
||||||
"seed": 90583844,
|
"seed": 90583844,
|
||||||
"version": 36,
|
"version": 42,
|
||||||
"versionNonce": 410566044,
|
"versionNonce": 256606364,
|
||||||
"isDeleted": false,
|
"isDeleted": false,
|
||||||
"boundElements": [],
|
"boundElements": [],
|
||||||
"updated": 1768867718993,
|
"updated": 1768903396886,
|
||||||
"link": null,
|
"link": null,
|
||||||
"locked": false,
|
"locked": false,
|
||||||
"text": "3",
|
"text": "3",
|
||||||
@@ -2207,7 +2207,7 @@
|
|||||||
{
|
{
|
||||||
"id": "hlPVtk_Zvb9ax1XWhuVNm",
|
"id": "hlPVtk_Zvb9ax1XWhuVNm",
|
||||||
"type": "rectangle",
|
"type": "rectangle",
|
||||||
"x": 1300,
|
"x": 1420,
|
||||||
"y": 920,
|
"y": 920,
|
||||||
"width": 80,
|
"width": 80,
|
||||||
"height": 80,
|
"height": 80,
|
||||||
@@ -2226,8 +2226,8 @@
|
|||||||
"type": 3
|
"type": 3
|
||||||
},
|
},
|
||||||
"seed": 662725404,
|
"seed": 662725404,
|
||||||
"version": 54,
|
"version": 64,
|
||||||
"versionNonce": 1945111708,
|
"versionNonce": 2065799836,
|
||||||
"isDeleted": false,
|
"isDeleted": false,
|
||||||
"boundElements": [
|
"boundElements": [
|
||||||
{
|
{
|
||||||
@@ -2235,14 +2235,14 @@
|
|||||||
"id": "DkDXjRsX0WzuKE7k0n4_C"
|
"id": "DkDXjRsX0WzuKE7k0n4_C"
|
||||||
}
|
}
|
||||||
],
|
],
|
||||||
"updated": 1768867831673,
|
"updated": 1768903401020,
|
||||||
"link": null,
|
"link": null,
|
||||||
"locked": false
|
"locked": false
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
"id": "DkDXjRsX0WzuKE7k0n4_C",
|
"id": "DkDXjRsX0WzuKE7k0n4_C",
|
||||||
"type": "text",
|
"type": "text",
|
||||||
"x": 1330.1000003814697,
|
"x": 1450.1000003814697,
|
||||||
"y": 937.5,
|
"y": 937.5,
|
||||||
"width": 19.799999237060547,
|
"width": 19.799999237060547,
|
||||||
"height": 45,
|
"height": 45,
|
||||||
@@ -2259,11 +2259,11 @@
|
|||||||
"index": "b0u",
|
"index": "b0u",
|
||||||
"roundness": null,
|
"roundness": null,
|
||||||
"seed": 1883086748,
|
"seed": 1883086748,
|
||||||
"version": 44,
|
"version": 54,
|
||||||
"versionNonce": 2036784796,
|
"versionNonce": 969664284,
|
||||||
"isDeleted": false,
|
"isDeleted": false,
|
||||||
"boundElements": [],
|
"boundElements": [],
|
||||||
"updated": 1768867834133,
|
"updated": 1768903401020,
|
||||||
"link": null,
|
"link": null,
|
||||||
"locked": false,
|
"locked": false,
|
||||||
"text": "4",
|
"text": "4",
|
||||||
@@ -2275,6 +2275,58 @@
|
|||||||
"originalText": "4",
|
"originalText": "4",
|
||||||
"autoResize": true,
|
"autoResize": true,
|
||||||
"lineHeight": 1.25
|
"lineHeight": 1.25
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"id": "IUHJRD7drxv1P2qzgkr9c",
|
||||||
|
"type": "arrow",
|
||||||
|
"x": 1469.29567331078,
|
||||||
|
"y": 391.89155029829396,
|
||||||
|
"width": 150.7043266892199,
|
||||||
|
"height": 28.108449701706036,
|
||||||
|
"angle": 0,
|
||||||
|
"strokeColor": "#1e1e1e",
|
||||||
|
"backgroundColor": "transparent",
|
||||||
|
"fillStyle": "hachure",
|
||||||
|
"strokeWidth": 2,
|
||||||
|
"strokeStyle": "solid",
|
||||||
|
"roughness": 1,
|
||||||
|
"opacity": 90,
|
||||||
|
"groupIds": [],
|
||||||
|
"frameId": null,
|
||||||
|
"index": "b0v",
|
||||||
|
"roundness": {
|
||||||
|
"type": 2
|
||||||
|
},
|
||||||
|
"seed": 181702948,
|
||||||
|
"version": 67,
|
||||||
|
"versionNonce": 396271132,
|
||||||
|
"isDeleted": true,
|
||||||
|
"boundElements": null,
|
||||||
|
"updated": 1768903373255,
|
||||||
|
"link": null,
|
||||||
|
"locked": false,
|
||||||
|
"points": [
|
||||||
|
[
|
||||||
|
0,
|
||||||
|
0
|
||||||
|
],
|
||||||
|
[
|
||||||
|
150.7043266892199,
|
||||||
|
28.108449701706036
|
||||||
|
]
|
||||||
|
],
|
||||||
|
"startBinding": {
|
||||||
|
"elementId": "Ny8zM8hZc1_aIC5xBaIFI",
|
||||||
|
"mode": "orbit",
|
||||||
|
"fixedPoint": [
|
||||||
|
0.8487681898891537,
|
||||||
|
0.8487681898891537
|
||||||
|
]
|
||||||
|
},
|
||||||
|
"endBinding": null,
|
||||||
|
"startArrowhead": null,
|
||||||
|
"endArrowhead": "arrow",
|
||||||
|
"elbowed": false
|
||||||
}
|
}
|
||||||
],
|
],
|
||||||
"appState": {
|
"appState": {
|
||||||
|
|||||||
Binary file not shown.
|
Before Width: | Height: | Size: 419 KiB After Width: | Height: | Size: 163 KiB |
161
main.typ
161
main.typ
@@ -1,5 +1,7 @@
|
|||||||
#import "@preview/ilm:1.4.2": *
|
#import "@preview/ilm:1.4.2": *
|
||||||
|
|
||||||
|
#let link-text(body) = text(blue, body)
|
||||||
|
|
||||||
#set text(lang: "de")
|
#set text(lang: "de")
|
||||||
|
|
||||||
#show: ilm.with(
|
#show: ilm.with(
|
||||||
@@ -9,34 +11,34 @@
|
|||||||
date-format: "[day padding:zero].[month repr:short].[year repr:full]",
|
date-format: "[day padding:zero].[month repr:short].[year repr:full]",
|
||||||
raw-text: (use-typst-defaults: true),
|
raw-text: (use-typst-defaults: true),
|
||||||
bibliography: bibliography("refs.bib"),
|
bibliography: bibliography("refs.bib"),
|
||||||
figure-index: (enabled: true, title: "Bilderverzeichnis"),
|
preface: [
|
||||||
|
Der Quelltext dieser Arbeit sowie Beispielcode und das vollständige Quellenverzeichnis sind unter #link-text([https://git.veltko.de/Weckyy702/uc-ausarbeitung-linux-treiber]) mit der GPL lizensiert aufzufinden.
|
||||||
|
]
|
||||||
)
|
)
|
||||||
|
|
||||||
#let link-text(body) = text(blue, body)
|
|
||||||
|
|
||||||
#counter(page).update(1)
|
#counter(page).update(1)
|
||||||
|
|
||||||
= Einleitung
|
= Einleitung
|
||||||
Damit Computersysteme mit der Umwelt interagieren können, muss mit externen Sensoren und Aktoren kommuniziert werden.
|
Damit Computersysteme mit ihrer Umwelt interagieren können, ist die Kommunikation mit externen Sensoren und Aktoren erforderlich.
|
||||||
Eine der Aufgaben eines Betriebssystems ist es, gemeinsame Schnittstellen für verschiedene Geräte darzustellen; Unter Linux werden dafür sogenannte _device files_ verwendet, so dass über klassische Dateioperationen auf diese Geräte zugegriffen werden kann.
|
Eine der Aufgaben eines Betriebssystems besteht darin, gemeinsame Schnittstellen für verschiedene Geräte bereitzustellen@os-tasks. Unter Linux werden hierfür sogenannte _device files_@device-files verwendet, die den Zugriff auf diese Geräte über klassische Dateioperationen ermöglichen.
|
||||||
|
|
||||||
== Gerätezugriff per Dateisystem
|
== Gerätezugriff per Dateisystem
|
||||||
|
|
||||||
Nach der UNIX-Philosophie #quote("Everything is a file") melden Gerätetreiber spezielle Dateien im virtuellen Dateisystem an (in der Regel im Verzeichnis `/dev` oder `/sys`).
|
Nach der UNIX-Philosophie #quote("Everything is a file")@everythings-a-file melden Gerätetreiber spezielle Dateien im virtuellen Dateisystem an (in der Regel im Verzeichnis `/dev` oder `/sys`).
|
||||||
Wird auf dieser Datei zum Beispiel `write()` aufgerufen, so wird mit den geschriebenen Daten eine Funktion im Kerneltreiber aufgerufen, der sie dann an das physische Gerät weitergibt.
|
Wird auf einer solchen Datei ein Systemaufruf wie `write()` ausgeführt, so wird eine Funktion im Kerneltreiber aufgerufen, die die 'geschriebenen' Daten an das physische Gerät weiterleitet.
|
||||||
|
|
||||||
=== Device-Dateien
|
=== Device-Dateien
|
||||||
|
|
||||||
Folgender Beispielcode zeigt die Kommunikation mit einem BME280-Sensor mithilfe des Userspace I²C-Treibers auf einem Raspberry Pi:
|
Folgender Beispielcode@i2c-example zeigt die Kommunikation mit einem BME280-Sensor mithilfe des Userspace I²C-Treibers auf einem Raspberry Pi:
|
||||||
```c
|
```c
|
||||||
int main() {
|
int main() {
|
||||||
// Öffne die Device-Datei
|
// Öffne die Device-Datei
|
||||||
int driver = open("/dev/i2c-1"); // (1)
|
int driver = open("/dev/i2c-1"); // (1)
|
||||||
|
|
||||||
// Setze die Slave-Addresse, die für die nachfolgenden Transaktionen verwendet wird
|
// Setze die Slave-Adresse für nachfolgende Transaktionen
|
||||||
ioctl(driver, I2C_SLAVE, 0x76); // (2)
|
ioctl(driver, I2C_SLAVE, 0x76); // (2)
|
||||||
|
|
||||||
// Schreibe die Addresse für das ID-Register
|
// Schreibe die Adresse für das ID-Register
|
||||||
uint8_t const write_buf[] = {0xd0};
|
uint8_t const write_buf[] = {0xd0};
|
||||||
write(driver, write_buf, sizeof(write_buf)); // (3)
|
write(driver, write_buf, sizeof(write_buf)); // (3)
|
||||||
|
|
||||||
@@ -49,17 +51,19 @@ int main() {
|
|||||||
```
|
```
|
||||||
|
|
||||||
Der Beispielcode zeigt die vier typischen Datei-Operationen bei der Arbeit mit Device-Dateien:
|
Der Beispielcode zeigt die vier typischen Datei-Operationen bei der Arbeit mit Device-Dateien:
|
||||||
1. Wie jede Datei muss auch die Device-Datei geöffnet werden. Der Treiber setzt die notwendigen Buchhaltungsstrukturen für eine weitere Anwendung auf.
|
1. Wie jede andere Datei muss die Device-Datei geöffnet werden. Der Treiber richtet dabei die notwendigen Verwaltungsstrukturen für die weitere Nutzung durch die Anwendung ein.
|
||||||
2. Der `ioctl`-Syscall wird verwendet, um Treibereinstellungen zu ändern oder Operationen auszuführen, die nicht mit `read` oder `write` dargestellt werden können. Die Flags und Parameter für `ioctl` sind treiberabhängig.
|
2. Der `ioctl`-Systemaufruf dient dazu, Treibereinstellungen zu ändern oder Operationen auszuführen, die nicht über `read` oder `write` abgebildet werden können. Die Flags und Parameter für `ioctl` sind treiberabhängig.
|
||||||
3. Der `write`-Syscall sendet eine schreibende Transaktion auf den I²C-Bus. In der Regel wird `write` verwendet, um Daten auf Busse zu schreiben oder Ausgänge zu schalten.
|
3. Der `write`-Systemaufruf sendet eine schreibende Transaktion auf den I²C-Bus. In der Regel wird `write` verwendet, um Daten auf Busse zu schreiben oder Ausgänge zu schalten.
|
||||||
4. `read` führt eine lesende Transaktion auf dem I²C-Bus aus. `read` wird typischerweise verwendet, um Gerätedaten auszulesen oder von Bussen zu empfangen.
|
4. `read` führt eine lesende Transaktion auf dem I²C-Bus aus. `read` wird typischerweise verwendet, um Gerätedaten auszulesen oder von Bussen zu empfangen.
|
||||||
|
|
||||||
|
Typischerweise stellt der Kernel eine Begleitbibliothek wie `libi2c` für I²C-Operationen bereit, um versionsabhängige Unterschiede zu abstrahieren. Diese Bibliotheken werden hier nicht näher beschrieben, stellen jedoch die empfohlene Schnittstelle dar.
|
||||||
|
|
||||||
=== Zugriff über Sysfs
|
=== Zugriff über Sysfs
|
||||||
|
|
||||||
Einige Gerätetreiber registrieren keine Dateien in `/dev`, sondern werden über Dateien im virtuellen Dateisystem unter `/sys` kontrolliert.
|
Einige Gerätetreiber registrieren keine Dateien in `/dev`, sondern werden über Dateien im virtuellen Dateisystem unter `/sys` kontrolliert.
|
||||||
Die Konvention dafür ist, dass I/O-Geräte typsicherweise in `/dev` registriert werden, während andere Geräte über `/sys` konfiguriert werden. Außerdem wird `/sys` verwendet um Geräte zu finden.
|
Die Konvention dafür ist, dass für Eingabe-/Ausgabe-Operationen mit Geräten die Dateien in `/dev` verwendet werden, während `/sys` für strukturierte Zugriffe und Konfiguration verwendet wird@devfs-vs-sysfs.
|
||||||
|
|
||||||
Geräte-Dateien in `/sys` haben eine String-basierte Schnittstelle, es werden also Menschenlesbare Werte in verschiedenen Dateien geschrieben. Das macht die Interaktion mit `/sys`-Dateien in der Shell attraktiv.
|
Geräte-Dateien in `/sys` haben eine String-basierte Schnittstelle, es werden also menschenlesbare Werte in verschiedenen Dateien geschrieben. Das macht die Interaktion mit `/sys`-Dateien in der Shell attraktiv.
|
||||||
|
|
||||||
Folgender Shell-Code liest die momentane Batteriespannung meines Laptops aus.
|
Folgender Shell-Code liest die momentane Batteriespannung meines Laptops aus.
|
||||||
```sh
|
```sh
|
||||||
@@ -83,7 +87,7 @@ Wie in der Einleitung beschrieben stellt der I²C-Treiber device-Dateien unter `
|
|||||||
- Implementiert in #link("https://github.com/torvalds/linux/blob/master/drivers/i2c/i2c-dev.c", link-text[`drivers/i2c/i2c-dev.c`])
|
- Implementiert in #link("https://github.com/torvalds/linux/blob/master/drivers/i2c/i2c-dev.c", link-text[`drivers/i2c/i2c-dev.c`])
|
||||||
- #link("https://www.kernel.org/doc/html/latest/i2c/dev-interface.html", link-text[Offizielle Dokumentation])
|
- #link("https://www.kernel.org/doc/html/latest/i2c/dev-interface.html", link-text[Offizielle Dokumentation])
|
||||||
|
|
||||||
Implementierte Syscalls:
|
Implementierte Systemaufrufe:
|
||||||
|
|
||||||
#figure(
|
#figure(
|
||||||
table(
|
table(
|
||||||
@@ -107,7 +111,7 @@ Der GPIO-Treiber stellt zwei Schnittstellen bereit, eine unter `/dev` und eine v
|
|||||||
- Implementiert in #link("https://github.com/torvalds/linux/blob/master/drivers/gpio/gpiolib-cdev.c", link-text(`drivers/gpio/gpiolib-cdev.c`));
|
- Implementiert in #link("https://github.com/torvalds/linux/blob/master/drivers/gpio/gpiolib-cdev.c", link-text(`drivers/gpio/gpiolib-cdev.c`));
|
||||||
- #link("https://www.kernel.org/doc/html/latest/userspace-api/gpio/chardev.html", link-text([Offizielle Dokumentation])).
|
- #link("https://www.kernel.org/doc/html/latest/userspace-api/gpio/chardev.html", link-text([Offizielle Dokumentation])).
|
||||||
|
|
||||||
Implementierte Syscalls:
|
Implementierte Systemaufrufe:
|
||||||
|
|
||||||
#figure(
|
#figure(
|
||||||
table(
|
table(
|
||||||
@@ -117,7 +121,7 @@ Implementierte Syscalls:
|
|||||||
[`ioctl(<file>, GPIO_GET_CHIPINFO_IOCTL, <chip_info>)`], [Informationen über einen Gpio-Chip holen],
|
[`ioctl(<file>, GPIO_GET_CHIPINFO_IOCTL, <chip_info>)`], [Informationen über einen Gpio-Chip holen],
|
||||||
[`ioctl(<file>, GPIO_GET_LINEINFO_UNWATCH_IOCTL , <line_offset>)`], [Stoppt das Beobachten eines GPIO-Pins],
|
[`ioctl(<file>, GPIO_GET_LINEINFO_UNWATCH_IOCTL , <line_offset>)`], [Stoppt das Beobachten eines GPIO-Pins],
|
||||||
[`ioctl(<file>, GPIO_V2_GET_LINEINFO_IOCTL, <line_info>)`], [Beschafft Informationen über einen spezifischen GPIO-Pin],
|
[`ioctl(<file>, GPIO_V2_GET_LINEINFO_IOCTL, <line_info>)`], [Beschafft Informationen über einen spezifischen GPIO-Pin],
|
||||||
[`ioctl(<file>, GPIO_V2_GET_LINEINFO_WATCH_IOCTL, <line_info>)`], [Beschafft Informationen über einen GPIO-Pin und],
|
[`ioctl(<file>, GPIO_V2_GET_LINEINFO_WATCH_IOCTL, <line_info>)`], [Beschafft Informationen über einen GPIO-Pin und macht nachfolgende Änderungen über `read` verfügbar],
|
||||||
[`ioctl(<file>, GPIO_V2_GET_LINE_IOCTL, <line_request>)`], [Reserviert und konfiguriert einen GPIO-Pin für das aufrufende Programm],
|
[`ioctl(<file>, GPIO_V2_GET_LINE_IOCTL, <line_request>)`], [Reserviert und konfiguriert einen GPIO-Pin für das aufrufende Programm],
|
||||||
[`ioctl(<file>, GPIO_V2_LINE_SET_CONFIG_IOCTL, <line_config>)`], [Setzt Attribute für einen Pin, zum Beispiel Input/Output oder active LOW/HIGH],
|
[`ioctl(<file>, GPIO_V2_LINE_SET_CONFIG_IOCTL, <line_config>)`], [Setzt Attribute für einen Pin, zum Beispiel Input/Output oder active LOW/HIGH],
|
||||||
[`ioctl(<file>, GPIO_V2_LINE_GET_VALUES_IOCTL, <line_values>)`], [Liest Werte von mehreren Eingangs-Pins],
|
[`ioctl(<file>, GPIO_V2_LINE_GET_VALUES_IOCTL, <line_values>)`], [Liest Werte von mehreren Eingangs-Pins],
|
||||||
@@ -129,17 +133,16 @@ Implementierte Syscalls:
|
|||||||
|
|
||||||
== ADC
|
== ADC
|
||||||
|
|
||||||
ADCs werden in Linux nicht direkt als eigene Geräteklasse verwaltet, sondern sind in der Regel als _Hardware Monitoring_ (Überwachung) oder _Industrial I/O_ (iio).
|
ADCs werden in Linux nicht direkt als eigene Geräteklasse verwaltet, sondern sind in der Regel als _Hardware Monitoring_ (Überwachung) oder _Industrial I/O_ (iio) gelistet.
|
||||||
|
|
||||||
Als Beispiel wird hier der Kernel-eigene Treiber für den #link("https://www.kernel.org/doc/html/v6.12/iio/ep93xx_adc.html", link-text[ADC des Cirrus Logic EP93xx SoC]) genutzt.
|
|
||||||
Hier wird für jeden der ADC-Pins ein eigener Eintrag unter `/sys/bus/iio/devices/iio:device<N>/` angelegt, wobei $N$ die Geräte-ID ist:
|
|
||||||
|
|
||||||
|
Als Beispiel wird hier der Kernel-eigene Treiber für den ADC des Cirrus Logic EP93xx SoC@adc-driver genutzt.
|
||||||
|
Dabei wird für jeden der ADC-Pins ein eigener Eintrag unter `/sys/bus/iio/devices/iio:device<N>/` angelegt, wobei $N$ die Geräte-ID ist:
|
||||||
|
|
||||||
#figure(
|
#figure(
|
||||||
table(
|
table(
|
||||||
columns: (auto, 1fr),
|
columns: (auto, 1fr),
|
||||||
align: horizon,
|
align: horizon,
|
||||||
table.header([Sysfs-Eintrag], [Pin-Name]),
|
table.header([Sysfs-Eintrag], [Name des gesampleten Pins]),
|
||||||
[in_voltage0_raw], [`Y-`],
|
[in_voltage0_raw], [`Y-`],
|
||||||
[in_voltage1_raw], [`sX+`],
|
[in_voltage1_raw], [`sX+`],
|
||||||
[in_voltage2_raw], [`sX-`],
|
[in_voltage2_raw], [`sX-`],
|
||||||
@@ -152,15 +155,109 @@ Hier wird für jeden der ADC-Pins ein eigener Eintrag unter `/sys/bus/iio/device
|
|||||||
caption: [Sysfs-Einträge des ADC-Treibers]
|
caption: [Sysfs-Einträge des ADC-Treibers]
|
||||||
)<tab-adc-syscalls>
|
)<tab-adc-syscalls>
|
||||||
|
|
||||||
Das Auslesen einer dieser Datein startet führt synchron eine ADC-Umwandlung durch und gibt den ganzzahligen µV-Wert als String aus.
|
Das Auslesen einer dieser Datein führt synchron eine ADC-Umwandlung durch.
|
||||||
|
|
||||||
|
Aus der Dokumentation anderer ADC-Treiber@adc-microchip geht hervor, dass der `in_voltageX_raw`-Wert der unskalierte Bitwert des ADC ist. Die Datei `/sys/[...]/in_voltage_scale` beinhaltet den Umrechnungswert vom Rohwert zu Millivolt. Manche Treiber stellen zusätzlich die Datei `/sys/[...]/in_voltage_offset` bereit, die einen konstanten Fehlerwert enthält. Die vollständige Umrechnung ist dann:
|
||||||
|
|
||||||
|
$U_["mV"] = ("voltage_raw" dot "voltage_scale") + "voltage_offset"$
|
||||||
|
|
||||||
= Design einer Hardwareschnittstelle für AT91SAM7-Timer
|
= Design einer Hardwareschnittstelle für AT91SAM7-Timer
|
||||||
|
|
||||||
Der AT91SAM7-Mikrocontroller stellt das _Timer Counter_ Peripheral bereit; Drei 16-bit Zähler
|
Der AT91SAM7-Mikrocontroller@sam7s-datasheet stellt das _Timer Counter Peripheral_ bereit;
|
||||||
|
Drei unabhängige 16-bit Zähler, Kanäle genannt, mit einstellbaren Taktgeschwindigkeiten, Überlaufgrenzen und _Triggern_.
|
||||||
|
|
||||||
== Features
|
== Features
|
||||||
|
|
||||||
TODO
|
Jeder Kanal kann sich in einem der folgenden Modi befinden:
|
||||||
|
- _Capture_ zum Festhalten von Zeitpunkten, zu denen Eingänge geschaltet wurden
|
||||||
|
- _Waveform_ zum Erzeugen von einstellbaren Rechtecksignalen
|
||||||
|
|
||||||
|
Außerdem hat jeder Kanal drei Eingangssignale `XC0-2`, zwei Ausgangssignale `A/B` und kann einen von fünf Vorteilern wählen.
|
||||||
|
|
||||||
|
=== Capture-Modus
|
||||||
|
|
||||||
|
Im _Capture_-Modus zählt der Zähler kontinuierlich und es wir bei einem konfigurierbaren _Event_ (eine Flanke auf `TIOA` oder `TIOB`) der Zählerstand in eins der Register geschrieben.
|
||||||
|
|
||||||
|
Dieser Modus ist unter anderem für die Bestimmung von Frequenz, Pulszeit und Pahsenbestimmung eins oder mehrerer anliegender Signale gedacht.
|
||||||
|
|
||||||
|
=== Waveform-Modus
|
||||||
|
|
||||||
|
Dieser Modus ist für die Erzeugung von Rechtecksignalen gedacht. Es gibt vier Untermodi:
|
||||||
|
|
||||||
|
#figure(
|
||||||
|
table(
|
||||||
|
columns: (auto, auto, 1fr),
|
||||||
|
align: horizon,
|
||||||
|
table.header([Modus], [Zählrichtung], [Verhalten wenn $="RC"$]),
|
||||||
|
[`00`], [Hoch], [Nichts, nur durch Überlauf zurückgesetzt],
|
||||||
|
[`10`], [Hoch], [Zurücksetzen auf 0],
|
||||||
|
[`01`], [Hoch, dann Runter], [Nichts, Richtungswechsel wenn $=0$ oder $="0xFFFF"$],
|
||||||
|
[`11`], [Hoch, dann Runter], [Richtungswechsel],
|
||||||
|
),
|
||||||
|
caption: [Wellenmodi im Waveform-Modus]
|
||||||
|
)
|
||||||
|
|
||||||
|
Außerdem wird der Zählerwert immer mit den Werten in den Registern `RA/RB/RC` auf Gleichheit verglichen.
|
||||||
|
Die daraus entstehenden Trigger-Signale können dann die Ausganspins `A/B` jeweils entweder einschalten, ausschalten oder umschalten.
|
||||||
|
|
||||||
|
== Umsetzung
|
||||||
|
|
||||||
|
Die API ist an der Struktur der GPIO-API orientiert.
|
||||||
|
|
||||||
|
Jeder Kanal muss mit `REQ_CHANNEL` vom Kernel angefragt werden, damit ein Kanal von genau einem Prozess verwaltet wird.
|
||||||
|
Mithilfe der `SET_MODE_CAPTURE` und `SET_MODE_WAVE` `ioctl`s wird der Kanal in den jeweiligen Modus versetzt und konfiguriert.
|
||||||
|
Der `TIMER_START`-Befehl startet einen einzelnen Kanal.
|
||||||
|
Wenn der aufrufende Prozess alle Kanäle kontrolliert, kann `TIMER_START` auf dem Timer selbst aufgerufen werden, was das SYNC-Signal für alle Kanäle setzt.
|
||||||
|
|
||||||
|
Folgend eine Beispielanwendung:
|
||||||
|
```c
|
||||||
|
int main() {
|
||||||
|
int timer_fd = open("/dev/timer0");
|
||||||
|
|
||||||
|
int ch0 = ioctl(timer_fd, REQ_CHANNEL_IOCTL, 0);
|
||||||
|
int some_free_channel = ioctl(timer_fd, REQ_CHANNEL_IOCTL, -1);
|
||||||
|
|
||||||
|
struct capture_config capture_config = {
|
||||||
|
.clock = CLOCK_1, // = TIMER_CLOCK1
|
||||||
|
.clock_burst = CLOCK_BURST_NONE, // Oder CLOCK_BURST_TIOA0/1/2
|
||||||
|
.clock_invert = false,
|
||||||
|
.a_edge = EDGE_RISING,
|
||||||
|
.b_edge = EDGE_NONE,
|
||||||
|
.external_trigger = EXT_TRIGGER_A,
|
||||||
|
.interrupt_on = INT_LDRA | INT_LDRB | INT_OVF, // Aktivierte interrupts
|
||||||
|
.compare = -1, //Deaktiviert CPCTRG, >0 aktiviert CPCTRG
|
||||||
|
};
|
||||||
|
|
||||||
|
ioctl(ch0, SET_MODE_CAPTURE, &capture_config);
|
||||||
|
|
||||||
|
struct wave_config wave_config = {
|
||||||
|
.clock = CLOCK_TIOA2, //-EINVAL wenn nicht verfügbar
|
||||||
|
.clock_invert = true,
|
||||||
|
.wave_mode = WAVE_MODE_UP_RC_TRIGGER, // WAVSEL = 10
|
||||||
|
.ra = 100,
|
||||||
|
.rb = 0x4000,
|
||||||
|
.rc = 0x9fff,
|
||||||
|
.tioa = (struct mtio) {
|
||||||
|
.a_mode = MTIO_MODE_SET,
|
||||||
|
.b_mode = MTIO_MODE_CLEAR,
|
||||||
|
.c_mode = MTIO_MODE_TOGGLE,
|
||||||
|
.sw_mode = MTIO_MODE_NONE,
|
||||||
|
}
|
||||||
|
.tiob = (struct mtio) {0}, // TIOB ist deaktiviert
|
||||||
|
};
|
||||||
|
ioctl(some_free_channel, SET_MODE_WAVE, &wave_config);
|
||||||
|
|
||||||
|
//Würde mit dem SYNC-Signal alle Kanäle starten,
|
||||||
|
//allerdings hat dieser Prozess nicht alle Kanäle angefragt.
|
||||||
|
//Der Aufruf würde also fehlschlagen
|
||||||
|
//ioctl(timer_fd, TIMER_START);
|
||||||
|
|
||||||
|
ioctl(ch0, TIMER_START); //Setzt SWTRG
|
||||||
|
struct capture_event capture_event;
|
||||||
|
// Blockiert bis mindestens eins der Signale in interrupt_on ausgelöst wurde
|
||||||
|
read(ch0, &capture_event, sizeof(capture_event));
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
= Scheduling bei geteilten Bussystemen
|
= Scheduling bei geteilten Bussystemen
|
||||||
|
|
||||||
@@ -181,20 +278,20 @@ Zudem sollen in regelmäßigen Abständen Temperatur und Luftfeuchtigkeit vom Se
|
|||||||
|
|
||||||
Wie in @fig-i2c-starvation gezeigt, wird durch die häufigen Display-Übertragungen der Temperatur-Sensor "ausgehungert" (schraffierter Hintergrund) und kann seine Daten nicht rechtzeitig übertragen.
|
Wie in @fig-i2c-starvation gezeigt, wird durch die häufigen Display-Übertragungen der Temperatur-Sensor "ausgehungert" (schraffierter Hintergrund) und kann seine Daten nicht rechtzeitig übertragen.
|
||||||
|
|
||||||
Bei geteilten Ressourcen wie Bussen tritt dieses Problem häufig auf, weswegen im nächsten Schritt ein typsicher Lösungsansatz besprochen wird.
|
Dieses Problem gehört zur Klasse der _Scheduling_-Aufgaben. Ein klassischer Lösungsansatz wird im nächsten Abschnitt besprochen
|
||||||
|
|
||||||
== Lösungsansatz
|
== Lösungsansatz
|
||||||
|
|
||||||
Da hier eine geteilte Ressource (der Bus) _fair_ zwischen mehreren Clients (den Treibern) verteilt werden soll, bietet sich ein #link("https://de.wikipedia.org/wiki/Prozess-Scheduler", link-text([Scheduling Verfahren])) an.
|
Da hier eine geteilte Ressource (der Bus) *fair* zwischen mehreren Clients (den Treibern) verteilt werden soll, bietet sich ein _Scheduling_-Verfahren@wiki-scheduling an.
|
||||||
|
|
||||||
Fragt ein Client einen I²C-Transfer an, so wird er nicht direkt ausgeführt, sondern mit anderen ausstehenden Anfragen in einer Warteschlange (Queue) gespeichert.
|
Fragt ein Client einen I²C-Transfer an, so wird er nicht direkt ausgeführt, sondern mit anderen ausstehenden Anfragen in einer _Queue_ (dt. Warteschlange)@wiki-queue gespeichert.
|
||||||
Nun kann der I²C-Scheduler die nächste anstehende Transaktion nach einem Scheduling-Verfahren wie dem Completely Fair Scheduler@wiki-cfs aussuchen und durchführen, um Aushungern zu vermeiden.
|
Nun kann der I²C-Scheduler die nächste anstehende Transaktion nach einem Scheduling-Verfahren wie dem _Completely Fair Scheduler_@wiki-cfs aussuchen und durchführen, um Aushungern zu vermeiden.
|
||||||
|
|
||||||
Nachfolgend ist der Ablauf mit dem simplen Round-Robin-Verfahren@wiki-round-robin gezeigt:
|
|
||||||
|
|
||||||
|
Nachfolgend ist der Ablauf mit dem simplen _Round-Robin-Verfahren_@wiki-round-robin gezeigt, das *keine* Fairness garantiert:
|
||||||
|
|
||||||
#figure(
|
#figure(
|
||||||
image("./i2c-scheduler-rr.excalidraw.png"),
|
image("./i2c-scheduler-rr.excalidraw.png"),
|
||||||
caption: [I²C-Scheduling mit Round Robin],
|
caption: [I²C-Scheduling mit Round Robin],
|
||||||
alt: "A vertical scheduling diagram showing round robin scheduling",
|
alt: "A vertical scheduling diagram showing round robin scheduling",
|
||||||
)<fig-i2c-round-robin>
|
)<fig-i2c-round-robin>
|
||||||
|
|
||||||
|
|||||||
87
refs.bib
87
refs.bib
@@ -8,7 +8,7 @@
|
|||||||
}
|
}
|
||||||
|
|
||||||
@misc{wiki-round-robin,
|
@misc{wiki-round-robin,
|
||||||
author = {Wikipedia contributors},
|
author = {wikipedia contributors},
|
||||||
title = {Round Robin (Informatik)},
|
title = {Round Robin (Informatik)},
|
||||||
howpublished = {\url{https://de.wikipedia.org/w/index.php?title=Round_Robin_(Informatik)&oldid=249025330}},
|
howpublished = {\url{https://de.wikipedia.org/w/index.php?title=Round_Robin_(Informatik)&oldid=249025330}},
|
||||||
year = {2024},
|
year = {2024},
|
||||||
@@ -17,10 +17,93 @@
|
|||||||
}
|
}
|
||||||
|
|
||||||
@misc{wiki-cfs,
|
@misc{wiki-cfs,
|
||||||
author = {Wikipedia contributors},
|
author = {wikipedia contributors},
|
||||||
title = {Completely Fair Scheduler},
|
title = {Completely Fair Scheduler},
|
||||||
howpublished = {\url{https://en.wikipedia.org/w/index.php?title=Completely_Fair_Scheduler&oldid=1329198135}},
|
howpublished = {\url{https://en.wikipedia.org/w/index.php?title=Completely_Fair_Scheduler&oldid=1329198135}},
|
||||||
year = {2025},
|
year = {2025},
|
||||||
month = {12},
|
month = {12},
|
||||||
note = {Zuletzt aufgerufen: 2026-01-20},
|
note = {Zuletzt aufgerufen: 2026-01-20},
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@misc{wiki-scheduling,
|
||||||
|
author = {wikipedia contributors},
|
||||||
|
title = {Prozess-Scheduler},
|
||||||
|
howpublished = {\url{https://de.wikipedia.org/w/index.php?title=Prozess-Scheduler&oldid=251680761}},
|
||||||
|
year = {2024},
|
||||||
|
month = {12},
|
||||||
|
note = {Zuletzt aufgerufen: 2026-01-20},
|
||||||
|
}
|
||||||
|
|
||||||
|
@misc{wiki-queue,
|
||||||
|
author = {wikipedia contributors},
|
||||||
|
title = {Queue (abstract data type)},
|
||||||
|
howpublished = {\url{https://en.wikipedia.org/w/index.php?title=Queue_(abstract_data_type)&oldid=1332703688}},
|
||||||
|
year = {2026},
|
||||||
|
month = {01},
|
||||||
|
note = {Zuletzt aufgerufen: 2026-01-20},
|
||||||
|
}
|
||||||
|
|
||||||
|
@misc{os-tasks,
|
||||||
|
author = {Javeria Aiman},
|
||||||
|
title = { 5 Functions of an Operating System },
|
||||||
|
howpublished = {\url{https://mindscribes.com/5-functions-of-an-operating-system/}},
|
||||||
|
year = {2025},
|
||||||
|
month = {07},
|
||||||
|
note = {Zuletzt aufgerufen: 2026-01-20},
|
||||||
|
}
|
||||||
|
|
||||||
|
@misc{everythings-a-file,
|
||||||
|
author = {Neil Brown},
|
||||||
|
title = {Ghosts of Unix Past: a historical search for design patterns},
|
||||||
|
howpublished = {\url{https://lwn.net/Articles/411845/}},
|
||||||
|
year = {2010},
|
||||||
|
month = {10},
|
||||||
|
note = {Zuletzt aufgerufen: 2026-01-20},
|
||||||
|
}
|
||||||
|
|
||||||
|
@misc{device-files,
|
||||||
|
author = {linux kernel contributors},
|
||||||
|
title = {Character device drivers},
|
||||||
|
howpublished = {\url{https://linux-kernel-labs.github.io/refs/heads/master/labs/device_drivers.html}},
|
||||||
|
note = {Zuletzt aufgerufen: 2026-01-20},
|
||||||
|
}
|
||||||
|
|
||||||
|
@manual{sam7s-datasheet,
|
||||||
|
title = {AT91SAM ARM-based Flash MCU},
|
||||||
|
organization = {Microchip Technology Inc.},
|
||||||
|
address = {2355 West Chandler Blvd. Chandler, Arizona, USA},
|
||||||
|
edition = {6175L},
|
||||||
|
year = {2012},
|
||||||
|
month = {10},
|
||||||
|
}
|
||||||
|
|
||||||
|
@misc{i2c-example,
|
||||||
|
author = {Konstantin Veltmann},
|
||||||
|
howpublished = {\url{https://git.veltko.de/Weckyy702/uc-ausarbeitung-linux-treiber/src/commit/d6e0fb978ee99b3bdf1b6b6fe73da930a2b59bbc/examples/i2c.c}},
|
||||||
|
year = {2026},
|
||||||
|
month = {01},
|
||||||
|
}
|
||||||
|
|
||||||
|
@misc{devfs-vs-sysfs,
|
||||||
|
author = {Youssef Salem},
|
||||||
|
title = {The Difference Between /dev and /sys/class},
|
||||||
|
howpublished = {\url{https://www.baeldung.com/linux/dev-sys-class-differences}},
|
||||||
|
year = {2024},
|
||||||
|
month = {08},
|
||||||
|
note = {Zuletzt aufgerufen: 2026-01-22},
|
||||||
|
}
|
||||||
|
|
||||||
|
@misc{adc-driver,
|
||||||
|
author = {the kernel development community},
|
||||||
|
title = {Cirrus Logic EP93xx ADC driver},
|
||||||
|
howpublished = {\url{https://www.kernel.org/doc/html/v6.12/iio/ep93xx_adc.html}},
|
||||||
|
note = {Zuletzt aufgerufen: 2026-01-22},
|
||||||
|
}
|
||||||
|
|
||||||
|
@manual{adc-microchip,
|
||||||
|
title = {How to Use the SAMA5D2 ADC Under Linux®},
|
||||||
|
organization = {Microchip Technology Inc},
|
||||||
|
address = {2355 West Chandler Blvd. Chandler, Arizona, USA},
|
||||||
|
edition = {AN3250},
|
||||||
|
year = {2019},
|
||||||
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user