Add notes about python, databases, japan, debugging and inotify.

This commit is contained in:
2022-01-09 15:28:22 +01:00
parent c14526f2ed
commit 0d043ef2ef
14 changed files with 436 additions and 2 deletions

160
20220106214423-inotify.org Normal file
View File

@@ -0,0 +1,160 @@
:PROPERTIES:
:ID: fad57303-ce0c-4ae4-9529-294f70ecfaa5
:mtime: 20220107081819
:ctime: 20220106214423
:END:
#+title: Inotify
* Présentation
Mécanisme du noyan Linux fournissant des notifications concernant le système de fichiers.
* Exemples
** C++
#+BEGIN_SRC C++ :tangle "/tmp/dummy.cpp" :results output
#include <cstring>
#include <iostream>
#include <fstream>
#include <sys/stat.h>
#include <sys/inotify.h>
#include <unistd.h>
#include <poll.h>
static void onInotify(int fd)
{
std::cout << "onInotify(" << fd << ")" << std::endl;
bool finished = false;
while (!finished)
{
struct inotify_event event;
const ssize_t len = read(fd, &event, sizeof(event));
if (len == -1 && errno != EAGAIN)
{
std::cout << "!read " << strerror(errno);
finished = true;
}
// If the nonblocking read() found no events to read, then
// it returns -1 with errno set to EAGAIN.
// Nothing to read here, exit the loop.
if (len <= 0)
{
finished = true;
}
else
{
// Print event type.
if (event.mask & IN_OPEN)
{
std::cout << "IN_OPEN: ";
}
if (event.mask & IN_CLOSE_NOWRITE)
{
std::cout << "IN_CLOSE_NOWRITE: ";
}
if (event.mask & IN_CLOSE_WRITE)
{
std::cout << "IN_CLOSE_WRITE: ";
}
// Print the name of the file.
if (event.len)
{
std::cout << event.name << std::endl;
}
// Print type of filesystem object.
if (event.mask & IN_ISDIR)
{
std::cout << " [directory]" << std::endl;
}
else
{
std::cout << " [file]" << std::endl;
}
}
}
}
int main(int argc, char** argv)
{
const std::string filename = "/tmp/dummy";
// Make sure the filename exists.
struct stat buffer;
if (stat(filename.c_str(), &buffer) != 0)
{
std::cout << filename << " doesn't exists... create it." << std::endl;
std::ofstream dummy(filename);
}
const int fd = inotify_init1(IN_NONBLOCK | IN_CLOEXEC);
if (fd < 0)
{
std::cout << "Unable to init inotify: " << strerror(errno) << std::endl;
exit(EXIT_FAILURE);
}
// Trigger on open and close events.
const int wd = inotify_add_watch(fd, filename.c_str(), IN_OPEN | IN_CLOSE);
if (wd == -1)
{
std::cout << "Cannot watch '" << filename << "': " << strerror(errno) << std::endl;
close(fd);
exit(EXIT_FAILURE);
}
// Prepare for pooling.
const nfds_t nfds = 2;
struct pollfd fds[2];
// Console input
fds[0].fd = STDIN_FILENO;
fds[0].events = POLLIN;
// Inotify input
fds[1].fd = fd;
fds[1].events = POLLIN;
// Wait for events and/or terminal input.
std::cout << "Listening for events." << std::endl;
bool stop = false;
bool error = false;
while (!stop)
{
const int poll_num = poll(fds, nfds, -1);
if (poll_num == -1)
{
if (errno == EINTR)
{
continue;
}
std::cout << "poll" << std::endl;
error = stop = true;
}
else if (poll_num > 0)
{
if (fds[0].revents & POLLIN)
{
// Console input is available. Empty stdin and quit.
char buf;
while (read(STDIN_FILENO, &buf, 1) > 0 && buf != '\n')
{
continue;
}
std::cout << "Stopping resquested..." << std::endl;
break;
}
if (fds[1].revents & POLLIN)
{
// Inotify events are available.
onInotify(fd);
}
}
}
std::cout << "Listening for events stopped." << std::endl;
/* Close inotify file descriptor. */
close(fd);
exit(EXIT_SUCCESS);
}
#+END_SRC
* Références
* inotify(7) — Linux manual page]]