我写了一个应用程序来重现电影的矩阵数字雨。如果我将N_DROPS
设置为低数字 (5),它可以正常工作。如果我将其设置为 (10),字符开始闪烁,如果我将其设置为 15,则会出现段错误。我试图给你瓦尔格林德,但似乎我无法在我的MacOS 11.6.1上正确安装它。问题的根源是什么,我可以用打印语句诊断它,我该如何解决?
这是代码:
/*matrix_digital_rain.c*/
#include <curses.h>
#include <unistd.h>
#include <locale.h>
#include <time.h>
#include <stdlib.h>
#include <string.h>
#include "set_characters.h"
#include "hyperparameters.h"
#include "functions.h"
int main() {
srand((unsigned) time(NULL)); // Initialization, should only be called once.
setlocale(LC_ALL, "");
int max_y = 0, max_x = 0;
Drop_init_vals drop_init_vals_array[N_DROPS] ;
for (int drop_num = 0; drop_num < N_DROPS; drop_num++){
drop_init_vals_array[drop_num] = drop_init_vals_array_to_zero(drop_init_vals_array[drop_num]);
drop_init_vals_array[drop_num].rand_iter_start = rand() % ITER_START_RANGE;
}
int iter = 0;
initscr();
noecho();
curs_set(FALSE);
start_color();
init_color(CUSTOM_GREEN1, 90, 280, 90);
init_color(CUSTOM_GREEN2, 100, 500, 100);
init_color(CUSTOM_GREEN3, 100, 900, 100);
init_color(COLOR_BLACK, 0, 0, 0);
char char_set[DIM_1_ARRAY_STRING][BYTES_PER_CHAR] = {SET_CHAR};
char str_display[DIM_0_ARRAY_STRING][DIM_1_ARRAY_STRING][BYTES_PER_CHAR];
for (int i = 0; i<DIM_0_ARRAY_STRING; i++){
for (int j = 0; j<DIM_1_ARRAY_STRING; j++){
strcpy(str_display[i][j], char_set[rand() % N_COMMAS]);
}
}
while(1)
{
getmaxyx(stdscr, max_y, max_x);
clear();
for (int drop_num = 0; drop_num<N_DROPS; drop_num++){
if (iter % ITER_REFRESH == drop_init_vals_array[drop_num].rand_iter_start){
drop_init_vals_array[drop_num].n_dim_str = drop_num;
drop_init_vals_array[drop_num].x1 = rand() % X1_RANGE;
drop_init_vals_array[drop_num].n_string = 20 + rand() % N_STRING_RANGE;
drop_init_vals_array[drop_num].iter_init = iter;
drop_init_vals_array[drop_num].rand_iter_start_bool = 1;
}
if(drop_init_vals_array[drop_num].rand_iter_start_bool == 1){
print_n_string_from_string_array_struct(
drop_init_vals_array[drop_num],
str_display,
iter
);
if (iter == drop_init_vals_array[drop_num].iter_init + ITER_REFRESH){
drop_init_vals_array[drop_num].rand_iter_start_bool = 0;
}
}
}
iter++;
refresh();
usleep(DELAY);
}
attron(COLOR_PAIR(1));
attron(COLOR_PAIR(2));
attron(COLOR_PAIR(3));
endwin();
refresh();
use_default_colors();
}
/*functions.h*/
#ifndef FUNCTIONS_H
#define FUNCTIONS_H
typedef struct {
int x1, y1, n_string, n_dim_str, iter_init, rand_iter_start, rand_iter_start_bool;
} Drop_init_vals ;
void print_n_string_from_string_array_struct(Drop_init_vals drop_init_vals, char str_display[][DIM_1_ARRAY_STRING][BYTES_PER_CHAR], int iter);
Drop_init_vals random_drop_init_vals(Drop_init_vals drop_init_vals);
Drop_init_vals drop_init_vals_to_zero(void);
void print_GREEN1(int y1, int x1, int i, int n_string, int n_dim_str, char str_display[][DIM_1_ARRAY_STRING][BYTES_PER_CHAR]);
void print_GREEN2(int y1, int x1, int i, int n_string, int n_dim_str, char str_display[][DIM_1_ARRAY_STRING][BYTES_PER_CHAR]);
void print_GREEN3(int y1, int x1, int i, int n_string, int n_dim_str, char str_display[][DIM_1_ARRAY_STRING][BYTES_PER_CHAR]);
Drop_init_vals drop_init_vals_array_to_zero(Drop_init_vals drop_init_vals);
#endif
/*functions.c*/
#include "hyperparameters.h"
#include "functions.h"
#include <curses.h>
#include <time.h>
#include <stdlib.h>
void print_GREEN1(int y1, int x1, int i, int n_string, int n_dim_str, char str_display[][DIM_1_ARRAY_STRING][BYTES_PER_CHAR])
{
init_pair(1, CUSTOM_GREEN1, COLOR_BLACK);
attron(COLOR_PAIR(1));
mvprintw(y1+i-n_string, x1, str_display[n_dim_str][i]);
}
void print_GREEN2(int y1, int x1, int i, int n_string, int n_dim_str, char str_display[][DIM_1_ARRAY_STRING][BYTES_PER_CHAR])
{
init_pair(2, CUSTOM_GREEN2, COLOR_BLACK);
attron(COLOR_PAIR(2));
mvprintw(y1+i-n_string, x1, str_display[n_dim_str][i]);
}
void print_GREEN3(int y1, int x1, int i, int n_string, int n_dim_str, char str_display[][DIM_1_ARRAY_STRING][BYTES_PER_CHAR])
{
init_pair(3, CUSTOM_GREEN3, COLOR_BLACK);
attron(COLOR_PAIR(3));
mvprintw(y1+i-n_string, x1, str_display[n_dim_str][i]);
}
Drop_init_vals drop_init_vals_to_zero(void)
{
Drop_init_vals drop_init_vals;
drop_init_vals.y1 = 0;
drop_init_vals.x1 = 0;
drop_init_vals.n_string = 0;
drop_init_vals.iter_init = 0;
drop_init_vals.n_dim_str = 0;
return drop_init_vals;
}
Drop_init_vals random_drop_init_vals(Drop_init_vals drop_init_vals)
{
drop_init_vals.x1 = rand() % X1_RANGE;
drop_init_vals.n_string = 20 + rand() % N_STRING_RANGE;
return drop_init_vals;
}
void print_n_string_from_string_array_struct(Drop_init_vals drop_init_vals, char str_display[][DIM_1_ARRAY_STRING][BYTES_PER_CHAR], int iter)
{
int y1 = drop_init_vals.y1;
int x1 = drop_init_vals.x1;
int n_string = drop_init_vals.n_string;
int n_dim_str = drop_init_vals.n_dim_str;
int y_start = iter - drop_init_vals.iter_init;
int count = 0;
for (int i=y_start; i<y_start+n_string; i++)
{
if (count == 0 || count == 1){
print_GREEN1(y1, x1, i, n_string, n_dim_str, &str_display[n_dim_str]);
}
else if (count == 2 || count == 3 || count == 4){
print_GREEN2(y1, x1, i, n_string, n_dim_str, &str_display[n_dim_str]);
}
else{
print_GREEN3(y1, x1, i, n_string, n_dim_str, &str_display[n_dim_str]);
}
count++;
}
}
Drop_init_vals drop_init_vals_array_to_zero(Drop_init_vals drop_init_vals)
{
for (int drop_num = 0; drop_num < N_DROPS; drop_num++){
drop_init_vals.y1 = 0;
drop_init_vals.x1 = 0;
drop_init_vals.n_string = 0;
drop_init_vals.iter_init = 0;
drop_init_vals.n_dim_str = 0;
}
return drop_init_vals;
}
/*set_characters.h*/
#ifndef SET_CHARACTERS_H
#define SET_CHARACTERS_H
#define N_COMMAS 56
#define SET_CHAR "ㇰ", "ㇱ", "ㇲ","ㇳ","ㇴ","ㇵ","ㇶ","ㇷ","ㇸ","ㇹ","ㇺ","ㇻ","ㇼ","ㇽ","ㇾ", "+", ",", "-", ".", "/", "0", "1", "2", "3", "4", "5", "6", "7", "8", "9", "<", "=", ">", "T", "H","E", "M", "A", "T", "R", "I", "X", "Z", ":", "・", ".", "=", "*", "+", "-", "<", ">", "¦", "|", "#", "_"
#endif
/*hyperparameters.h*/
#ifndef HYPERPARAMETERS_H
#define HYPERPARAMETERS_H
#define DELAY 60000 //480000
#define CUSTOM_GREEN1 8
#define CUSTOM_GREEN2 9
#define CUSTOM_GREEN3 10
#define COLOR_BLACK 0
#define DIM_0_ARRAY_STRING 20
#define DIM_1_ARRAY_STRING 100
#define BYTES_PER_CHAR 5
#define LEN_STRING_DISPLAY 100
#define MAX_Y 100
#define MAX_X 100
#define N_STRING_MAX 20
#define N_DROPS 5
#define Y1_RANGE 20
#define X1_RANGE 30
#define N_STRING_RANGE 5
#define Y_START_RANGE 15
#define ITER_REFRESH 80
#define ITER_START_RANGE 80
#endif
#makefile
CC = gcc
CFLAGS = -O2 -Wextra -Wall -Wfloat-equal -Wundef -Wshadow -Wpointer-arith -Wcast-align -Wstrict-prototypes -Wstrict-overflow=5 -Wwrite-strings -Waggregate-return -Wcast-qual -Wswitch-default -Wswitch-enum -Wconversion -Wunreachable-code -pedantic -Wmissing-prototypes -Wstrict-prototypes -Wold-style-definition
BINC=matrix_digital_rain
allc: $(BINC)
$(BINC): $(BINC).o functions.o
$(CC) $(CFLAGS) -ggdb3 $(BINC).o functions.o -o $@ -lncurses
$(BINC).o: $(BINC).c set_characters.h hyperparameters.h set_characters.h
$(CC) $(CFLAGS) -c $(BINC).c
functions.o: functions.c functions.h
$(CC) $(CFLAGS) -c functions.c
clean:
$(RM) -rf $(BINC) *.dSYM *.o
runc: allc
./$(BINC)
编辑
因此,如评论中所述,我将-fsanitize=address,undefined
添加到编译中,并得到以下输出:
make runc
gcc -O2 -Wextra -Wall -Wfloat-equal -Wundef -Wshadow -Wpointer-arith -Wcast-align -Wstrict-prototypes -Wstrict-overflow=5 -Wwrite-strings -Waggregate-return -Wcast-qual -Wswitch-default -Wswitch-enum -Wconversion -Wunreachable-code -pedantic -Wmissing-prototypes -Wstrict-prototypes -Wold-style-definition -c functions.
ㇰ=en_US.UTF-8 2
S.UTF-8 ㇰ
-8 #
CURITYSESSIONID=186a6
YSESSIONID=186a6
IONID=186a6 /
=186a6 ㇺ
6
P_OPTIONS=--color=auto
IONS=--color=autoAddressSanitizer:DEADLYSIGNAL
=================================================================
==37477==ERROR: AddressSanitizer: stack-overflow on address 0x7ffeeac8d253 (pc 0x000104fe2d90 bp 0x7ffeeac882e0 sp 0x7ffeeac882e0 T0)
#0 0x104fe2d90 in __sanitizer::internal_strlen(char const*)+0x10 (libclang_rt.asan_osx_dynamic.dylib:x86_64h+0x5dd90)
#1 0x104fa7f75 in printf_common(void*, char const*, __va_list_tag*)+0x25 (libclang_rt.asan_osx_dynamic.dylib:x86_64h+0x22f75)
#2 0x104fa8a69 in wrap_vsnprintf+0x99 (libclang_rt.asan_osx_dynamic.dylib:x86_64h+0x23a69)
#3 0x7fff40e9c161 in _nc_printf_string+0xba (libncurses.5.4.dylib:x86_64+0x1d161)
#4 0x7fff40e93952 in vwprintw+0x13 (libncurses.5.4.dylib:x86_64+0x14952)
#5 0x7fff40e93abb in mvprintw+0xa7 (libncurses.5.4.dylib:x86_64+0x14abb)
#6 0x104f76765 in print_n_string_from_string_array_struct+0x255 (matrix_digital_rain:x86_64+0x100003765)
#7 0x104f75e5b in main+0x74b (matrix_digital_rain:x86_64+0x100002e5b)
#8 0x7fff20506f3c in start+0x0 (libdyld.dylib:x86_64+0x15f3c)
SUMMARY: AddressSanitizer: stack-overflow (libclang_rt.asan_osx_dynamic.dylib:x86_64h+0x5dd90) in __sanitizer::internal_strlen(char const*)+0x10
==37477==ABORTING
make: *** [runc] Abort trap: 6
编辑 2
我将以下内容添加到编译-O0 -ggdb
并得到以下输出:
make runc
gcc -O2 -Wextra -Wall -Wfloat-equal -Wundef -Wshadow -Wpointer-arith -Wcast-align -Wstrict-prototypes -Wstrict-overflow=5 -Wwrite-strings -Waggregate-return -Wcast-qual -Wswitch-default -Wswitch-enum -Wconversion -Wunreachable-code -pedantic -Wmissing-prototypes -Wstrict-prototypes -Wold-style-definition -c functions.
2 f2
=>0x1fffdca62250: f2 f2 f2 f2 f2[f2]f2 f2 f2 f2 f2 f2 f2 f2 f2 f2
0x1fffdca62260: f2 f2 f2 f2 f2 f2 f2 f2 00 00 00 04 f3 f3 f3 f3
0x1fffdca62270: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
0x1fffdca62280: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
0x1fffdca62290: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
0x1fffdca622a0: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
Shadow byte legend (one shadow byte represents 8 application bytes):
Addressable: 00
Partially addressable: 01 02 03 04 05 06 07
Heap left redzone: fa
Freed heap region: fd
Stack left redzone: f1
Stack mid redzone: f2
Stack right redzone: f3
Stack after return: f5
Stack use after scope: f8
Global redzone: f9
Global init order: f6
Poisoned by user: f7
Container overflow: fc
Array cookie: ac
Intra object redzone: bb
ASan internal: fe
Left alloca redzone: ca
Right alloca redzone: cb
Shadow gap: cc
==41647==ABORTING
make: *** [runc] Abort trap: 6
%
[@matrix_digital_rain]$
[@matrix_digital_rain]$
编辑
我试图实施@n.m.建议的更改,即:
- 我检查了是否N_DROPS> DIM_0_ARRAY_STRING,如果是这种情况,则使程序终止(脚本
matrix_digital_rain.c
的第 15-19 行)
if (N_DROPS > DIM_0_ARRAY_STRING)
{
printf("error N_DROPS should be equal or lower than DIM_0_ARRAY_STRING");
exit(EXIT_FAILURE);
}
- 我没有在
print_GREENX
和print_n_string_from_string_array_struct
中增加两次str_display(在脚本function.c
的第 64、68 和 72 行中)
不再有段错误(这是一个重大改进,非常感谢@n.m)但是,仍然有字符的闪烁。它与许多不同的mvprintw
陈述有关吗?
以下是完整编辑的代码:
/*matrix_digital_rain.c*/
#include <curses.h>
#include <unistd.h>
#include <locale.h>
#include <time.h>
#include <stdlib.h>
#include <string.h>
#include "set_characters.h"
#include "hyperparameters.h"
#include "functions.h"
int main() {
if (N_DROPS > DIM_0_ARRAY_STRING)
{
printf("error N_DROPS should be equal or lower than DIM_0_ARRAY_STRING");
exit(EXIT_FAILURE);
}
srand((unsigned) time(NULL)); // Initialization, should only be called once.
setlocale(LC_ALL, "");
int max_y = 0, max_x = 0;
Drop_init_vals drop_init_vals_array[N_DROPS] ;
for (int drop_num = 0; drop_num < N_DROPS; drop_num++){
drop_init_vals_array[drop_num] = drop_init_vals_array_to_zero(drop_init_vals_array[drop_num]);
drop_init_vals_array[drop_num].rand_iter_start = rand() % ITER_START_RANGE;
}
int iter = 0;
initscr();
noecho();
curs_set(FALSE);
start_color();
init_color(CUSTOM_GREEN1, 90, 280, 90);
init_color(CUSTOM_GREEN2, 100, 500, 100);
init_color(CUSTOM_GREEN3, 100, 900, 100);
init_color(COLOR_BLACK, 0, 0, 0);
char char_set[DIM_1_ARRAY_STRING][BYTES_PER_CHAR] = {SET_CHAR};
char str_display[DIM_0_ARRAY_STRING][DIM_1_ARRAY_STRING][BYTES_PER_CHAR];
for (int i = 0; i<DIM_0_ARRAY_STRING; i++){
for (int j = 0; j<DIM_1_ARRAY_STRING; j++){
strcpy(str_display[i][j], char_set[rand() % N_COMMAS]);
}
}
while(1)
{
getmaxyx(stdscr, max_y, max_x);
clear();
for (int drop_num = 0; drop_num<N_DROPS; drop_num++){
if (iter % ITER_REFRESH == drop_init_vals_array[drop_num].rand_iter_start){
drop_init_vals_array[drop_num].n_dim_str = drop_num;
drop_init_vals_array[drop_num].x1 = rand() % X1_RANGE;
drop_init_vals_array[drop_num].n_string = 20 + rand() % N_STRING_RANGE;
drop_init_vals_array[drop_num].iter_init = iter;
drop_init_vals_array[drop_num].rand_iter_start_bool = 1;
}
if(drop_init_vals_array[drop_num].rand_iter_start_bool == 1){
print_n_string_from_string_array_struct(
drop_init_vals_array[drop_num],
str_display,
iter
);
if (iter == drop_init_vals_array[drop_num].iter_init + ITER_REFRESH){
drop_init_vals_array[drop_num].rand_iter_start_bool = 0;
}
}
}
iter++;
refresh();
usleep(DELAY);
}
attron(COLOR_PAIR(1));
attron(COLOR_PAIR(2));
attron(COLOR_PAIR(3));
endwin();
refresh();
use_default_colors();
}
/*functions.h*/
#ifndef FUNCTIONS_H
#define FUNCTIONS_H
typedef struct {
int x1, y1, n_string, n_dim_str, iter_init, rand_iter_start, rand_iter_start_bool;
} Drop_init_vals ;
void print_n_string_from_string_array_struct(Drop_init_vals drop_init_vals, char str_display[][DIM_1_ARRAY_STRING][BYTES_PER_CHAR], int iter);
Drop_init_vals random_drop_init_vals(Drop_init_vals drop_init_vals);
Drop_init_vals drop_init_vals_to_zero(void);
void print_GREEN1(int y1, int x1, int i, int n_string, int n_dim_str, char str_display[][DIM_1_ARRAY_STRING][BYTES_PER_CHAR]);
void print_GREEN2(int y1, int x1, int i, int n_string, int n_dim_str, char str_display[][DIM_1_ARRAY_STRING][BYTES_PER_CHAR]);
void print_GREEN3(int y1, int x1, int i, int n_string, int n_dim_str, char str_display[][DIM_1_ARRAY_STRING][BYTES_PER_CHAR]);
Drop_init_vals drop_init_vals_array_to_zero(Drop_init_vals drop_init_vals);
#endif
/*functions.c*/
#include "hyperparameters.h"
#include "functions.h"
#include <curses.h>
#include <time.h>
#include <stdlib.h>
void print_GREEN1(int y1, int x1, int i, int n_string, int n_dim_str, char str_display[][DIM_1_ARRAY_STRING][BYTES_PER_CHAR])
{
init_pair(1, CUSTOM_GREEN1, COLOR_BLACK);
attron(COLOR_PAIR(1));
mvprintw(y1+i-n_string, x1, str_display[n_dim_str][i]);
}
void print_GREEN2(int y1, int x1, int i, int n_string, int n_dim_str, char str_display[][DIM_1_ARRAY_STRING][BYTES_PER_CHAR])
{
init_pair(2, CUSTOM_GREEN2, COLOR_BLACK);
attron(COLOR_PAIR(2));
mvprintw(y1+i-n_string, x1, str_display[n_dim_str][i]);
}
void print_GREEN3(int y1, int x1, int i, int n_string, int n_dim_str, char str_display[][DIM_1_ARRAY_STRING][BYTES_PER_CHAR])
{
init_pair(3, CUSTOM_GREEN3, COLOR_BLACK);
attron(COLOR_PAIR(3));
mvprintw(y1+i-n_string, x1, str_display[n_dim_str][i]);
}
Drop_init_vals drop_init_vals_to_zero(void)
{
Drop_init_vals drop_init_vals;
drop_init_vals.y1 = 0;
drop_init_vals.x1 = 0;
drop_init_vals.n_string = 0;
drop_init_vals.iter_init = 0;
drop_init_vals.n_dim_str = 0;
return drop_init_vals;
}
Drop_init_vals random_drop_init_vals(Drop_init_vals drop_init_vals)
{
drop_init_vals.x1 = rand() % X1_RANGE;
drop_init_vals.n_string = 20 + rand() % N_STRING_RANGE;
return drop_init_vals;
}
void print_n_string_from_string_array_struct(Drop_init_vals drop_init_vals, char str_display[][DIM_1_ARRAY_STRING][BYTES_PER_CHAR], int iter)
{
int y1 = drop_init_vals.y1;
int x1 = drop_init_vals.x1;
int n_string = drop_init_vals.n_string;
int n_dim_str = drop_init_vals.n_dim_str;
int y_start = iter - drop_init_vals.iter_init;
int count = 0;
for (int i=y_start; i<y_start+n_string; i++)
{
if (count == 0 || count == 1){
//print_GREEN1(y1, x1, i, n_string, n_dim_str, &str_display[n_dim_str]);
print_GREEN1(y1, x1, i, n_string, n_dim_str, str_display);
}
else if (count == 2 || count == 3 || count == 4){
//print_GREEN2(y1, x1, i, n_string, n_dim_str, &str_display[n_dim_str]);
print_GREEN2(y1, x1, i, n_string, n_dim_str, str_display);
}
else{
//print_GREEN3(y1, x1, i, n_string, n_dim_str, &str_display[n_dim_str]);
print_GREEN3(y1, x1, i, n_string, n_dim_str, str_display);
}
count++;
}
}
Drop_init_vals drop_init_vals_array_to_zero(Drop_init_vals drop_init_vals)
{
for (int drop_num = 0; drop_num < N_DROPS; drop_num++){
drop_init_vals.y1 = 0;
drop_init_vals.x1 = 0;
drop_init_vals.n_string = 0;
drop_init_vals.iter_init = 0;
drop_init_vals.n_dim_str = 0;
}
return drop_init_vals;
}
/*set_characters.h*/
#ifndef SET_CHARACTERS_H
#define SET_CHARACTERS_H
#define N_COMMAS 56
#define SET_CHAR "ㇰ", "ㇱ", "ㇲ","ㇳ","ㇴ","ㇵ","ㇶ","ㇷ","ㇸ","ㇹ","ㇺ","ㇻ","ㇼ","ㇽ","ㇾ", "+", ",", "-", ".", "/", "0", "1", "2", "3", "4", "5", "6", "7", "8", "9", "<", "=", ">", "T", "H","E", "M", "A", "T", "R", "I", "X", "Z", ":", "・", ".", "=", "*", "+", "-", "<", ">", "¦", "|", "#", "_"
#endif
/*hyperparameters.h*/
#ifndef HYPERPARAMETERS_H
#define HYPERPARAMETERS_H
#define DELAY 60000 //480000
#define CUSTOM_GREEN1 8
#define CUSTOM_GREEN2 9
#define CUSTOM_GREEN3 10
#define COLOR_BLACK 0
#define DIM_0_ARRAY_STRING 30
#define DIM_1_ARRAY_STRING 100
#define BYTES_PER_CHAR 5
#define LEN_STRING_DISPLAY 100
#define MAX_Y 100
#define MAX_X 100
#define N_STRING_MAX 20
#define N_DROPS 20
#define Y1_RANGE 20
#define X1_RANGE 50
#define N_STRING_RANGE 5
#define Y_START_RANGE 15
#define ITER_REFRESH 80
#define ITER_START_RANGE 80
#endif
#makefile
CC = gcc
CFLAGS = -O2 -Wextra -Wall -Wfloat-equal -Wundef -Wshadow -Wpointer-arith -Wcast-align -Wstrict-prototypes -Wstrict-overflow=5 -Wwrite-strings -Waggregate-return -Wcast-qual -Wswitch-default -Wswitch-enum -Wconversion -Wunreachable-code -pedantic -Wmissing-prototypes -Wstrict-prototypes -Wold-style-definition -fsanitize=address,undefined -O0 -ggdb
BINC=matrix_digital_rain
allc: $(BINC)
$(BINC): $(BINC).o functions.o
$(CC) $(CFLAGS) -ggdb3 $(BINC).o functions.o -o $@ -lncurses
$(BINC).o: $(BINC).c set_characters.h hyperparameters.h set_characters.h
$(CC) $(CFLAGS) -c $(BINC).c
functions.o: functions.c functions.h
$(CC) $(CFLAGS) -c functions.c
clean:
$(RM) -rf $(BINC) *.dSYM *.o
runc: allc
./$(BINC)
# ./$(BINC) >/dev/null
你打电话
print_GREEN1(y1, x1, i, n_string, n_dim_str, &str_display[n_dim_str]);
和内部print_GREEN1
mvprintw(y1+i-n_string, x1, str_display[n_dim_str][i]);
因此,您将n_dim_str
添加到str_display
两次,这会溢出数组。您可能只想尝试一次。
此外,您的数组大小是DIM_0_ARRAY_STRING
,并且n_dim_str
受到独立设置N_DROPS
的限制。您可能应该检查N_DROPS
不超过DIM_0_ARRAY_STRING
。
最后一个错误是未重新初始化的drop_init_vals_array[drop_num]
的值,我在脚本matrix_digital_rain.c
的第73行添加了以下值:
drop_init_vals_array[drop_num] = drop_init_vals_array_to_zero(drop_init_vals_array[drop_num]);
这是最终的工作代码:
/*matrix_digital_rain.c*/
#include <curses.h>
#include <unistd.h>
#include <locale.h>
#include <time.h>
#include <stdlib.h>
#include <string.h>
#include "set_characters.h"
#include "hyperparameters.h"
#include "functions.h"
#include "test.h"
int main() {
test_N_DROPS_more_than_DIM_0_ARRAY_STRING();
srand((unsigned) time(NULL)); // Initialization, should only be called once.
setlocale(LC_ALL, "");
int max_y = 0, max_x = 0;
Drop_init_vals drop_init_vals_array[N_DROPS] ;
for (int drop_num = 0; drop_num < N_DROPS; drop_num++){
drop_init_vals_array[drop_num] = drop_init_vals_array_to_zero(drop_init_vals_array[drop_num]);
drop_init_vals_array[drop_num].rand_iter_start = rand() % ITER_START_RANGE;
}
int iter = 0;
initscr();
noecho();
curs_set(FALSE);
start_color();
init_color(CUSTOM_GREEN1, 90, 280, 90);
init_color(CUSTOM_GREEN2, 100, 500, 100);
init_color(CUSTOM_GREEN3, 100, 900, 100);
init_color(COLOR_BLACK, 0, 0, 0);
char char_set[DIM_1_ARRAY_STRING][BYTES_PER_CHAR] = {SET_CHAR};
char str_display[DIM_0_ARRAY_STRING][DIM_1_ARRAY_STRING][BYTES_PER_CHAR];
for (int i = 0; i<DIM_0_ARRAY_STRING; i++){
for (int j = 0; j<DIM_1_ARRAY_STRING; j++){
strcpy(str_display[i][j], char_set[rand() % N_COMMAS]);
}
}
while(1)
{
getmaxyx(stdscr, max_y, max_x);
//clear();
erase();
for (int drop_num = 0; drop_num<N_DROPS; drop_num++){
if (iter % ITER_REFRESH == drop_init_vals_array[drop_num].rand_iter_start){
drop_init_vals_array[drop_num].n_dim_str = drop_num;
drop_init_vals_array[drop_num].x1 = rand() % X1_RANGE;
drop_init_vals_array[drop_num].n_string = 20 + rand() % N_STRING_RANGE;
drop_init_vals_array[drop_num].iter_init = iter;
drop_init_vals_array[drop_num].rand_iter_start_bool = 1;
}
if(drop_init_vals_array[drop_num].rand_iter_start_bool == 1){
print_n_string_from_string_array_struct(
drop_init_vals_array[drop_num],
str_display,
iter
);
if (iter == drop_init_vals_array[drop_num].iter_init + ITER_REFRESH){
drop_init_vals_array[drop_num].rand_iter_start_bool = 0;
drop_init_vals_array[drop_num] = drop_init_vals_array_to_zero(drop_init_vals_array[drop_num]);
}
}
}
iter++;
refresh();
usleep(DELAY);
}
attron(COLOR_PAIR(1));
attron(COLOR_PAIR(2));
attron(COLOR_PAIR(3));
endwin();
refresh();
use_default_colors();
}
/*functions.h*/
#ifndef FUNCTIONS_H
#define FUNCTIONS_H
typedef struct {
int x1, y1, n_string, n_dim_str, iter_init, rand_iter_start, rand_iter_start_bool;
} Drop_init_vals ;
void print_n_string_from_string_array_struct(Drop_init_vals drop_init_vals, char str_display[][DIM_1_ARRAY_STRING][BYTES_PER_CHAR], int iter);
Drop_init_vals random_drop_init_vals(Drop_init_vals drop_init_vals);
Drop_init_vals drop_init_vals_to_zero(void);
void print_GREEN1(int y1, int x1, int i, int n_string, int n_dim_str, char str_display[][DIM_1_ARRAY_STRING][BYTES_PER_CHAR]);
void print_GREEN2(int y1, int x1, int i, int n_string, int n_dim_str, char str_display[][DIM_1_ARRAY_STRING][BYTES_PER_CHAR]);
void print_GREEN3(int y1, int x1, int i, int n_string, int n_dim_str, char str_display[][DIM_1_ARRAY_STRING][BYTES_PER_CHAR]);
Drop_init_vals drop_init_vals_array_to_zero(Drop_init_vals drop_init_vals);
#endif
/*functions.c*/
#include "hyperparameters.h"
#include "functions.h"
#include "test.h"
#include <curses.h>
#include <time.h>
#include <stdlib.h>
void print_GREEN1(int y1, int x1, int i, int n_string, int n_dim_str, char str_display[][DIM_1_ARRAY_STRING][BYTES_PER_CHAR])
{
n_dim_str_morethan_DIM_0_ARRAY_STRING(n_dim_str);
i_morethan_DIM_1_ARRAY_STRING(i);
init_pair(1, CUSTOM_GREEN1, COLOR_BLACK);
attron(COLOR_PAIR(1));
mvprintw(y1+i-n_string, x1, str_display[n_dim_str][i]);
}
void print_GREEN2(int y1, int x1, int i, int n_string, int n_dim_str, char str_display[][DIM_1_ARRAY_STRING][BYTES_PER_CHAR])
{
n_dim_str_morethan_DIM_0_ARRAY_STRING(n_dim_str);
i_morethan_DIM_1_ARRAY_STRING(i);
init_pair(2, CUSTOM_GREEN2, COLOR_BLACK);
attron(COLOR_PAIR(2));
mvprintw(y1+i-n_string, x1, str_display[n_dim_str][i]);
}
void print_GREEN3(int y1, int x1, int i, int n_string, int n_dim_str, char str_display[][DIM_1_ARRAY_STRING][BYTES_PER_CHAR])
{
n_dim_str_morethan_DIM_0_ARRAY_STRING(n_dim_str);
i_morethan_DIM_1_ARRAY_STRING(i);
init_pair(3, CUSTOM_GREEN3, COLOR_BLACK);
attron(COLOR_PAIR(3));
mvprintw(y1+i-n_string, x1, str_display[n_dim_str][i]);
}
Drop_init_vals random_drop_init_vals(Drop_init_vals drop_init_vals)
{
drop_init_vals.x1 = rand() % X1_RANGE;
drop_init_vals.n_string = 20 + rand() % N_STRING_RANGE;
return drop_init_vals;
}
void print_n_string_from_string_array_struct(Drop_init_vals drop_init_vals, char str_display[][DIM_1_ARRAY_STRING][BYTES_PER_CHAR], int iter)
{
int y1 = drop_init_vals.y1;
int x1 = drop_init_vals.x1;
int n_string = drop_init_vals.n_string;
int n_dim_str = drop_init_vals.n_dim_str;
int y_start = iter - drop_init_vals.iter_init;
int count = 0;
for (int i=y_start; i<y_start+n_string; i++)
{
if (count == 0 || count == 1){
print_GREEN1(y1, x1, i, n_string, n_dim_str, str_display);
}
else if (count == 2 || count == 3 || count == 4){
print_GREEN2(y1, x1, i, n_string, n_dim_str, str_display);
}
else{
print_GREEN3(y1, x1, i, n_string, n_dim_str, str_display);
}
count++;
}
}
Drop_init_vals drop_init_vals_array_to_zero(Drop_init_vals drop_init_vals)
{
for (int drop_num = 0; drop_num < N_DROPS; drop_num++){
drop_init_vals.y1 = 0;
drop_init_vals.x1 = 0;
drop_init_vals.n_string = 0;
drop_init_vals.iter_init = 0;
drop_init_vals.n_dim_str = 0;
}
return drop_init_vals;
}
/*set_characters.h*/
#ifndef SET_CHARACTERS_H
#define SET_CHARACTERS_H
#define N_COMMAS 56
#define SET_CHAR "ㇰ", "ㇱ", "ㇲ","ㇳ","ㇴ","ㇵ","ㇶ","ㇷ","ㇸ","ㇹ","ㇺ","ㇻ","ㇼ","ㇽ","ㇾ", "+", ",", "-", ".", "/", "0", "1", "2", "3", "4", "5", "6", "7", "8", "9", "<", "=", ">", "T", "H","E", "M", "A", "T", "R", "I", "X", "Z", ":", "・", ".", "=", "*", "+", "-", "<", ">", "¦", "|", "#", "_"
#endif
/*hyperparameters.h*/
#ifndef HYPERPARAMETERS_H
#define HYPERPARAMETERS_H
#define DELAY 60000 //480000
#define CUSTOM_GREEN1 8
#define CUSTOM_GREEN2 9
#define CUSTOM_GREEN3 10
#define COLOR_BLACK 0
#define DIM_0_ARRAY_STRING 30
#define DIM_1_ARRAY_STRING 150
#define BYTES_PER_CHAR 5
#define LEN_STRING_DISPLAY 100
#define MAX_Y 100
#define MAX_X 100
#define N_STRING_MAX 20
#define N_DROPS 20
#define Y1_RANGE 20
#define X1_RANGE 50
#define N_STRING_RANGE 5
#define Y_START_RANGE 15
#define ITER_REFRESH 80
#define ITER_START_RANGE 80
#endif
#makefile
CC = gcc
CFLAGS = -O2 -Wextra -Wall -Wfloat-equal -Wundef -Wshadow -Wpointer-arith -Wcast-align -Wstrict-prototypes -Wstrict-overflow=5 -Wwrite-strings -Waggregate-return -Wcast-qual -Wswitch-default -Wswitch-enum -Wconversion -Wunreachable-code -pedantic -Wmissing-prototypes -Wstrict-prototypes -Wold-style-definition -fsanitize=address,undefined -O0 -ggdb
BINC=matrix_digital_rain
allc: $(BINC)
$(BINC): $(BINC).o functions.o test.o
$(CC) $(CFLAGS) -ggdb3 $(BINC).o functions.o test.o -o $@ -lncurses
$(BINC).o: $(BINC).c set_characters.h hyperparameters.h set_characters.h
$(CC) $(CFLAGS) -c $(BINC).c
functions.o: functions.c functions.h
$(CC) $(CFLAGS) -c functions.c
test.o: test.c test.h
$(CC) $(CFLAGS) -c test.c
clean:
$(RM) -rf $(BINC) *.dSYM *.o
runc: allc
./$(BINC)
# ./$(BINC) >/dev/null