20801 Commits

Author SHA1 Message Date
Simon McVittie
0a019869bb Merge branch 'backport-1206-option-nul-termination' into 'glib-2-62'
Backport !1206 “goption: Relax assertion to avoid being broken by kdeinit5” to glib-2-62

See merge request GNOME/glib!1207
2019-10-31 16:20:37 +00:00
Simon McVittie
20863d3522 goption: Relax assertion to avoid being broken by kdeinit5
kdeinit5 overwrites argv, which in turn results in /proc/self/cmdline
being overwritten. It seems that this is done in a way that does not
necessarily guarantee that /proc/self/cmdline will end up NUL-terminated.

However, g_file_get_contents() is documented to fill a buffer of size
len + 1, where buffer[len] == '\0', even if the file's actual contents
(from buffer[0] to buffer[len-1] inclusive) did not include a NUL;
so we can safely relax this assertion slightly.

Resolves: https://gitlab.gnome.org/GNOME/glib/issues/1923
Signed-off-by: Simon McVittie <smcv@collabora.com>
2019-10-31 15:42:01 +00:00
Simon McVittie
b123ee4db6 Merge branch 'backport-1192-1193-gdbus-peer-brokenness' into 'glib-2-62'
Backport !1192, !1193, !1197 Fixes for gdbus-peer tests to glib-2-62

See merge request GNOME/glib!1203
2019-10-31 14:01:26 +00:00
Simon McVittie
73e4bc7fed gdbus-peer test: Use unix:dir address if exact format doesn't matter
Previously, we used unix:tmpdir, except in tests that verify that a
particular address type works (notably unix:dir). Now we use unix:dir
most of the time, and unix:tmpdir gets its own test instead.

This helps to ensure that the tests continue to work on non-Linux Unix
kernels, where abstract sockets do not exist and so unix:tmpdir is
equivalent to unix:dir, even in the common case where the developer has
only tried the test on Linux.

Signed-off-by: Simon McVittie <smcv@collabora.com>
2019-10-31 12:40:31 +00:00
Simon McVittie
3560c29d94 gdbus-peer test: Stop GDBusServer before tearing down temporary directory
Otherwise, since GNOME/glib!1193, the listening socket won't be deleted,
and if we are not using abstract sockets (for example on *BSD), g_rmdir
will fail with ENOTEMPTY.

Fixes: 8e32b8e8 "gdbusserver: Delete socket and nonce file when stopping server"
Resolves: GNOME/glib#1921
Signed-off-by: Simon McVittie <smcv@collabora.com>
2019-10-31 12:40:31 +00:00
Simon McVittie
4de7fc9bed gdbus-peer test: Improve diagnostics if g_rmdir fails
Helps: GNOME/glib#1921
Signed-off-by: Simon McVittie <smcv@collabora.com>
2019-10-31 12:40:31 +00:00
Philip Withnall
4c8d7c24c1 gdbusserver: Keep a strong reference to the server in callbacks
The `on_run()` function could be executed in any worker thread from the
`GThreadedSocketListener`, but didn’t previously hold a strong reference
to the `GDBusServer`, which meant the server could be finalised in
another thread while `on_run()` was still running.

This was not ideal.

Hold a strong reference to the `GDBusServer` while the socket listener
is listening, i.e. between every paired call to `g_dbus_server_start()`
and `g_dbus_server_stop()`.

Signed-off-by: Philip Withnall <withnall@endlessm.com>

Fixes: #1318
2019-10-31 10:52:21 +00:00
Philip Withnall
30b7623e1e gdbusserver: Delete socket and nonce file when stopping server
Rather than when finalising it. They should be automatically recreated
if the server is re-started.

This is important for ensuring that all externally visible behaviour of
the `GDBusServer` is synchronised with calls to
g_dbus_server_{start,stop}(). Finalisation of the server object could
happen an arbitrarily long time after g_dbus_server_stop() is called.

Signed-off-by: Philip Withnall <withnall@endlessm.com>

Helps: #1318
2019-10-31 10:52:21 +00:00
Philip Withnall
964804014a tests: Isolate directories in gdbus-peer test
So that the tests all end up using separate `.dbus-keyring` directories,
and hence not racing to create and acquire lock files, use
`G_TEST_OPTION_ISOLATE_DIRS` to ensure they all run in separate
disposable directories.

