17 Commits
1.3.1 ... 1.3.2

8 changed files with 225 additions and 30 deletions

View File

@@ -53,12 +53,18 @@ jobs:
- name: Build - name: Build
run: cmake --build ${{ env.BUILD_PATH }} -j 4 --config ${{ env.BUILD_TYPE }} run: cmake --build ${{ env.BUILD_PATH }} -j 4 --config ${{ env.BUILD_TYPE }}
- name: Upload artifact - name: Upload artifact executable
uses: actions/upload-artifact@v4 uses: actions/upload-artifact@v4
with: with:
name: Windows amd64 Build - MSVC name: Windows amd64 Build - MSVC
path: ${{ env.BUILD_PATH }}/${{ env.BUILD_TYPE }}/ncmdump.exe path: ${{ env.BUILD_PATH }}/${{ env.BUILD_TYPE }}/ncmdump.exe
- name: Upload artifact DLL
uses: actions/upload-artifact@v4
with:
name: Windows amd64 Build - MSVC DLL
path: ${{ env.BUILD_PATH }}/${{ env.BUILD_TYPE }}/libncmdump.dll
build_on_linux: build_on_linux:
runs-on: ubuntu-latest runs-on: ubuntu-latest

View File

@@ -14,38 +14,73 @@ if(MSVC)
add_compile_options("$<$<CXX_COMPILER_ID:MSVC>:/execution-charset:utf-8>") add_compile_options("$<$<CXX_COMPILER_ID:MSVC>:/execution-charset:utf-8>")
endif() endif()
FILE(GLOB HEADERS ./src/include/*.h) FILE(GLOB COMMON_HEADERS src/include/*.h)
FILE(GLOB COMMON_SOURCES ./src/*.cpp ./src/utils/*.cpp) FILE(GLOB COMMON_SOURCES src/ncmcrypt.cpp src/utils/*.cpp)
FILE(GLOB WIN_SOURCES ./src/platform/win32_init.cpp) FILE(GLOB EXECUTABLE_SOURCES src/main.cpp)
FILE(GLOB LIBRARY_HEADERS src/lib/libncmdump.h)
FILE(GLOB LIBRARY_SOURCES src/lib/*.cpp)
FILE(GLOB WIN_SOURCES src/platform/win32_init.cpp)
if(WIN32) if(WIN32)
set(SOURCES ${COMMON_SOURCES} ${WIN_SOURCES}) add_executable(ncmdump_exec
else() ${COMMON_HEADERS}
set(SOURCES ${COMMON_SOURCES}) ${COMMON_SOURCES}
endif() ${EXECUTABLE_SOURCES}
add_executable(ncmdump ${WIN_SOURCES}
${HEADERS} )
${SOURCES} add_library(ncmdump_lib SHARED
${COMMON_HEADERS}
${COMMON_SOURCES}
${LIBRARY_HEADERS}
${LIBRARY_SOURCES}
${WIN_SOURCES}
) )
target_include_directories(ncmdump PRIVATE src/include) set_target_properties(ncmdump_lib PROPERTIES OUTPUT_NAME "libncmdump")
target_link_libraries(ncmdump tag) target_include_directories(ncmdump_lib PRIVATE src/include)
target_include_directories(ncmdump PRIVATE taglib)
target_include_directories(ncmdump PRIVATE taglib/taglib) target_link_libraries(ncmdump_lib tag)
target_include_directories(ncmdump PRIVATE taglib/taglib/toolkit) target_include_directories(ncmdump_lib PRIVATE taglib)
target_include_directories(ncmdump PRIVATE taglib/taglib/mpeg/id3v2) target_include_directories(ncmdump_lib PRIVATE taglib/taglib)
target_include_directories(ncmdump_lib PRIVATE taglib/taglib/toolkit)
target_include_directories(ncmdump_lib PRIVATE taglib/taglib/mpeg/id3v2)
if(WIN32)
if(CMAKE_COMPILER_IS_GNUCXX) if(CMAKE_COMPILER_IS_GNUCXX)
target_link_options(ncmdump PRIVATE -static) # static link when using MinGW
target_link_options(ncmdump_exec PRIVATE -static)
target_link_options(ncmdump_lib PRIVATE -static)
endif() endif()
else()
add_executable(ncmdump_exec
${COMMON_HEADERS}
${COMMON_SOURCES}
${EXECUTABLE_SOURCES}
)
endif() endif()
# all executable target
set_target_properties(ncmdump_exec PROPERTIES OUTPUT_NAME "ncmdump")
target_include_directories(ncmdump_exec PRIVATE src/include)
target_link_libraries(ncmdump_exec tag)
target_include_directories(ncmdump_exec PRIVATE taglib)
target_include_directories(ncmdump_exec PRIVATE taglib/taglib)
target_include_directories(ncmdump_exec PRIVATE taglib/taglib/toolkit)
target_include_directories(ncmdump_exec PRIVATE taglib/taglib/mpeg/id3v2)
include(GNUInstallDirs) include(GNUInstallDirs)
install(TARGETS ncmdump
if(WIN32)
install(TARGETS ncmdump_exec ncmdump_lib
BUNDLE DESTINATION . BUNDLE DESTINATION .
LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR} LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR}
RUNTIME DESTINATION ${CMAKE_INSTALL_BINDIR} RUNTIME DESTINATION ${CMAKE_INSTALL_BINDIR}
) )
else()
install(TARGETS ncmdump_exec
BUNDLE DESTINATION .
LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR}
RUNTIME DESTINATION ${CMAKE_INSTALL_BINDIR}
)
endif()

View File

@@ -6,8 +6,9 @@
该版本为最早的 C++ 版本,也是作者开发的市面上第一个支持 ncm 转换的程序 该版本为最早的 C++ 版本,也是作者开发的市面上第一个支持 ncm 转换的程序
源码复刻自 anonymous5l/ncmdump感谢前辈的付出 源码复刻自 anonymous5l/ncmdump感谢前辈的付出做了 Windows 下的移植,修复了一些编译问题
做了 Windows 下的移植,修复了一些编译问题
1.3.0 版本更新说明因为之前有小伙伴反馈无法解密带有特殊字符的文件名例如中文、日文、韩文或者是表情符号等在1.3.0以及之后的版本彻底修复了这个问题,所有的 UTF-8 字符都可以正常解密。并且还自带了 dll 的构建可以供其他应用程序C#、Python、Java等调用。
## 传送门 ## 传送门
@@ -15,7 +16,9 @@
## 使用 ## 使用
你可以使用 Homebrew 来安装 ncmdump ### 命令行工具
你可以使用 Homebrew 来安装 ncmdump 的 cli 版本
```shell ```shell
brew install ncmdump brew install ncmdump
@@ -41,6 +44,12 @@ ncmdump file1 file2...
ncmdump -d folder ncmdump -d folder
``` ```
### 动态库
或者,如果你想利用此项目进行二次开发,例如在你的 C#、Python、Java 等项目中调用,你可以使用 `libncmdump` 动态库,具体使用方法见仓库的 `example` 文件夹
请注意!如果你在 Windows 下开发,传递到库构造函数的文件名编码**必须为 UTF-8 编码**,否则会抛出运行时错误。
## 编译项目 ## 编译项目
克隆本仓库 克隆本仓库
@@ -78,3 +87,9 @@ cmake --build build -j 8 --config Release
# Windows MinGW / Linux / macOS # Windows MinGW / Linux / macOS
cmake --build build -j 8 cmake --build build -j 8
``` ```
你可以在 `build` 文件夹下找到编译好的二进制文件,以及一个可供其它项目使用的动态库(Windows Only),使用方法见仓库的 `example` 文件夹
## Star History
[![Star History Chart](https://api.star-history.com/svg?repos=taurusxin/ncmdump&type=Date)](https://star-history.com/#taurusxin/ncmdump&Date)

View File

@@ -0,0 +1,67 @@
using System;
using System.Runtime.InteropServices;
namespace libncmdump_demo_cli
{
/// <summary>
/// NeteaseCrypt C# Wrapper
/// </summary>
class NeteaseCrypt
{
const string DLL_PATH = "libncmdump.dll";
[DllImport(DLL_PATH, CallingConvention = CallingConvention.Cdecl)]
private static extern IntPtr CreateNeteaseCrypt(IntPtr path);
[DllImport(DLL_PATH, CallingConvention = CallingConvention.Cdecl)]
private static extern int Dump(IntPtr NeteaseCrypt);
[DllImport(DLL_PATH, CallingConvention = CallingConvention.Cdecl)]
private static extern void FixMetadata(IntPtr NeteaseCrypt);
[DllImport(DLL_PATH, CallingConvention = CallingConvention.Cdecl)]
private static extern void DestroyNeteaseCrypt(IntPtr NeteaseCrypt);
private IntPtr NeteaseCryptClass = IntPtr.Zero;
/// <summary>
/// 创建 NeteaseCrypt 类的实例。
/// </summary>
/// <param name="FileName">网易云音乐 ncm 加密文件路径</param>
public NeteaseCrypt(string FileName)
{
byte[] bytes = Encoding.UTF8.GetBytes(FileName);
IntPtr inputPtr = Marshal.AllocHGlobal(bytes.Length + 1);
Marshal.Copy(bytes, 0, inputPtr, bytes.Length);
Marshal.WriteByte(inputPtr, bytes.Length, 0);
NeteaseCryptClass = CreateNeteaseCrypt(inputPtr);
}
/// <summary>
/// 启动转换过程。
/// </summary>
/// <returns>返回一个整数指示转储过程的结果。如果成功返回0如果失败返回1。</returns>
public int Dump()
{
return Dump(NeteaseCryptClass);
}
/// <summary>
/// 修复音乐文件元数据。
/// </summary>
public void FixMetadata()
{
FixMetadata(NeteaseCryptClass);
}
/// <summary>
/// 销毁 NeteaseCrypt 类的实例。
/// </summary>
public void Destroy()
{
DestroyNeteaseCrypt(NeteaseCryptClass);
}
}
}

26
example/csharp/Program.cs Normal file
View File

@@ -0,0 +1,26 @@
using System;
using System.Threading.Tasks;
namespace libncmdump_demo_cli
{
internal class Program
{
static void Main(string[] args)
{
// 文件名
string filePath = "test.ncm";
// 创建 NeteaseCrypt 类的实例
NeteaseCrypt neteaseCrypt = new NeteaseCrypt(filePath);
// 启动转换过程
int result = neteaseCrypt.Dump();
// 修复元数据
neteaseCrypt.FixMetadata();
// [务必]销毁 NeteaseCrypt 类的实例
neteaseCrypt.Destroy();
}
}
}

31
src/lib/libncmdump.cpp Normal file
View File

@@ -0,0 +1,31 @@
#include "libncmdump.h"
#include <filesystem>
namespace fs = std::filesystem;
extern "C" {
API NeteaseCrypt* CreateNeteaseCrypt(const char* path) {
fs::path fPath = fs::u8path(path);
return new NeteaseCrypt(fPath.u8string());
}
API int Dump(NeteaseCrypt* neteaseCrypt) {
try
{
neteaseCrypt->Dump();
}
catch (const std::invalid_argument& e)
{
return 1;
}
return 0;
}
API void FixMetadata(NeteaseCrypt* neteaseCrypt) {
neteaseCrypt->FixMetadata();
}
API void DestroyNeteaseCrypt(NeteaseCrypt* neteaseCrypt) {
delete neteaseCrypt;
}
}

14
src/lib/libncmdump.h Normal file
View File

@@ -0,0 +1,14 @@
#include "ncmcrypt.h"
#ifdef _WIN32
#define API __declspec(dllexport)
#else
#define API
#endif
extern "C" {
API NeteaseCrypt* CreateNeteaseCrypt(const char* path);
API int Dump(NeteaseCrypt* neteaseCrypt);
API void FixMetadata(NeteaseCrypt* neteaseCrypt);
API void DestroyNeteaseCrypt(NeteaseCrypt* neteaseCrypt);
}

View File

@@ -253,9 +253,10 @@ void NeteaseCrypt::FixMetadata()
tag->setAlbum(TagLib::String(mMetaData->album(), TagLib::String::UTF8)); tag->setAlbum(TagLib::String(mMetaData->album(), TagLib::String::UTF8));
} }
tag->setComment(TagLib::String("Create by netease copyright protected dump tool. author 5L", TagLib::String::UTF8)); tag->setComment(TagLib::String("Create by taurusxin/ncmdump.", TagLib::String::UTF8));
audioFile->save(); audioFile->save();
audioFile->~File();
} }
void NeteaseCrypt::Dump() void NeteaseCrypt::Dump()