summaryrefslogtreecommitdiff
path: root/src/screen/drm/connector/mode.zig
blob: fb61b5b0df4bcce8ddd0c7f0c553cca12b3e6f50 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
pub const Mode = extern struct {
    const Self = @This();

    const DimensionInfo = extern struct {
        const Sync = extern struct { start: u16, end: u16 };

        size: u16,
        sync: Sync,
        total: u16,
    };

    const Type = packed struct(u32) {
        builtin: bool,
        clock_c: bool,
        crtc_c: bool,
        preferred: bool,
        default: bool,
        userdef: bool,
        driver: bool,
        _padding: u25,
    };

    const Flags = packed struct(u32) {
        phsync: bool,
        nhsync: bool,
        pvsync: bool,
        nvsync: bool,
        interlace: bool,
        dblscan: bool,
        csync: bool,
        pcsync: bool,
        ncsync: bool,
        hskew: bool,
        bcast: bool,
        pixmux: bool,
        dblclk: bool,
        clkdiv2: bool,
        _padding: u18,
    };

    clock: u32,
    horizontal: DimensionInfo,
    skew: u16,
    vertical: DimensionInfo,
    line_scans: u16,
    vertical_refresh: u32,

    flags: Flags,
    type: Type,
    name: [32]u8,

    pub fn frame_rate(self: *const Self) f32 {
        var rate = (@as(u64, @intCast(self.clock)) * 1000000 / self.horizontal.total + self.vertical.total / 2) / self.vertical.total;

        if (self.flags.interlace) {
            rate *= 2;
        }

        if (self.flags.dblscan) {
            rate /= 2;
        }

        if (self.line_scans > 1) {
            rate /= self.line_scans;
        }

        return @as(f32, @floatFromInt(rate)) / 1000.0;
    }
};