diff options
| author | Manuel Traut <manut@linutronix.de> | 2017-07-11 19:10:03 +0200 |
|---|---|---|
| committer | Manuel Traut <manut@linutronix.de> | 2017-07-11 19:10:03 +0200 |
| commit | 934f8aecb52bacdcde1da4fc8d2e77cecda22678 (patch) | |
| tree | 836bdf8384f0176f59372f85a3ce0ad00e13418b | |
| parent | 1003ad45790088f8964d305f0cb047c39a60e9d3 (diff) | |
add pruefung 2016
Signed-off-by: Manuel Traut <manut@linutronix.de>
| -rw-r--r-- | 2016-pruefung.tex | 540 |
1 files changed, 540 insertions, 0 deletions
diff --git a/2016-pruefung.tex b/2016-pruefung.tex new file mode 100644 index 0000000..7e36f89 --- /dev/null +++ b/2016-pruefung.tex @@ -0,0 +1,540 @@ +\documentclass[addpoints,12pt]{exam} + +\usepackage{ngerman} +\usepackage{listings,color} +\usepackage{graphicx} + +\firstpageheadrule +\runningheadrule +\lhead{Manuel Traut\\Sommersemester 2016} +\chead{Hochschule Ravensburg-Weingarten\\Linux-Kernelprogrammierung} +\rhead{MatrNr:\\Datum:} + +\firstpagefootrule +\runningfootrule +\firstpagefooter{Page \thepage\ of \numpages} +{} +{Punkte: \makebox[.5in]{\hrulefill}\\ +von \pointsonpage{\thepage} Punkten} + +\runningfooter{Page \thepage\ of \numpages} +{} +{} + +\pagestyle{headandfoot} + +\pointsinrightmargin +\pointpoints{Punkt}{Punkte} + +\begin{document} + + +\begin{coverpages} +\begin{titlepage} +\title{Pr\"ufung Linux-Kernelprogrammierung} +\author{Dozent: Manuel Traut} +\date{04. Juli 2016 10:30 Uhr} +\maketitle +\begin{center} +Hochschule Ravensburg-Weingarten +\vspace{1cm} + +Dauer: 60 Minuten, erlaubte Hilfsmittel: eigene Mitschriebe/Notizen +\end{center} + +\vspace{2cm} +Name:\enspace\hrulefill +\vspace{2cm} +MatrNr:\enspace\hrulefill +\begin{center} +\begin{lstlisting} + a8888b. + d888888b. + 8P"YP"Y88 (((((((()))))))))) + 8|o||o|88 ||VIEL ERFOLG !!|| + 8' .88 ((((((((((((())))) + 8`._.' Y8. + d/ `8b. + .dP . Y8b. + d8:' " `::88b. + d8" `Y88b + :8P ' :888 + 8a. : _a88P + ._/"Yaa_ : .| 88P| + \ YP" `| 8P `. + / \._____.d| .' + `--..__)888888P`._.' +\end{lstlisting} +\end{center} +\end{titlepage} +\end{coverpages} + +\lstset{ % + basicstyle=\scriptsize, % the size of the fonts that are used for the code + breaklines=true, % sets automatic line breaking + frame=single, % adds a frame around the code + language=C, % the language of the code + numbers=left, % where to put the line-numbers; + numbersep=5pt, % how far the line-numbers are from the code + numberstyle=\tiny, % the style that is used for the line-numbers + tabsize=8, % sets default tabsize to 2 spaces +} + + +\begin{questions} + +\question Sie haben einen Roboter entwickelt. Zur Steuerung des Roboters wurde + ein ARM basiertes Linuxsystem integriert. Um die Sensoren und Aktoren des + Roboters vom User-space zugreifbar zu machen haben Sie den Linuxkernel + modifiziert. Die Steuerungsapplikation l\"auft im Userspace und wurde nur + gegen die unter LGPL stehende glibc gelinkt. + +\begin{parts} +\part[2] Argumentieren Sie weshalb es f\"ur zuk\"unftige Entwicklungen am + Roboter f\"ur Ihre Firma von Vorteil ist, die \"Anderungen am Kernel + "Mainline" zu bekommen. + +\part[4] Sie wollen Ihre Modifikationen am Kernel in Mainline Linux + integriert haben. Was \"ubermitteln Sie auf welchem Weg wohin? + +\part[4] Welche Aufgaben haben die Kernel Maintainer in diesem Zusammenhang? + +\part[1] M\"ussen Sie die K\"aufer des Roboters informieren, dass Sie Linux + einsetzen? + +\part[1] Wem m\"ussen Sie auf Anfrage die Modifikationen am Kernel zur + Verf\"ugung stellen? + +\part[1] Wem m\"ussen Sie auf Anfrage den Quellcode Ihrer Applikation zur + Verf\"ugung stellen? +\end{parts} + +\question F\"ur die Kernelentwicklungen im Rahmen des oben genannten + Roboterprojekts wird git als Versionskontrollsystem eingesetzt. Im Produkt + soll ein in einem branch (v4.4.y) des "linux-stable" Repository gepflegter + LTS (long-term support) Kernel zum Einsatz kommen. F\"ur das Mainlining + Ihrer Modifikationen m\"ussen diese gegen den aktuellsten Entwicklungskernel + (master branch des "linux" Repositories gebaut und getestet werden. +\begin{parts} +\part[2] Wozu dient 'git remote' und wie/wozu wird es hier zweckm\"assig + eingesetzt? +\part[4] Sie arbeiten am Kameratreiber und haben einen Zwischenstand erreicht. + Kollege Max koordiniert alle Arbeiten am Kernel. Wie funktioniert die + Integration Ihres Treiberstands in das von Max gepflegte "linux-robo" + Repository? Skizzieren/Beschreiben Sie welche Repositories/Branches in dem + Prozess involviert sind und wem diese geh\"oren. +\end{parts} + +\newpage + +\question +\begin{parts} +\part[1] Welches Kommando f\"uhrt zu den Ausgaben auf folgendem Bild? +\part[1] \"Uber welche Dateien wird der Inhalt / Struktur des Tools gesteuert? +\part[2] Der Kernel kann 'out of tree' gebaut werden. Nenne 2 Vorteile dieser + Methode. +\end{parts} + +\includegraphics[height=0.3\textwidth]{./menuconfig.png} + +\question Sie haben einen Treiber entwickelt, welcher dem User-space + erm\"oglicht einen Ultraschallsensor via sysfs auszulesen. Die + Steuerungsapplikation des Roboters nutzt diese Funktion zyklisch (alle 2ms). + In einer Testapplikation kann dedektiert werden, dass in seltenen F\"allen + (bei einem Dauerlauf, ca. 2 mal t\"aglich) Ihr Treiber einen Wert liefert, + der im Rahmen des Testaufbaus v\"ollig unrealistisch ist. Sie vermuten, dass + es sich um eine Race-condition (Wert wird von Ihrem Treiber + geschrieben, w\"ahrend er vom User-space gelesen wird.) handelt. +\begin{parts} + \part[10] Wie gehen Sie vor um zu pr\"ufen ob Ihre Vermutung wahr ist? + Welche Tools / Infrastruktur setzen Sie wie ein? M\"ussen Sie die User-space + Testapplikation modifizeren? Falls ja wie? M\"ussen Sie den Kernel + modifizieren? Falls ja wie? +\end{parts} + +\question +F\"ur Ihren Roboter ben\"otigen Sie ein Rootfilesystem welches einen Webserver +sowie die user-space Tools zur WLAN Konfiguration enth\"alt. +\begin{parts} + \part[2] Nennen Sie 2 Punkte die Sie beim Erstellen des Rootfilesystem mit + 'Linux from scratch Ansatu' (also ohne Distribution) selber erledigen + m\"u\ss en, welche aber klassischerweise von einer bin\"aren + Linuxdistribution wie z.B. Debian gel\"ost w\"aren. +\end{parts} + +\newpage + +\question +Die folgenden Fragen beziehen sich auf den Quellcode 1 im Anhang. +\begin{parts} +\part[4] Welche Funktionalit\"at stellt der Code zur Verf\"ugung? +\part[2] Der Treiber wird in einem System geladen, welches 2 PCI Devices mit + Vendor ID 0x186c und Device ID 0x0624 besitzt. Wie oft wird mf624\_pci\_probe + und mf624\_init aufgerufen? +\part[4] Egal auf welches Device Sie zugreifen, Sie interagieren immer nur mit + einer der zwei PCI Karten. Wie m\"usssen Sie den Treiber modifizieren, damit + beide Karten funktionieren? +\part[2] Sie wollen dass der Code nicht mehr angesprungen wird, welche Zeile(n) + m\"ussen Sie mindestens l\"oschen? +\part[3] Die Interruptfunktion wird nicht mehr ben\"otigt, welche Zeilen + k\"onnen gel\"oscht werden? +\end{parts} + +\question +Die folgenden Fragen beziehen sich auf den Quellcode 2 im Anhang. +\begin{parts} +\part[10] Mittels 'set\_latch\_u7 / get\_latch\_u7' kann analog zu + 'set\_latch\_u5 / get\_latch\_u5' eine gr\"une LED vom Kernel aus + geschalten werden. Erweitern Sie den Treiber so, dass die gr\"une LED + via 'echo 1 > /sys/class/leds/huhu/brightness' dauerhaft eingeschalten werden + kann. +\end{parts} + +\end{questions} + +\vspace{1cm} +Punkte: \_\_\_\_ von \numpoints +\hspace{1cm} +Note: + +\newpage + +\begin{appendix} + +Quellcode 1: + +\begin{lstlisting} +/* + * UIO driver fo Humusoft MF624 DAQ card. + * Copyright (C) 2011 Rostislav Lisovy <lisovy@gmail.com>, + * Czech Technical University in Prague + * + * Copyright (C) 2016 Manuel Traut <manut@mecka.net>, + * modified for usage in kernel exams + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + */ + +#include <linux/init.h> +#include <linux/module.h> +#include <linux/device.h> +#include <linux/pci.h> +#include <linux/slab.h> +#include <linux/io.h> +#include <linux/kernel.h> +#include <linux/uio_driver.h> + +#define PCI_VENDOR_ID_HUMUSOFT 0x186c +#define PCI_DEVICE_ID_MF624 0x0624 +#define PCI_SUBVENDOR_ID_HUMUSOFT 0x186c +#define PCI_SUBDEVICE_DEVICE 0x0624 + +/* BAR0 Interrupt control/status register */ +#define INTCSR 0x4C +#define INTCSR_ADINT_ENABLE (1 << 0) +#define INTCSR_CTR4INT_ENABLE (1 << 3) +#define INTCSR_PCIINT_ENABLE (1 << 6) +#define INTCSR_ADINT_STATUS (1 << 2) +#define INTCSR_CTR4INT_STATUS (1 << 5) + +enum mf624_interrupt_source {ADC, CTR4, ALL}; + +static void mf624_disable_interrupt(enum mf624_interrupt_source source, + struct uio_info *info) +{ + void __iomem *INTCSR_reg = info->mem[0].internal_addr + INTCSR; + + switch (source) { + case ADC: + iowrite32(ioread32(INTCSR_reg) + & ~(INTCSR_ADINT_ENABLE | INTCSR_PCIINT_ENABLE), + INTCSR_reg); + break; + + case CTR4: + iowrite32(ioread32(INTCSR_reg) + & ~(INTCSR_CTR4INT_ENABLE | INTCSR_PCIINT_ENABLE), + INTCSR_reg); + break; + + case ALL: + default: + iowrite32(ioread32(INTCSR_reg) + & ~(INTCSR_ADINT_ENABLE | INTCSR_CTR4INT_ENABLE + | INTCSR_PCIINT_ENABLE), + INTCSR_reg); + break; + } +} + +static void mf624_enable_interrupt(enum mf624_interrupt_source source, + struct uio_info *info) +{ + void __iomem *INTCSR_reg = info->mem[0].internal_addr + INTCSR; + + switch (source) { + case ADC: + iowrite32(ioread32(INTCSR_reg) + | INTCSR_ADINT_ENABLE | INTCSR_PCIINT_ENABLE, + INTCSR_reg); + break; + + case CTR4: + iowrite32(ioread32(INTCSR_reg) + | INTCSR_CTR4INT_ENABLE | INTCSR_PCIINT_ENABLE, + INTCSR_reg); + break; + + case ALL: + default: + iowrite32(ioread32(INTCSR_reg) + | INTCSR_ADINT_ENABLE | INTCSR_CTR4INT_ENABLE + | INTCSR_PCIINT_ENABLE, + INTCSR_reg); + break; + } +} + +static irqreturn_t mf624_irq_handler(int irq, struct uio_info *info) +{ + void __iomem *INTCSR_reg = info->mem[0].internal_addr + INTCSR; + + if ((ioread32(INTCSR_reg) & INTCSR_ADINT_ENABLE) + && (ioread32(INTCSR_reg) & INTCSR_ADINT_STATUS)) { + mf624_disable_interrupt(ADC, info); + return IRQ_HANDLED; + } + + if ((ioread32(INTCSR_reg) & INTCSR_CTR4INT_ENABLE) + && (ioread32(INTCSR_reg) & INTCSR_CTR4INT_STATUS)) { + mf624_disable_interrupt(CTR4, info); + return IRQ_HANDLED; + } + + return IRQ_NONE; +} + +static int mf624_irqcontrol(struct uio_info *info, s32 irq_on) +{ + if (irq_on == 0) + mf624_disable_interrupt(ALL, info); + else if (irq_on == 1) + mf624_enable_interrupt(ALL, info); + + return 0; +} + +static struct uio_info mf624_info = { + .name = "mf624"; + .version = "0.0.1"; +}; + +static int mf624_pci_probe(struct pci_dev *dev, const struct pci_device_id *id) +{ + struct uio_info *info = &mf624_info; + + if (pci_enable_device(dev)) + return -1; + + if (pci_request_regions(dev, "mf624")) + goto out_disable; + + /* Note: Datasheet says device uses BAR0, BAR1, BAR2 -- do not trust it */ + + /* BAR0 */ + info->mem[0].name = "PCI chipset, interrupts, status " + "bits, special functions"; + info->mem[0].addr = pci_resource_start(dev, 0); + if (!info->mem[0].addr) + goto out_release; + info->mem[0].size = pci_resource_len(dev, 0); + info->mem[0].memtype = UIO_MEM_PHYS; + info->mem[0].internal_addr = pci_ioremap_bar(dev, 0); + if (!info->mem[0].internal_addr) + goto out_release; + + /* BAR2 */ + info->mem[1].name = "ADC, DAC, DIO"; + info->mem[1].addr = pci_resource_start(dev, 2); + if (!info->mem[1].addr) + goto out_unmap0; + info->mem[1].size = pci_resource_len(dev, 2); + info->mem[1].memtype = UIO_MEM_PHYS; + info->mem[1].internal_addr = pci_ioremap_bar(dev, 2); + if (!info->mem[1].internal_addr) + goto out_unmap0; + + /* BAR4 */ + info->mem[2].name = "Counter/timer chip"; + info->mem[2].addr = pci_resource_start(dev, 4); + if (!info->mem[2].addr) + goto out_unmap1; + info->mem[2].size = pci_resource_len(dev, 4); + info->mem[2].memtype = UIO_MEM_PHYS; + info->mem[2].internal_addr = pci_ioremap_bar(dev, 4); + if (!info->mem[2].internal_addr) + goto out_unmap1; + + info->irq = dev->irq; + info->irq_flags = IRQF_SHARED; + info->handler = mf624_irq_handler; + + info->irqcontrol = mf624_irqcontrol; + + if (uio_register_device(&dev->dev, info)) + goto out_unmap2; + + pci_set_drvdata(dev, info); + + return 0; + +out_unmap2: + iounmap(info->mem[2].internal_addr); +out_unmap1: + iounmap(info->mem[1].internal_addr); +out_unmap0: + iounmap(info->mem[0].internal_addr); + +out_release: + pci_release_regions(dev); + +out_disable: + pci_disable_device(dev); + + return -ENODEV; +} + +static void mf624_pci_remove(struct pci_dev *dev) +{ + struct uio_info *info = pci_get_drvdata(dev); + + mf624_disable_interrupt(ALL, info); + + uio_unregister_device(info); + pci_release_regions(dev); + pci_disable_device(dev); + + iounmap(info->mem[0].internal_addr); + iounmap(info->mem[1].internal_addr); + iounmap(info->mem[2].internal_addr); + + kfree(info); +} + +static const struct pci_device_id mf624_pci_id[] = { + { PCI_DEVICE(PCI_VENDOR_ID_HUMUSOFT, PCI_DEVICE_ID_MF624) }, + { 0, } +}; + +static struct pci_driver mf624_pci_driver = { + .name = "mf624", + .id_table = mf624_pci_id, + .probe = mf624_pci_probe, + .remove = mf624_pci_remove, +}; +MODULE_DEVICE_TABLE(pci, mf624_pci_id); + +int mf624_init(void) +{ + return pci_driver_register(&mf624_pci_driver); +} + +void mf624_exit(void) +{ + pci_driver_unregister(&mf624_pci_driver); +} + +module_init(mf624_init); +module_exit(mf624_exit); + +MODULE_LICENSE("GPL v2"); +MODULE_AUTHOR("Rostislav Lisovy <lisovy@gmail.com>"); +\end{lstlisting} + +\newpage + +Quellcode 2: + +\begin{lstlisting} +/* + * LEDs driver for the "User LED" on Routerboard532 + * + * Copyright (C) 2009 Phil Sutter <n0-1@freewrt.org> + * + * Based on leds-cobalt-qube.c by Florian Fainelly and + * rb-diag.c (my own standalone driver for both LED and + * button of Routerboard532). + */ + +#include <linux/leds.h> +#include <linux/module.h> +#include <linux/platform_device.h> + +#include <asm/mach-rc32434/gpio.h> +#include <asm/mach-rc32434/rb.h> + +static void rb532_led_set(struct led_classdev *cdev, + enum led_brightness brightness) +{ + if (brightness) + set_latch_u5(LO_ULED, 0); + + else + set_latch_u5(0, LO_ULED); +} + +static enum led_brightness rb532_led_get(struct led_classdev *cdev) +{ + return (get_latch_u5() & LO_ULED) ? LED_FULL : LED_OFF; +} + +static struct led_classdev rb532_uled = { + .name = "uled", + .brightness_set = rb532_led_set, + .brightness_get = rb532_led_get, + .default_trigger = "nand-disk", +}; + +static int rb532_led_probe(struct platform_device *pdev) +{ + return led_classdev_register(&pdev->dev, &rb532_uled); +} + +static int rb532_led_remove(struct platform_device *pdev) +{ + led_classdev_unregister(&rb532_uled); + return 0; +} + +static struct platform_driver rb532_led_driver = { + .probe = rb532_led_probe, + .remove = rb532_led_remove, + .driver = { + .name = "rb532-led", + }, +}; + +module_platform_driver(rb532_led_driver); + +MODULE_LICENSE("GPL"); +MODULE_DESCRIPTION("User LED support for Routerboard532"); +MODULE_AUTHOR("Phil Sutter <n0-1@freewrt.org>"); +MODULE_ALIAS("platform:rb532-led"); +\end{lstlisting} + +\end{appendix} + + +\end{document} |