This has the added benefit of meaning they don’t touch the developer’s
actual `$HOME` directory.

This reduces the false-failure rate of `gdbus-peer` by a factor of 9 for
me on my local machine.

Signed-off-by: Philip Withnall <withnall@endlessm.com>

Fixes: #1912
2019-10-31 10:52:21 +00:00
Philip Withnall
45d98b8863 tests: Move main loop and test GUID into test functions in gdbus-peer
There’s actually no need for them to be global or reused between unit
tests, so move them inside the test functions.

This is one step towards eliminating shared state between the unit
tests.

Signed-off-by: Philip Withnall <withnall@endlessm.com>

Helps: #1912
2019-10-31 10:52:21 +00:00
Philip Withnall
3f7fa2f955 gdbusauthmechanismsha1: Create .dbus-keyrings directory recursively
If the directory is overridden, for example when running tests, the
parent directory of `.dbus-keyrings` (i.e. the fake `$HOME` directory)
might not exist. Create it automatically.

This should realistically not have an effect on non-test code.

Signed-off-by: Philip Withnall <withnall@endlessm.com>

Helps: #1912
2019-10-31 10:52:21 +00:00
Philip Withnall
74c33c73ac gdbusauthmechanismsha1: Remove unnecessary g_warning() calls
These can be hit in the tests (if multiple tests run in parallel are
racing for `~/.dbus-keyrings/org_gtk_gdbus_general.lock` for a prolonged
period) and will cause spurious test failures due to the use of
`G_DEBUG=fatal-warnings`.

Instead, allow the error messages to be inspected programmatically.

Signed-off-by: Philip Withnall <withnall@endlessm.com>

Helps: #1912
2019-10-31 10:52:20 +00:00
Simon McVittie
fcbb888238 Merge branch 'backport-1173-ossfuzz-variant-parser-glib-2-62' into 'glib-2-62'
Backport !1173 “gvariant: Limit recursion in g_variant_parse()” to glib-2-62

See merge request GNOME/glib!1184
2019-10-29 14:25:30 +00:00
Simon McVittie
404b07183b Merge branch 'backport-1176-1183-1188-1191-glib-2-62' into 'glib-2-62'
Backport !1176, !1183, !1188, !1191 to `glib-2-62`

See merge request GNOME/glib!1194
2019-10-29 14:20:56 +00:00
Simon McVittie
c7618cce37 GDBus: prefer getsockopt()-style credentials-passing APIs
Conceptually, a D-Bus server is really trying to determine the credentials
of (the process that initiated) a connection, not the credentials that
the process had when it sent a particular message. Ideally, it does
this with a getsockopt()-style API that queries the credentials of the
connection's initiator without requiring any particular cooperation from
that process, avoiding a class of possible failures.

The leading '\0' in the D-Bus protocol is primarily a workaround
for platforms where the message-based credentials-passing API is
strictly better than the getsockopt()-style API (for example, on
FreeBSD, SCM_CREDS includes a process ID but getpeereid() does not),
or where the getsockopt()-style API does not exist at all. As a result
libdbus, the reference implementation of D-Bus, does not implement
Linux SCM_CREDENTIALS at all - it has no reason to do so, because the
SO_PEERCRED socket option is equally informative.

This change makes GDBusServer on Linux more closely match the behaviour
of libdbus.

In particular, GNOME/glib#1831 indicates that when a libdbus client
connects to a GDBus server, recvmsg() sometimes yields a SCM_CREDENTIALS
message with cmsg_data={pid=0, uid=65534, gid=65534}. I think this is
most likely a race condition in the early steps to connect:

        client           server
    connect
                         accept
    send '\0' <- race -> set SO_PASSCRED = 1
                         receive '\0'

If the server wins the race:

        client           server
    connect
                         accept
                         set SO_PASSCRED = 1
    send '\0'
                         receive '\0'

then everything is fine. However, if the client wins the race:

        client           server
    connect
                         accept
    send '\0'
                         set SO_PASSCRED = 1
                         receive '\0'

then the kernel does not record credentials for the message containing
'\0' (because SO_PASSCRED was 0 at the time). However, by the time the
server receives the message, the kernel knows that credentials are
desired. I would have expected the kernel to omit the credentials header
in this case, but it seems that instead, it synthesizes a credentials
structure with a dummy process ID 0, a dummy uid derived from
/proc/sys/kernel/overflowuid and a dummy gid derived from
/proc/sys/kernel/overflowgid.

