aboutsummaryrefslogtreecommitdiffstats
path: root/device_info_procfs.c
diff options
context:
space:
mode:
Diffstat (limited to 'device_info_procfs.c')
-rw-r--r--device_info_procfs.c43
1 files changed, 24 insertions, 19 deletions
diff --git a/device_info_procfs.c b/device_info_procfs.c
index d5350c8..168905f 100644
--- a/device_info_procfs.c
+++ b/device_info_procfs.c
@@ -9,7 +9,7 @@
9// @param off Requested offset. Updated by number of characters written. 9// @param off Requested offset. Updated by number of characters written.
10// @return -errno on error, otherwise number of bytes written to *buf 10// @return -errno on error, otherwise number of bytes written to *buf
11// Note: Parent `data` field MUST be the GPU index 11// Note: Parent `data` field MUST be the GPU index
12static ssize_t nvdebug_reg32_read(struct file *f, char __user *buf, size_t size, loff_t *off){ 12static ssize_t nvdebug_reg32_read(struct file *f, char __user *buf, size_t size, loff_t *off) {
13 char out[16]; 13 char out[16];
14 int chars_written; 14 int chars_written;
15 struct nvdebug_state *g = &g_nvdebug_state[file2parentgpuidx(f)]; 15 struct nvdebug_state *g = &g_nvdebug_state[file2parentgpuidx(f)];
@@ -22,37 +22,42 @@ static ssize_t nvdebug_reg32_read(struct file *f, char __user *buf, size_t size,
22 *off += chars_written; 22 *off += chars_written;
23 return chars_written; 23 return chars_written;
24} 24}
25static ssize_t nvdebug_read4_pascal(struct file *f, char __user *buf, size_t size, loff_t *off){ 25
26 char out[16]; 26static ssize_t nvdebug_reg_range_read(struct file *f, char __user *buf, size_t size, loff_t *off) {
27 char out[12];
27 int chars_written; 28 int chars_written;
29 uint32_t read, mask;
28 struct nvdebug_state *g = &g_nvdebug_state[file2parentgpuidx(f)]; 30 struct nvdebug_state *g = &g_nvdebug_state[file2parentgpuidx(f)];
29 void* data = PDE_DATA(file_inode(f)); 31 // See comment in nvdebug_entry.c to understand `union reg_range`
30 struct combo local_combo = *(struct combo*) &data; 32 union reg_range range;
33 range.raw = (uintptr_t)PDE_DATA(file_inode(f));
31 34
32 // 32 bit register will always take less than 16 characters to print 35 // "0x" + up to 32-bit register as hex + "\n\0" is at most 12 characters
33 if (size < 16 || *off != 0) 36 if (size < 12 || *off != 0)
34 return 0; 37 return 0;
35 if (local_combo.index % 2 == 0) 38
36 chars_written = scnprintf(out, 16, "%#0x\n", (nvdebug_readl(g, local_combo.offset) & 0x0f)); 39 // Print bits `start_bit` to `stop_bit` from 32 bits at address `offset`
37 else 40 if ((read = nvdebug_readl(g, range.offset)) == -1)
38 chars_written = scnprintf(out, 16, "%#0x\n", (nvdebug_readl(g, local_combo.offset) & 0xf0) >> 4); 41 return -EOPNOTSUPP;
42 // Setup `mask` used to throw out unused upper bits
43 mask = -1u >> (32 - range.stop_bit + range.start_bit);
44 // Throw out unused lower bits via a shift, apply the mask, and print
45 chars_written = scnprintf(out, 12, "%#0x\n", (read >> range.start_bit) & mask);
39 if (copy_to_user(buf, out, chars_written)) 46 if (copy_to_user(buf, out, chars_written))
40 printk(KERN_WARNING "Unable to copy all data for %s\n", file_dentry(f)->d_name.name); 47 printk(KERN_WARNING "Unable to copy all data for %s\n", file_dentry(f)->d_name.name);
41 *off += chars_written; 48 *off += chars_written;
42 return chars_written; 49 return chars_written;
43
44//(nvdebug_readl(g,NV_LCE_FOR_PCE_GP100(*(int*)PDE_DATA(file_inode(f))))
45
46
47
48} 50}
51
49struct file_operations nvdebug_read_reg32_file_ops = { 52struct file_operations nvdebug_read_reg32_file_ops = {
50 .read = nvdebug_reg32_read, 53 .read = nvdebug_reg32_read,
51 .llseek = default_llseek, 54 .llseek = default_llseek,
52}; 55};
53// File operation for reading 4 bits in 32 bit register (used for Pascal copy engine offsets) 56
54struct file_operations nvdebug_read4_pascal_file_ops = { 57// Generic mechanism used for printing a subset of bits from a register
55 .read = nvdebug_read4_pascal, 58// Please store a `union reg_range` rather than a `uintptr_t` in the PDE_DATA
59struct file_operations nvdebug_read_reg_range_file_ops = {
60 .read = nvdebug_reg_range_read,
56 .llseek = default_llseek, 61 .llseek = default_llseek,
57}; 62};
58 63