Repository navigation
Expand file tree
/
Copy pathtest_kernel_0.py
More file actions
108 lines (85 loc) · 2.94 KB
/
Copy pathtest_kernel_0.py
File metadata and controls
108 lines (85 loc) · 2.94 KB
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
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
# <complete ModelNew code>
import torch
import torch.nn as nn
from torch.utils.cpp_extension import load_inline
# Define the custom CUDA kernel for matrix multiplication with shared memory tiling
source = """
#include <torch/extension.h>
#include <cuda_runtime.h>
#define TILE_SIZE 16
__global__ void matmul_kernel(const float* A, const float* B, float* C, int N) {
// Shared memory for tiles of A and B
__shared__ float As[TILE_SIZE][TILE_SIZE];
__shared__ float Bs[TILE_SIZE][TILE_SIZE];
int bx = blockIdx.x, by = blockIdx.y;
int tx = threadIdx.x, ty = threadIdx.y;
int row = by * TILE_SIZE + ty;
int col = bx * TILE_SIZE + tx;
float sum = 0.0f;
// Loop over tiles
for (int tile = 0; tile < (N + TILE_SIZE - 1) / TILE_SIZE; ++tile) {
// Load tile of A into shared memory
int a_row = row;
int a_col = tile * TILE_SIZE + tx;
if (a_row < N && a_col < N) {
As[ty][tx] = A[a_row * N + a_col];
} else {
As[ty][tx] = 0.0f;
}
// Load tile of B into shared memory
int b_row = tile * TILE_SIZE + ty;
int b_col = col;
if (b_row < N && b_col < N) {
Bs[ty][tx] = B[b_row * N + b_col];
} else {
Bs[ty][tx] = 0.0f;
}
__syncthreads();
// Compute partial dot product
for (int k = 0; k < TILE_SIZE; ++k) {
sum += As[ty][k] * Bs[k][tx];
}
__syncthreads();
}
// Write result to global memory
if (row < N && col < N) {
C[row * N + col] = sum;
}
}
torch::Tensor matmul_cuda(torch::Tensor A, torch::Tensor B) {
auto N = A.size(0);
auto C = torch::zeros({N, N}, A.options());
dim3 block_dim(TILE_SIZE, TILE_SIZE);
dim3 grid_dim((N + TILE_SIZE - 1) / TILE_SIZE, (N + TILE_SIZE - 1) / TILE_SIZE);
matmul_kernel<<<grid_dim, block_dim>>>(A.data_ptr<float>(), B.data_ptr<float>(), C.data_ptr<float>(), N);
return C;
}
"""
cpp_src = "torch::Tensor matmul_cuda(torch::Tensor A, torch::Tensor B);"
# Compile the inline CUDA code for matrix multiplication
matmul_op = load_inline(
name="matmul_custom",
cpp_sources=cpp_src,
cuda_sources=source,
functions=["matmul_cuda"],
verbose=False,
extra_cflags=[],
extra_ldflags=[],
)
class ModelNew(nn.Module):
"""
Optimized model that performs a single square matrix multiplication (C = A * B)
using a custom CUDA kernel with shared memory tiling.
"""
def __init__(self):
super(ModelNew, self).__init__()
def forward(self, A: torch.Tensor, B: torch.Tensor) -> torch.Tensor:
"""
Performs the matrix multiplication using a custom CUDA kernel.
Args:
A (torch.Tensor): Input matrix A of shape (N, N).
B (torch.Tensor): Input matrix B of shape (N, N).
Returns:
torch.Tensor: Output matrix C of shape (N, N).
"""
return matmul_op.matmul_cuda(A, B)