In an unconfigured GDBusServer, hitting this race condition results in
falling back to DBUS_COOKIE_SHA1 authentication, which in practice usually
succeeds in authenticating the peer's uid. However, we encourage AF_UNIX
servers on Unix platforms to allow only EXTERNAL authentication as a
security-hardening measure, because DBUS_COOKIE_SHA1 relies on a series
of assumptions including a cryptographically strong PRNG and a shared
home directory with no write access by others, which are not necessarily
true for all operating systems and users. EXTERNAL authentication will
fail if the server cannot determine the client's credentials.

In particular, this caused a regression when CVE-2019-14822 was fixed
in ibus, which appears to be resolved by this commit. Qt clients
(which use libdbus) intermittently fail to connect to an ibus server
(which uses GDBusServer), because ibus no longer allows DBUS_COOKIE_SHA1
authentication or non-matching uids.

Signed-off-by: Simon McVittie <smcv@collabora.com>
Closes: https://gitlab.gnome.org/GNOME/glib/issues/1831
2019-10-28 21:02:44 +00:00
Simon McVittie
5f9318af8f credentials: Invalid Linux struct ucred means "no information"
On Linux, if getsockopt SO_PEERCRED is used on a TCP socket, one
might expect it to fail with an appropriate error like ENOTSUP or
EPROTONOSUPPORT. However, it appears that in fact it succeeds, but
yields a credentials structure with pid 0, uid -1 and gid -1. These
are not real process, user and group IDs that can be allocated to a
real process (pid 0 needs to be reserved to give kill(0) its documented
special semantics, and similarly uid and gid -1 need to be reserved for
setresuid() and setresgid()) so it is not meaningful to signal them to
high-level API users.

An API user with Linux-specific knowledge can still inspect these fields
via g_credentials_get_native() if desired.

Similarly, if SO_PASSCRED is used to receive a SCM_CREDENTIALS message
on a receiving Unix socket, but the sending socket had not enabled
SO_PASSCRED at the time that the message was sent, it is possible
for it to succeed but yield a credentials structure with pid 0, uid
/proc/sys/kernel/overflowuid and gid /proc/sys/kernel/overflowgid. Even
if we were to read those pseudo-files, we cannot distinguish between
the overflow IDs and a real process that legitimately has the same IDs
(typically they are set to 'nobody' and 'nogroup', which can be used
by a real process), so we detect this situation by noticing that
pid == 0, and to save syscalls we do not read the overflow IDs from
/proc at all.

This results in a small API change: g_credentials_is_same_user() now
returns FALSE if we compare two credentials structures that are both
invalid. This seems like reasonable, conservative behaviour: if we cannot
prove that they are the same user, we should assume they are not.

(Dropped new translatable string when backporting to `glib-2-62`.)

Signed-off-by: Simon McVittie <smcv@collabora.com>
2019-10-28 21:02:44 +00:00
Simon McVittie
1cfab12a28 gcredentialsprivate: Document the various private macros
Signed-off-by: Simon McVittie <smcv@collabora.com>
2019-10-28 21:02:31 +00:00
Philip Withnall
8214e07a60 gspawn: Port to g_poll() from select()
This removes the limitation of select() that only FDs with values lower
than FD_SETSIZE can be used. Previously, if the out/err pipe FDs had
high values (which could happen if a large process, like Firefox, was
spawning subprocesses while having a lot of FDs open), GLib would abort
due to an assertion failure in libc.

(Minor cherry-pick conflicts when cherry picked to `glib-2-62`. Dropped
translatable string changes.)

Signed-off-by: Philip Withnall <withnall@endlessm.com>

Fixes: #954
2019-10-28 21:02:31 +00:00
Philip Withnall
531baac79d gtestutils: Add additional non-NULL check in g_assert_cmpmem()
The compiler can’t work out from the combination of other conditions
that it’s not possible for (m2 == NULL) to hold true when memcmp() is
called, so add an explicit condition.

Signed-off-by: Philip Withnall <withnall@endlessm.com>

Fixes: #1897
2019-10-28 20:57:14 +00:00
Philip Withnall
9dc2fca288 docs: Add objcopy to example cross-compilation file
Signed-off-by: Philip Withnall <withnall@endlessm.com>

