439 lines
16 KiB
Rust

mod vhdl;
#[allow(unused)]
const TESTFILES_DIR: &str = "testfiles";
#[allow(unused)]
const DIGTIAL_IDE_TEST: &str = "/home/dide/project/Digital-Test/Digital-IDE-test/user";
#[allow(unused)]
const MIPS_DESIGN_TEST: &str = "/home/dide/project/Digital-Test/MipsDesign";
#[allow(unused)]
const TEST_FILE: &str = "/home/dide/project/Digital-Test/MipsDesign/src/MyCpu.v";
#[allow(unused)]
const INCOMPLETE_EXAMPLE: &str = "/home/dide/project/Digital-Test/Digital-IDE-test/user/src/incomplete-example";
#[allow(unused)]
const TESTFILES_TEMP_DIR: &str = "/home/dide/project/Digital-Test/Digital-IDE-temp";
#[allow(unused)]
macro_rules! unwrap_result {
($expr:expr) => {
match $expr {
Ok(e) => e,
Err(_) => return
}
};
}
#[allow(unused)]
macro_rules! unwrap_option {
($expr:expr) => {
match $expr {
Some(e) => e,
None => return
}
};
}
#[cfg(test)]
mod test_fast {
use std::{env, fs, path::Path};
use crate::core::sv_parser::sv_parser;
use super::*;
#[test]
fn test_mycpu() {
let hdlparam = sv_parser("/home/dide/project/Digital-Test/Digital-IDE-test/user/src/svlog/tools/ivtest/undef.sv");
// println!("{hdlparam:?}");
assert!(hdlparam.is_some());
}
#[test]
fn test_parent() {
let fast = sv_parser("/home/dide/project/Digital-Test/Digital-IDE-temp/user/src/svlog/std2017/dependence/parent.sv");
let fast = fast.unwrap();
println!("{:#?}", fast.content);
}
#[test]
fn test_controller() {
let fast = sv_parser("/home/dide/project/Digital-Test/MipsDesign/src/Controller/controller.v");
let fast = fast.unwrap();
println!("{:#?}", fast.content[0].params);
}
#[test]
fn test_testfiles() {
let ws_path = env::current_dir().unwrap();
let entries = unwrap_result!(fs::read_dir(TESTFILES_DIR));
for entry in entries {
let entry = unwrap_result!(entry);
let file_path = entry.path();
if file_path.is_file() {
let extension = unwrap_option!(file_path.extension());
let file_path = unwrap_option!(file_path.to_str());
if extension == "v" || extension == "sv" {
let file_path = ws_path.join(file_path);
let file_path = file_path.to_str().unwrap();
println!("Test file: {:?}", file_path);
let _ = sv_parser(file_path);
}
}
}
}
// cargo test --release --package digital-lsp --lib -- test::test_fast::test_digital_ide_test --nocapture
#[test]
fn test_digital_ide_test() {
// 判断路径是否存在且为文件夹
let path = Path::new(DIGTIAL_IDE_TEST);
if path.exists() && path.is_dir() {
// 递归遍历文件夹
if let Err(e) = traverse_directory(path) {
eprintln!("Error: {}", e);
}
} else {
eprintln!("Path does not exist or is not a directory");
}
}
#[test]
fn test_mips_design() {
// 判断路径是否存在且为文件夹
let path = Path::new(MIPS_DESIGN_TEST);
if path.exists() && path.is_dir() {
// 递归遍历文件夹
if let Err(e) = traverse_directory(path) {
eprintln!("Error: {}", e);
}
} else {
eprintln!("Path does not exist or is not a directory");
}
}
#[test]
fn test_incomplete_example() {
let path = Path::new(INCOMPLETE_EXAMPLE);
if path.exists() && path.is_dir() {
// 递归遍历文件夹
if let Err(e) = traverse_directory(path) {
eprintln!("Error: {}", e);
}
} else {
eprintln!("Path does not exist or is not a directory");
}
}
fn traverse_directory(dir: &Path) -> Result<(), Box<dyn std::error::Error>> {
if dir.is_dir() {
for entry in fs::read_dir(dir)? {
let entry = entry?;
let path = entry.path();
if path.is_dir() {
// 递归遍历子文件夹
traverse_directory(&path)?;
} else if path.is_file() {
// 检查文件扩展名
if let Some(ext) = path.extension() {
if ext == "v" || ext == "sv" {
println!("Test file: {:?}", path);
// TODO: Check Stack Overflow tests
if path.to_str().unwrap() == "/home/dide/project/Digital-Test/Digital-IDE-test/user/src/svlog/tools/ivtest/comp1001.sv" {
continue;
}
if path.to_str().unwrap() == "/home/dide/project/Digital-Test/Digital-IDE-test/user/src/svlog/tools/ivtest/comp1000.sv" {
continue;
}
if path.to_str().unwrap() == "/home/dide/project/Digital-Test/Digital-IDE-test/user/src/svlog/tools/ivtest/br_gh330.sv" {
continue;
}
if path.to_str().unwrap() == "/home/dide/project/Digital-Test/Digital-IDE-test/user/src/svlog/tools/hdlconv/pri_encoder_using_assign.sv" {
continue;
}
if path.to_str().unwrap() == "/home/dide/project/Digital-Test/Digital-IDE-test/user/src/svlog/tools/ivtest/macro_with_args.sv" {
continue;
}
if path.to_str().unwrap() == "/home/dide/project/Digital-Test/Digital-IDE-test/user/src/vlog/element/macro.v" {
continue;
}
let file_path = path.to_str().unwrap();
let result = sv_parser(file_path);
assert!(result.is_some());
}
}
}
}
}
Ok(())
}
}
#[cfg(test)]
mod test_svparse {
use std::{fs, path::{Path, PathBuf}};
use ropey::Rope;
use tower_lsp::lsp_types::{Position, Range, Url};
use crate::sources::recovery_sv_parse;
use super::{INCOMPLETE_EXAMPLE, TEST_FILE};
#[test]
/// 测试单独的文件
fn test_mycpu() {
let includes: Vec<PathBuf> = Vec::new();
let path = TEST_FILE;
let text = match fs::read_to_string(path) {
Ok(text) => text,
Err(_) => return
};
let doc = Rope::from_str(&text);
let uri = Url::from_file_path(&path).unwrap();
let last_change_range = Range::new(
Position { line: 0, character: 0 },
Position { line: 0, character: 0 },
);
let result = recovery_sv_parse(&doc, &uri, &Some(last_change_range), &includes);
match result {
Some(syntax_tree) => {
println!("success");
println!("{:?}", syntax_tree);
},
None => {
eprintln!("gen None");
}
}
}
#[test]
/// 测试语法不完整的例子
fn test_incomplete_example() {
let path = Path::new(INCOMPLETE_EXAMPLE);
if path.exists() && path.is_dir() {
// 递归遍历文件夹
if let Err(e) = traverse_directory(path) {
eprintln!("Error: {}", e);
}
} else {
eprintln!("Path does not exist or is not a directory");
}
}
fn traverse_directory(dir: &Path) -> Result<(), Box<dyn std::error::Error>> {
if dir.is_dir() {
for entry in fs::read_dir(dir)? {
let entry = entry?;
let path = entry.path();
if path.is_dir() {
// 递归遍历子文件夹
traverse_directory(&path)?;
} else if path.is_file() {
// 检查文件扩展名
if let Some(ext) = path.extension() {
if ext == "v" || ext == "sv" {
println!("Test file: {:?}", path);
// TODO: Check Stack Overflow tests
if path.to_str().unwrap() == "/home/dide/project/Digital-Test/Digital-IDE-test/user/src/svlog/tools/ivtest/comp1001.sv" {
continue;
}
if path.to_str().unwrap() == "/home/dide/project/Digital-Test/Digital-IDE-test/user/src/svlog/tools/ivtest/comp1000.sv" {
continue;
}
if path.to_str().unwrap() == "/home/dide/project/Digital-Test/Digital-IDE-test/user/src/svlog/tools/ivtest/br_gh330.sv" {
continue;
}
if path.to_str().unwrap() == "/home/dide/project/Digital-Test/Digital-IDE-test/user/src/svlog/tools/hdlconv/pri_encoder_using_assign.sv" {
continue;
}
let file_path = path.to_str().unwrap();
let text = match fs::read_to_string(file_path) {
Ok(text) => text,
Err(_) => continue
};
let includes: Vec<PathBuf> = Vec::new();
let doc = Rope::from_str(&text);
let uri = Url::from_file_path(file_path).unwrap();
let result = recovery_sv_parse(&doc, &uri, &None, &includes);
assert!(result.is_some());
}
}
}
}
}
Ok(())
}
}
#[cfg(test)]
mod test_scope_tree {
use std::{fs, path::{Path, PathBuf}};
use crate::{definition::{get_scopes_from_syntax_tree, GenericScope}, sources::recovery_sv_parse};
use ropey::Rope;
use tower_lsp::lsp_types::Url;
use super::*;
fn get_scope_tree(file_path: &str) -> Option<GenericScope> {
let includes: Vec<PathBuf> = Vec::new();
let text = match fs::read_to_string(file_path) {
Ok(text) => text,
Err(_) => return None
};
let doc = Rope::from_str(&text);
let uri = Url::from_file_path(&file_path).unwrap();
let result = recovery_sv_parse(&doc, &uri, &None, &includes);
if let Some(syntax_tree) = result {
let file_url = format!("file://{}", file_path);
let uri = Url::parse(&file_url);
if let Ok(uri) = uri {
return get_scopes_from_syntax_tree(&syntax_tree, &uri);
} else {
eprintln!("error happen when unwrap uri: {:?}", uri);
return None;
}
}
None
}
#[test]
fn test_mycpu() {
let result = get_scope_tree(TEST_FILE);
if let Some(scope) = result {
println!("{:?}", scope);
} else {
panic!("error parsing");
}
}
#[test]
fn test_testfiles() {
let entries = unwrap_result!(fs::read_dir(TESTFILES_DIR));
for entry in entries {
let entry = unwrap_result!(entry);
let file_path = entry.path();
if file_path.is_file() {
let extension = unwrap_option!(file_path.extension());
let file_path = unwrap_option!(file_path.to_str());
if extension == "v" || extension == "sv" {
println!("Test file: {:?}", file_path);
let _ = get_scope_tree(file_path);
}
}
}
}
#[test]
fn test_digital_ide_test() {
// 判断路径是否存在且为文件夹
let path = Path::new(DIGTIAL_IDE_TEST);
if path.exists() && path.is_dir() {
// 递归遍历文件夹
if let Err(e) = traverse_directory(path) {
eprintln!("Error: {}", e);
}
} else {
eprintln!("Path does not exist or is not a directory");
}
}
#[test]
fn test_incomplete_example() {
let path = Path::new(INCOMPLETE_EXAMPLE);
if path.exists() && path.is_dir() {
// 递归遍历文件夹
if let Err(e) = traverse_directory(path) {
eprintln!("Error: {}", e);
}
} else {
eprintln!("Path does not exist or is not a directory");
}
}
fn traverse_directory(dir: &Path) -> Result<(), Box<dyn std::error::Error>> {
if dir.is_dir() {
for entry in fs::read_dir(dir)? {
let entry = entry?;
let path = entry.path();
if path.is_dir() {
// 递归遍历子文件夹
traverse_directory(&path)?;
} else if path.is_file() {
// 检查文件扩展名
if let Some(ext) = path.extension() {
if ext == "v" || ext == "sv" {
println!("Test file: {:?}", path);
// TODO: Check Stack Overflow tests
if path.to_str().unwrap() == "/home/dide/project/Digital-Test/Digital-IDE-test/user/src/svlog/tools/ivtest/comp1001.sv" {
continue;
}
if path.to_str().unwrap() == "/home/dide/project/Digital-Test/Digital-IDE-test/user/src/svlog/tools/ivtest/comp1000.sv" {
continue;
}
if path.to_str().unwrap() == "/home/dide/project/Digital-Test/Digital-IDE-test/user/src/svlog/tools/ivtest/br_gh330.sv" {
continue;
}
if path.to_str().unwrap() == "/home/dide/project/Digital-Test/Digital-IDE-test/user/src/svlog/tools/hdlconv/pri_encoder_using_assign.sv" {
continue;
}
let file_path = path.to_str().unwrap();
let scope = get_scope_tree(file_path);
assert!(scope.is_some());
}
}
}
}
}
Ok(())
}
}
#[cfg(test)]
mod test_file {
use std::fs;
use crate::utils::{file_size_in_kb, get_language_id_by_pathbuf, RecursiveFileIterator};
use super::*;
#[test]
fn test_big_file_detect() {
let file_iter = RecursiveFileIterator::new(DIGTIAL_IDE_TEST);
// 超过 1 MB 的文件,我们都认为是大文件
let threshold: u64 = 1024;
for pathbuf in file_iter {
let language_id = get_language_id_by_pathbuf(&pathbuf);
if language_id == "verilog" || language_id == "systemverilog" {
let size = file_size_in_kb(pathbuf.to_str().unwrap());
if let Ok(size) = size {
if size >= threshold {
println!("detect big file : {:?}, size: {}", pathbuf, size);
}
} else {
eprintln!("error to get size of {:?}", pathbuf);
}
}
}
}
#[test]
fn test_cache() {
let _ = fs::create_dir_all("/home/dide/project/digital-lsp-server/.cache");
}
}