⬢ DragonFlyBSD Kernel Audit
DF-3682 / gtf_fix_test.c
← back to finding ↓ download raw
/*
 * gtf_fix_test.c — same verbatim extraction as gtf_kernel_extract.c,
 * but with the proposed fix.diff guard applied to the extracted body:
 *
 *   if (ideal_duty_cycle <= 0 || ideal_duty_cycle >= 100000) {
 *           kfree(drm_mode);
 *           return NULL;
 *   }
 *
 * (drm_mode_destroy() is drm_modes.c-internal cleanup; in userland we free.)
 *
 * Expected: NO trap; function returns NULL; caller prints "fix OK".
 */
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <stdbool.h>

#define u64 unsigned long long
#define DRM_MODE_FLAG_NHSYNC		(1 << 0)
#define DRM_MODE_FLAG_PVSYNC		(1 << 1)
#define DRM_MODE_FLAG_INTERLACE		(1 << 4)
#define DRM_MODE_FLAG_PHSYNC		(1 << 2)
#define DRM_MODE_FLAG_NVSYNC		(1 << 3)
struct drm_device { int dummy; };
struct drm_display_mode {
	int hdisplay, hsync_start, hsync_end, htotal;
	int vdisplay, vsync_start, vsync_end, vtotal;
	int clock, vrefresh;
	unsigned int flags;
	int hsync;
};
static struct drm_display_mode *drm_mode_create(struct drm_device *dev)
{
	return calloc(1, sizeof(struct drm_display_mode));
}
static void drm_mode_set_name(struct drm_display_mode *mode) { }

static struct drm_device dev;

/* ==== VERBATIM BODY WITH FIX GUARD ==== */
#include "gtf_body_fixed.inc"
/* ==== END ==== */

#define do_div(n, base) do { u64 __b = (base); (n) /= __b; } while (0)

static volatile unsigned char edid_dtd[18] = {
	0, 0, 0, 0xFD, 0, 0, 0, 0, 0, 0,
	0x02, 0x00, 0x01, 200, 0x00, 0x00, 128, 200
};
static volatile int std_timing[2] = { 208, 0x00 };

int main(void)
{
	int hsize = std_timing[0] * 8 + 248;
	int vsize = (hsize * 10) / 16;
	int vrefresh = (std_timing[1] & 0x3f) + 60;
	int M  = (edid_dtd[15] << 8) + edid_dtd[14];
	int C2 = edid_dtd[13];
	int K  = edid_dtd[16];
	int J2 = edid_dtd[17];
	void *r;

	printf("crafted EDID decodes to: %dx%d@%d  M=%d 2C=%d K=%d 2J=%d\n",
	       hsize, vsize, vrefresh, M, C2, K, J2);
	fflush(stdout);

	r = (void *)(unsigned long)drm_gtf_mode_complex(&dev, hsize, vsize, vrefresh, 0, 0, M, C2, K, J2);
	printf("returned %s -> fix OK (no trap)\n", r ? "mode" : "NULL (rejected bogus GTF2 params)");
	return 0;
}