Helps: #1916
2019-10-28 20:56:49 +00:00
Philip Withnall
56da3e5a01 tests: Use objcopy from the cross-compilation file, if configured
Otherwise we’ll end up using the host’s `objcopy`, which will output
object files in the wrong format.

Signed-off-by: Philip Withnall <withnall@endlessm.com>

Fixes: #1916
2019-10-28 20:56:49 +00:00
Philip Withnall
89c2ead766 gvariant: Limit recursion in g_variant_parse()
The token parsing done by g_variant_parse() uses recursive function
calls, so at some point it will hit the stack limit. As with previous
changes to `GVariantType` parsing (commit 7c4e6e9fbe4), limit the level
of nesting of containers parsed by g_variant_parse() to something
reasonable. We guarantee 64 levels of nesting, which should be enough
for anyone, and is the same as what we guarantee for types.

(Backport to 2.62: Dropped the new `G_VARIANT_PARSE_ERROR_RECURSION`
error code in favour of `G_VARIANT_PARSE_ERROR_FAILED`, to avoid adding
API.)

oss-fuzz#10286

Signed-off-by: Philip Withnall <withnall@endlessm.com>
2019-10-25 17:56:03 +01:00
Sebastian Dröge
4b3d30963c Merge branch 'backport-1164-mimeapps-test-race-glib-2-62' into 'glib-2-62'
Backport !1164 “use-after-free fix in mimeapps test” to glib-2-62

See merge request GNOME/glib!1174
2019-10-22 06:59:46 +00:00
Philip Withnall
ca9f51b82f 2.62.2
Signed-off-by: Philip Withnall <withnall@endlessm.com>
2.62.2
2019-10-21 18:18:23 +01:00
Philip Withnall
a2811a5236 glocalfilemonitor: Keep a weak ref to the monitor in GFileMonitorSource
Previously we were keeping a pointer to the `GFileMonitor` in a
`GFileMonitorSource` instance, but since we weren’t keeping a strong
reference, that `GFileMonitor` instance could be finalised from another
thread at any point while the source was referring to it. Not good.

Use a weak reference, and upgrade it to a strong reference whenever the
`GFileMonitorSource` is referring to the file monitor.

Signed-off-by: Philip Withnall <withnall@endlessm.com>

Helps: #1903
2019-10-18 16:59:50 +01:00
Philip Withnall
fd15e33bc8 gdesktopappinfo: Cancel file monitor when resetting a DesktopFileDir
It’s not enough to unref the monitor, since the GLib worker thread might
still hold a reference to it.

Signed-off-by: Philip Withnall <withnall@endlessm.com>

Helps: #1903
2019-10-18 16:59:50 +01:00
Philip Withnall
e127bf8453 gdesktopappinfo: Allocate DesktopFileDir structs dynamically
`DesktopFileDir` pointers are passed around between threads: they are
initially created on the main thread, but a pointer to them is passed to
the GLib worker thread in the file monitor callback
(`desktop_file_dir_changed()`).

Accordingly, the `DesktopFileDir` objects either have to be
 (1) immutable;
 (2) reference counted; or
 (3) synchronised between the two threads
to avoid one of them being used by one thread after being freed on
another. Option (1) changed with commit 99bc33b6 and is no longer an
option. Option (3) would mean blocking the main thread on the worker
thread, which would be hard to achieve and is against the point of
having a worker thread. So that leaves option (2), which is implemented
here.

Signed-off-by: Philip Withnall <withnall@endlessm.com>

Fixes: #1903
2019-10-18 16:59:50 +01:00
Sebastian Dröge
9191ab92f6 Merge branch 'backport-1158-dbus-race-glib-2-62' into 'glib-2-62'
Backport !1158 “Fix use-after-free when calling g_dbus_connection_flush_sync()” to glib-2-62

See merge request GNOME/glib!1162
2019-10-18 14:01:44 +00:00
Milan Crha
9214717971 Fix use-after-free when calling g_dbus_connection_flush_sync()
When the _g_dbus_worker_flush_sync() schedules the 'data' and releases
the worker->write_lock, it is possible for the GDBus worker thread thread
to finish the D-Bus call and acquire the worker->write_lock before
the _g_dbus_worker_flush_sync() re-acquires it in the if (data != NULL) body.
When that happens, the ostream_flush_cb() increases the worker->write_num_messages_flushed
and then releases the worker->write_lock. The write lock is reacquired by
the _g_dbus_worker_flush_sync(), which sees that the while condition is satisfied,
thus it doesn't enter the loop body and immediately clears the data members and
frees the data structure itself. The ostream_flush_cb() is still ongoing, possibly
inside flush_data_list_complete(), where it accesses the FlushData, which can be
in any stage of being freed.

Instead, add an explicit boolean flag indicating when the flush is truly finished.

Closes #1896
2019-10-10 15:58:59 +01:00
Philip Withnall
5c1fe670bb Merge branch 'backport-1146-solaris-fixes-glib-2-62' into 'glib-2-62'
Backport !1146 Solaris fixes to glib-2-62

See merge request GNOME/glib!1156
2019-10-08 09:23:56 +00:00
Alan Coopersmith
670d6d390a build: no --export-dynamic ldflags for Solaris
Signed-off-by: Alan Coopersmith <alan.coopersmith@oracle.com>
2019-10-07 19:13:59 +01:00
Alan Coopersmith
8e49fba3f3 gunixmounts: Handle Solaris name of mnt_mntopts in place of mnt_opts
Fixes build failure:
../gio/gunixmounts.c: In function ‘_g_get_unix_mounts’:
../gio/gunixmounts.c:742:53: error: ‘struct mnttab’ has no member named ‘mnt_opts’; did you mean ‘mnt_mntopts’?
  742 |                                              mntent.mnt_opts,
      |                                                     ^~~~~~~~
      |                                                     mnt_mntopts

Signed-off-by: Alan Coopersmith <alan.coopersmith@oracle.com>
2019-10-07 19:13:59 +01:00
Christoph Reiter
e605f779ab Merge branch 'backport-1152-winhttpvfs-prgname-glib-2-62' into 'glib-2-62'
Backport !1152 “gwinhttpvfs: Handle g_get_prgname() returning NULL” to glib-2-62

See merge request GNOME/glib!1154
2019-10-07 16:26:29 +00:00
Christoph Reiter
32fe7ad936 gwinhttpvfs: Handle g_get_prgname() returning NULL
When prgname wasn't set NULL would be passed to g_utf8_to_utf16()
resulting in "g_utf8_to_utf16: assertion 'str != NULL' failed"
2019-10-07 10:05:31 +01:00
Philip Withnall
2a0e33360d 2.62.1
Signed-off-by: Philip Withnall <withnall@endlessm.com>
2.62.1
2019-10-04 12:41:16 +01:00
Ondrej Holy
43530c09dd Merge branch 'backport-1134-file-copy-fix-glib-2-62' into 'glib-2-62'
Backport !1134 Fix for file copy permissions to glib-2-62

See merge request GNOME/glib!1142
2019-10-03 06:36:33 +00:00
Philip Withnall
3b3e3cad4c Merge branch 'cherry-pick-42d8e177' into 'glib-2-62'
[2.62] Always build tests if we enabled installed-tests

See merge request GNOME/glib!1141
2019-10-02 15:55:30 +00:00
Philip Withnall
56e244ecdf gfile: Don’t copy files as private if using default permissions
If a copy operation is started with `G_FILE_COPY_TARGET_DEFAULT_PERMS`,
don’t create the destination file as private. Instead, create it with
the process’ current umask (i.e. ‘default permissions’).

This is a partial re-work of commit d8f8f4d637ce43f8699ba94c9b, with
input from Ondrej Holy.

Signed-off-by: Philip Withnall <withnall@endlessm.com>

Fixes: #174
2019-10-02 16:42:40 +01:00
Philip Withnall
1b6d8e58b2 gfile: Factor out flags when copying files
This introduces no functional changes; just reduces duplication in the
code a little.

Signed-off-by: Philip Withnall <withnall@endlessm.com>
2019-10-02 16:42:40 +01:00
Sebastian Dröge
ab2d85ebfd Merge branch 'cherry-pick-14609b0b' into 'glib-2-62'
[2.62] g_file_info_get_modification_date_time: Calculate in integer domain

See merge request GNOME/glib!1140
2019-10-02 10:10:30 +00:00
Simon McVittie
db46306b47 Always build tests if we enabled installed-tests
If we're cross-compiling, the installed-tests are useful even if we
can't run them on the build machine: we can copy them to the host
machine (possibly via a distro package like Debian's libglib2.0-tests)
and run them there.

While I'm changing the build-tests condition anyway, deduplicate it.

Based on a patch by Helmut Grohne.

Bug-Debian: https://bugs.debian.org/941509
Signed-off-by: Simon McVittie <smcv@collabora.com>


(cherry picked from commit 42d8e17795254ed1590241347b34d19479b9b575)
2019-10-02 08:57:36 +00:00
Simon McVittie
5625760f12 g_file_info_get_modification_date_time: Calculate in integer domain
g_date_time_add_seconds() and g_date_time_add_full() use floating-point
seconds, which can result in the value varying slightly from what's
actually on disk. This causes intermittent test failures in
gio/tests/g-file-info.c on Debian i386, where we set a file's mtime
to be 50µs later, then read it back and sometimes find that it is only
49µs later than the previous value.

I've only seen this happen on i386, which means it might be to do with
different floating-point rounding when a value is stored in the 80-bit
legacy floating point registers rather than in double precision.

g_date_time_add() takes a GTimeSpan, which is in microseconds;
conveniently, that's exactly what we get from the GFileInfo.

Bug-Debian: https://bugs.debian.org/941547
Signed-off-by: Simon McVittie <smcv@collabora.com>


(cherry picked from commit 14609b0b256b9c13162719868d4dfc2b419d885f)
2019-10-02 08:56:14 +00:00
Ask Hjorth Larsen
514880671c Updated Danish translation 2019-10-02 05:54:08 +02:00
Sebastian Dröge
2de58d25b3 Merge branch 'backport-1125-date-time-error-handling-again-glib-2-62' into 'glib-2-62'
Backport !1125 and !1115 GDateTime parsing fixes to glib-2-62

See merge request GNOME/glib!1127
2019-09-26 08:17:35 +00:00
Sebastian Dröge
ed8c69eb03 Merge branch 'backport-1043-variant-bytes-glib-2-62' into 'glib-2-62'
Backport !1043 “gvariant: Handle empty serialisations in get_child_value()” to glib-2-62

See merge request GNOME/glib!1128
2019-09-26 07:57:40 +00:00
Philip Withnall
f2d9f16e61 gvariant: Handle empty serialisations in get_child_value()
When g_variant_get_child_value() is called for a child whose
serialisation is an empty byte string (which is possible), `bytes_data`
will be non-`NULL`, but `data` may be `NULL`. This results in a negative
offset being passed to `g_bytes_new_from_bytes()`, and a critical
warning.

So if `data` is `NULL`, set it to point to `bytes_data` so the offset is
calculated as zero. The actual value of the offset doesn’t matter, since
in this situation the size is always zero. An offset of zero is never
going to cause problems.

Signed-off-by: Philip Withnall <withnall@endlessm.com>
Fixes: #1865
2019-09-25 14:49:59 +01:00
Philip Withnall
7b393fce31 gdatetime: Fix error handling in g_date_time_new_week()
It was possible to pass in (for example) an invalid year to
g_date_time_new_week(), which would be passed on to g_date_time_new(),
which would (correctly) return `NULL` — but then
g_date_time_get_week_number() would try to dereference that.

Includes a test case.

oss-fuzz#17648

Signed-off-by: Philip Withnall <withnall@endlessm.com>
2019-09-25 14:45:25 +01:00
Philip Withnall
c39f1b6e69 gdatetime: Fix error handling in g_date_time_new_ordinal()
It was possible to pass in (for example) an invalid hour to
g_date_time_new_ordinal(), which would be passed on to
g_date_time_new(), which would (correctly) return `NULL` — but then
g_date_time_new_ordinal() would try to dereference that.

Includes some test cases.

oss-fuzz#16103
oss-fuzz#17183

Signed-off-by: Philip Withnall <withnall@endlessm.com>
2019-09-25 14:45:21 +01:00
Philip Withnall
58f12912a9 Merge branch 'gobject-tutorial-no-priv-2-60' into 'glib-2-62'
docs: Remove priv pointers from the tutorial example

See merge request GNOME/glib!1021
2019-09-20 10:17:23 +00:00
Emmanuele Bassi
ad58fee969 docs: Remove priv pointers from the tutorial example
We define `ViewerFile` as a final type with fields directly in the
instance structure. This means we don't have a `priv` pointer to
dereference.
2019-09-20 11:40:33 +02:00