Skip to content
项目
群组
代码片段
帮助
当前项目
正在载入...
登录 / 注册
切换导航面板
N
NiuTrans.Tensor
概览
Overview
Details
Activity
Cycle Analytics
版本库
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
问题
0
Issues
0
列表
Board
标记
里程碑
合并请求
0
Merge Requests
0
CI / CD
CI / CD
流水线
作业
日程表
图表
维基
Wiki
代码片段
Snippets
成员
Collapse sidebar
Close sidebar
活动
图像
聊天
创建新问题
作业
提交
Issue Boards
Open sidebar
杨迪
NiuTrans.Tensor
Commits
c52f9f7a
Commit
c52f9f7a
authored
Apr 18, 2020
by
liyinqiao
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
Support fp16 data type for more operations and fix the minor errors.
parent
1f1413ca
隐藏空白字符变更
内嵌
并排
正在显示
28 个修改的文件
包含
150 行增加
和
85 行删除
+150
-85
source/Main.cpp
+1
-1
source/tensor/XBLAS.cpp
+1
-1
source/tensor/XBLAS.h
+1
-1
source/tensor/XDataType.cpp
+1
-1
source/tensor/XDataType.h
+1
-1
source/tensor/XDevice.cpp
+1
-1
source/tensor/XDevice.h
+1
-1
source/tensor/XGlobal.cpp
+1
-1
source/tensor/XGlobal.h
+3
-1
source/tensor/XHeap.cpp
+1
-1
source/tensor/XHeap.h
+1
-1
source/tensor/XList.cpp
+22
-4
source/tensor/XList.h
+3
-0
source/tensor/XMem.cpp
+11
-11
source/tensor/XMem.h
+1
-1
source/tensor/XName.h
+1
-1
source/tensor/XPRunner.cpp
+1
-1
source/tensor/XPRunner.h
+1
-1
source/tensor/XQueue.cpp
+1
-1
source/tensor/XQueue.h
+1
-1
source/tensor/XStream.cpp
+1
-1
source/tensor/XStream.h
+1
-1
source/tensor/XTensor.cpp
+86
-44
source/tensor/XTensor.h
+3
-3
source/tensor/XThread.cpp
+1
-1
source/tensor/XThread.h
+1
-1
source/tensor/XUtility.cpp
+1
-1
source/tensor/XUtility.h
+1
-1
没有找到文件。
source/Main.cpp
查看文件 @
c52f9f7a
/* NiuTrans.Tensor - an open-source tensor library
* Copyright (C) 2018, Natural Language Processing Lab, Northeastern University.
* All rights reserved.
* All rights reserved.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
...
...
source/tensor/XBLAS.cpp
查看文件 @
c52f9f7a
/* NiuTrans.Tensor - an open-source tensor library
* Copyright (C) 2017, Natural Language Processing Lab, Northeastern University.
* Copyright (C) 2017, Natural Language Processing Lab, Northeastern University.
* All rights reserved.
*
* Licensed under the Apache License, Version 2.0 (the "License");
...
...
source/tensor/XBLAS.h
查看文件 @
c52f9f7a
/* NiuTrans.Tensor - an open-source tensor library
* Copyright (C) 2017, Natural Language Processing Lab, Northeastern University.
* Copyright (C) 2017, Natural Language Processing Lab, Northeastern University.
* All rights reserved.
*
* Licensed under the Apache License, Version 2.0 (the "License");
...
...
source/tensor/XDataType.cpp
查看文件 @
c52f9f7a
/* NiuTrans.Tensor - an open-source tensor library
* Copyright (C) 2018, Natural Language Processing Lab, Northeastern University.
* Copyright (C) 2018, Natural Language Processing Lab, Northeastern University.
* All rights reserved.
*
* Licensed under the Apache License, Version 2.0 (the "License");
...
...
source/tensor/XDataType.h
查看文件 @
c52f9f7a
/* NiuTrans.Tensor - an open-source tensor library
* Copyright (C) 2018, Natural Language Processing Lab, Northeastern University.
* Copyright (C) 2018, Natural Language Processing Lab, Northeastern University.
* All rights reserved.
*
* Licensed under the Apache License, Version 2.0 (the "License");
...
...
source/tensor/XDevice.cpp
查看文件 @
c52f9f7a
/* NiuTrans.Tensor - an open-source tensor library
* Copyright (C) 2017, Natural Language Processing Lab, Northeastern University.
* Copyright (C) 2017, Natural Language Processing Lab, Northeastern University.
* All rights reserved.
*
* Licensed under the Apache License, Version 2.0 (the "License");
...
...
source/tensor/XDevice.h
查看文件 @
c52f9f7a
/* NiuTrans.Tensor - an open-source tensor library
* Copyright (C) 2017, Natural Language Processing Lab, Northeastern University.
* Copyright (C) 2017, Natural Language Processing Lab, Northeastern University.
* All rights reserved.
*
* Licensed under the Apache License, Version 2.0 (the "License");
...
...
source/tensor/XGlobal.cpp
查看文件 @
c52f9f7a
/* NiuTrans.Tensor - an open-source tensor library
* Copyright (C) 2017, Natural Language Processing Lab, Northeastern University.
* Copyright (C) 2017, Natural Language Processing Lab, Northeastern University.
* All rights reserved.
*
* Licensed under the Apache License, Version 2.0 (the "License");
...
...
source/tensor/XGlobal.h
查看文件 @
c52f9f7a
/* NiuTrans.Tensor - an open-source tensor library
* Copyright (C) 2017, Natural Language Processing Lab, Northeastern University.
* Copyright (C) 2017, Natural Language Processing Lab, Northeastern University.
* All rights reserved.
*
* Licensed under the Apache License, Version 2.0 (the "License");
...
...
@@ -55,6 +55,8 @@ namespace nts {
#define DTYPE_MIN (DTYPE)-3.40E+38
#endif
#define MY_HALF_MIN 6.10E-5
#define LOGPROB_MIN (DTYPE)-2E+1
#define GRAD_MAX (DTYPE)1E+5
...
...
source/tensor/XHeap.cpp
查看文件 @
c52f9f7a
/* NiuTrans.Tensor - an open-source tensor library
* Copyright (C) 2017, Natural Language Processing Lab, Northeastern University.
* Copyright (C) 2017, Natural Language Processing Lab, Northeastern University.
* All rights reserved.
*
* Licensed under the Apache License, Version 2.0 (the "License");
...
...
source/tensor/XHeap.h
查看文件 @
c52f9f7a
/* NiuTrans.Tensor - an open-source tensor library
* Copyright (C) 2017, Natural Language Processing Lab, Northeastern University.
* Copyright (C) 2017, Natural Language Processing Lab, Northeastern University.
* All rights reserved.
*
* Licensed under the Apache License, Version 2.0 (the "License");
...
...
source/tensor/XList.cpp
查看文件 @
c52f9f7a
...
...
@@ -254,6 +254,9 @@ template <typename T>
void
TensorListBase
<
T
>::
Clear
()
{
count
=
0
;
delete
[]
items
;
maxNum
=
0
;
items
=
NULL
;
}
/*
...
...
@@ -288,12 +291,13 @@ inline void TensorListBase<T>::Reverse()
/* remove the item at position i */
template
<
typename
T
>
void
TensorListBase
<
T
>::
Remove
(
int
i
)
void
TensorListBase
<
T
>::
Remove
(
int
i
dx
)
{
if
(
i
>=
count
||
i
<
0
)
return
;
CheckNTErrors
(
idx
<
count
&&
idx
>
-
1
,
"invalid index"
);
memcpy
(
items
+
i
,
items
+
i
+
1
,
sizeof
(
T
*
)
*
(
count
-
i
-
1
));
for
(
int
i
=
idx
;
i
<
count
-
1
;
i
++
)
{
items
[
i
]
=
items
[
i
+
1
];
}
count
--
;
}
...
...
@@ -355,6 +359,20 @@ void TensorListBase<T>::Shuffle(int nround, int beg, int len)
}
}
/* sum a range of values */
template
<>
int
TensorListBase
<
int
>::
SumRange
(
int
begin
,
int
end
)
{
CheckNTErrors
(
begin
<
count
&&
end
<=
count
&&
end
>
begin
,
"invalid index of begin or end"
);
int
value
=
items
[
begin
];
int
i
=
begin
+
1
;
while
(
i
<
end
)
{
value
+=
items
[
i
];
i
++
;
}
return
value
;
}
/* specializations and typedef of list */
template
struct
TensorListBase
<
int
>
;
template
struct
TensorListBase
<
char
>
;
...
...
source/tensor/XList.h
查看文件 @
c52f9f7a
...
...
@@ -130,6 +130,9 @@ public:
};
T
&
Get
(
int
i
)
{
return
GetItem
(
i
);
};
void
Set
(
int
i
,
T
item
)
{
SetItem
(
i
,
item
);
};
/* sum a range of values */
T
SumRange
(
int
begin
,
int
end
);
};
struct
XTensor
;
...
...
source/tensor/XMem.cpp
查看文件 @
c52f9f7a
/* NiuTrans.Tensor - an open-source tensor library
* Copyright (C) 2017, Natural Language Processing Lab, Northeastern University.
* Copyright (C) 2017, Natural Language Processing Lab, Northeastern University.
* All rights reserved.
*
* Licensed under the Apache License, Version 2.0 (the "License");
...
...
@@ -1583,16 +1583,16 @@ MTYPE XMemManager::GetAvailableGPUMemory(int devID)
void
XMemManager
::
GetBufferSize
(
MTYPE
freeMem
,
MTYPE
*
myBufSize
)
{
*
myBufSize
=
0
;
if
(
freeMem
>=
MILLION
*
128
){
*
myBufSize
=
MILLION
*
32
;
if
(
freeMem
>=
MILLION
*
256
){
*
myBufSize
=
MILLION
*
64
;
if
(
freeMem
>=
MILLION
*
512
){
*
myBufSize
=
MILLION
*
128
;
if
(
freeMem
>=
MILLION
*
1024
)
{
*
myBufSize
=
MILLION
*
128
;
if
(
freeMem
>=
MILLION
*
2048
)
*
myBufSize
=
MILLION
*
128
;
if
(
freeMem
>=
MILLION
*
128
ULL
){
*
myBufSize
=
MILLION
*
32
ULL
;
if
(
freeMem
>=
MILLION
*
256
ULL
){
*
myBufSize
=
MILLION
*
64
ULL
;
if
(
freeMem
>=
MILLION
*
512
ULL
){
*
myBufSize
=
MILLION
*
128
ULL
;
if
(
freeMem
>=
MILLION
*
1024
ULL
)
{
*
myBufSize
=
MILLION
*
128
ULL
;
if
(
freeMem
>=
MILLION
*
2048
ULL
)
*
myBufSize
=
MILLION
*
128
ULL
;
}
}
}
...
...
source/tensor/XMem.h
查看文件 @
c52f9f7a
/* NiuTrans.Tensor - an open-source tensor library
* Copyright (C) 2017, Natural Language Processing Lab, Northeastern University.
* Copyright (C) 2017, Natural Language Processing Lab, Northeastern University.
* All rights reserved.
*
* Licensed under the Apache License, Version 2.0 (the "License");
...
...
source/tensor/XName.h
查看文件 @
c52f9f7a
/* NiuTrans.Tensor - an open-source tensor library
* Copyright (C) 2018, Natural Language Processing Lab, Northeastern University.
* Copyright (C) 2018, Natural Language Processing Lab, Northeastern University.
* All rights reserved.
*
* Licensed under the Apache License, Version 2.0 (the "License");
...
...
source/tensor/XPRunner.cpp
查看文件 @
c52f9f7a
/* NiuTrans.Tensor - an open-source tensor library
* Copyright (C) 2017, Natural Language Processing Lab, Northeastern University.
* Copyright (C) 2017, Natural Language Processing Lab, Northeastern University.
* All rights reserved.
*
* Licensed under the Apache License, Version 2.0 (the "License");
...
...
source/tensor/XPRunner.h
查看文件 @
c52f9f7a
/* NiuTrans.Tensor - an open-source tensor library
* Copyright (C) 2017, Natural Language Processing Lab, Northeastern University.
* Copyright (C) 2017, Natural Language Processing Lab, Northeastern University.
* All rights reserved.
*
* Licensed under the Apache License, Version 2.0 (the "License");
...
...
source/tensor/XQueue.cpp
查看文件 @
c52f9f7a
/* NiuTrans.Tensor - an open-source tensor library
* Copyright (C) 2017, Natural Language Processing Lab, Northeastern University.
* Copyright (C) 2017, Natural Language Processing Lab, Northeastern University.
* All rights reserved.
*
* Licensed under the Apache License, Version 2.0 (the "License");
...
...
source/tensor/XQueue.h
查看文件 @
c52f9f7a
/* NiuTrans.Tensor - an open-source tensor library
* Copyright (C) 2017, Natural Language Processing Lab, Northeastern University.
* Copyright (C) 2017, Natural Language Processing Lab, Northeastern University.
* All rights reserved.
*
* Licensed under the Apache License, Version 2.0 (the "License");
...
...
source/tensor/XStream.cpp
查看文件 @
c52f9f7a
/* NiuTrans.Tensor - an open-source tensor library
* Copyright (C) 2017, Natural Language Processing Lab, Northeastern University.
* Copyright (C) 2017, Natural Language Processing Lab, Northeastern University.
* All rights reserved.
*
* Licensed under the Apache License, Version 2.0 (the "License");
...
...
source/tensor/XStream.h
查看文件 @
c52f9f7a
/* NiuTrans.Tensor - an open-source tensor library
* Copyright (C) 2017, Natural Language Processing Lab, Northeastern University.
* Copyright (C) 2017, Natural Language Processing Lab, Northeastern University.
* All rights reserved.
*
* Licensed under the Apache License, Version 2.0 (the "License");
...
...
source/tensor/XTensor.cpp
查看文件 @
c52f9f7a
/* NiuTrans.Tensor - an open-source tensor library
* Copyright (C) 2017, Natural Language Processing Lab, Northeastern University.
* Copyright (C) 2017, Natural Language Processing Lab, Northeastern University.
* All rights reserved.
*
* Licensed under the Apache License, Version 2.0 (the "License");
...
...
@@ -50,6 +50,7 @@
#include "core/getandset/SetData.h"
#include "function/Identity.h"
#include "core/CHeader.h"
//#include "XHalf.hpp"
#ifdef USE_CUDA
...
...
@@ -179,11 +180,13 @@ XTensor::XTensor(const XTensor& reference)
_CopyValues
(
&
reference
,
this
);
}
if
(
reference
.
isTmp
)
XLink
::
Replace
(
&
reference
,
this
);
else
{
CheckNTErrors
(
outgo
.
tailNum
==
0
,
"The node has outgoing edge to other nodes!"
);
XLink
::
CopyIncoming
(
&
reference
,
this
);
if
(
reference
.
enableGrad
)
{
if
(
reference
.
isTmp
)
XLink
::
Replace
(
&
reference
,
this
);
else
{
CheckNTErrors
(
outgo
.
tailNum
==
0
,
"The node has outgoing edge to other nodes!"
);
XLink
::
CopyIncoming
(
&
reference
,
this
);
}
}
isInit
=
true
;
...
...
@@ -212,7 +215,9 @@ XTensor::XTensor(const XTensor&& reference)
This is VERY tricky and there might be better solutions :) */
*
reference
.
dataP
=
NULL
;
XLink
::
Replace
(
&
reference
,
this
);
if
(
reference
.
enableGrad
)
{
XLink
::
Replace
(
&
reference
,
this
);
}
isInit
=
true
;
isTmp
=
reference
.
isTmp
;
...
...
@@ -234,13 +239,15 @@ XTensor::~XTensor()
newTensor
->
SetTMPFlag
();
newTensor
->
data
=
data
;
data
=
NULL
;
XLink
::
Replace
(
this
,
newTensor
);
if
(
enableGrad
)
XLink
::
Replace
(
this
,
newTensor
);
}
if
(
enableGrad
)
{
XLink
::
ClearOutgoing
(
this
);
XLink
::
ClearIncoming
(
this
);
}
XLink
::
ClearOutgoing
(
this
);
XLink
::
ClearIncoming
(
this
);
DestroyData
();
if
(
grad
!=
NULL
)
...
...
@@ -341,9 +348,11 @@ XTensor& XTensor::operator= (const XTensor& tensor)
newTensor
->
dataHost
=
dataHost
;
newTensor
->
signature
=
tensor
.
signature
;
XLink
::
Replace
(
this
,
newTensor
);
XLink
::
ClearOutgoing
(
this
);
XLink
::
ClearIncoming
(
this
);
if
(
enableGrad
)
{
XLink
::
Replace
(
this
,
newTensor
);
XLink
::
ClearOutgoing
(
this
);
XLink
::
ClearIncoming
(
this
);
}
newTensor
->
ShallowCopy
(
this
);
data
=
NULL
;
...
...
@@ -354,15 +363,19 @@ XTensor& XTensor::operator= (const XTensor& tensor)
/* NOTE: this might lead to additional data copy by Mac LLVM compilers */
/* we make an identity transformation here */
if
(
outgo
.
tailNum
>
0
)
XLink
::
ClearOutgoing
(
this
);
XLink
::
ClearIncoming
(
this
);
if
(
enableGrad
)
{
if
(
outgo
.
tailNum
>
0
)
XLink
::
ClearOutgoing
(
this
);
XLink
::
ClearIncoming
(
this
);
}
if
(
!
_IsSameShaped
(
this
,
&
tensor
))
Resize
(
tensor
.
order
,
tensor
.
dimSize
,
tensor
.
dataType
,
tensor
.
denseRatio
);
_Identity
(
&
tensor
,
this
);
XLink
::
MakeLink
(
&
tensor
,
NULL
,
this
,
FUNC_IDENTITY
);
if
(
enableGrad
)
{
XLink
::
MakeLink
(
&
tensor
,
NULL
,
this
,
FUNC_IDENTITY
);
}
}
else
{
/* hard copy of the data array */
...
...
@@ -396,7 +409,9 @@ XTensor& XTensor::operator= (const XTensor& tensor)
CheckNTErrors
(
outgo
.
tailNum
==
0
,
"The node has outgoing edge to other nodes!"
);
/* create tensor links for the new tensor */
XLink
::
Copy
(
&
tensor
,
this
);
if
(
enableGrad
)
{
XLink
::
Copy
(
&
tensor
,
this
);
}
}
return
*
this
;
...
...
@@ -418,9 +433,11 @@ XTensor& XTensor::operator= (const XTensor&& tensor)
newTensor
->
dataHost
=
dataHost
;
newTensor
->
signature
=
tensor
.
signature
;
XLink
::
Replace
(
this
,
newTensor
);
XLink
::
ClearOutgoing
(
this
);
XLink
::
ClearIncoming
(
this
);
if
(
enableGrad
)
{
XLink
::
Replace
(
this
,
newTensor
);
XLink
::
ClearOutgoing
(
this
);
XLink
::
ClearIncoming
(
this
);
}
newTensor
->
ShallowCopy
(
this
);
data
=
NULL
;
...
...
@@ -444,7 +461,9 @@ XTensor& XTensor::operator= (const XTensor&& tensor)
This is VERY tricky and there might be better solutions :) */
*
tensor
.
dataP
=
NULL
;
XLink
::
Copy
(
&
tensor
,
this
);
if
(
enableGrad
)
{
XLink
::
Copy
(
&
tensor
,
this
);
}
return
*
this
;
}
...
...
@@ -1697,6 +1716,17 @@ void XTensor::Dump(FILE* file, const char* label, const int n, const int beg, co
fprintf
(
file
,
" %d"
,
f
);
}
}
/*else if (dataType == X_FLOAT16) {
int end = MIN(n > 0 ? beg + n : beg + unitNum, unitNum);
for(int i = beg; i < end; i++){
DTYPE f = ((half_float::half*)d)[i];
if(i == beg)
fprintf(file, "%e", f);
else
fprintf(file, " %e", f);
}
}*/
else
ShowNTErrors
(
"TODO!"
);
}
...
...
@@ -1749,12 +1779,17 @@ void XTensor::BinaryDump(FILE* file)
_CopyValues
(
this
,
&
tmp
);
switch
(
dataType
)
{
case
X_INT
:
{
fwrite
(
tmp
.
data
,
sizeof
(
int
),
unitNum
,
file
);
}
default
:
{
fwrite
(
tmp
.
data
,
sizeof
(
float
),
unitNum
,
file
);
}
case
X_INT
:
{
fwrite
(
tmp
.
data
,
sizeof
(
int
),
unitNum
,
file
);
break
;
}
/*case X_FLOAT16: {
fwrite(tmp.data, sizeof(half_float::half), unitNum, file);
break;
}*/
default
:
{
fwrite
(
tmp
.
data
,
sizeof
(
float
),
unitNum
,
file
);
}
}
}
...
...
@@ -1877,20 +1912,27 @@ read data from a binary file
*/
void
XTensor
::
BinaryRead
(
FILE
*
file
,
size_t
offset
)
{
fseek
(
file
,
offset
,
0
);
switch
(
dataType
)
{
case
X_INT
:
{
int
*
d
=
new
int
[
unitNum
];
fread
(
d
,
sizeof
(
int
),
unitNum
,
file
);
SetData
(
d
,
unitNum
);
delete
[]
d
;
}
default
:
{
float
*
d
=
new
float
[
unitNum
];
fread
(
d
,
sizeof
(
float
),
unitNum
,
file
);
SetData
(
d
,
unitNum
);
delete
[]
d
;
}
case
X_INT
:
{
int
*
d
=
new
int
[
unitNum
];
fread
(
d
,
sizeof
(
int
),
unitNum
,
file
);
SetData
(
d
,
unitNum
);
delete
[]
d
;
break
;
}
/*case X_FLOAT16: {
half_float::half* d = new half_float::half[unitNum];
fread(d, sizeof(half_float::half), unitNum, file);
SetData(d, unitNum);
delete[] d;
break;
}*/
default
:
{
float
*
d
=
new
float
[
unitNum
];
fread
(
d
,
sizeof
(
float
),
unitNum
,
file
);
SetData
(
d
,
unitNum
);
delete
[]
d
;
}
}
}
...
...
source/tensor/XTensor.h
查看文件 @
c52f9f7a
/* NiuTrans.Tensor - an open-source tensor library
* Copyright (C) 2017, Natural Language Processing Lab, Northeastern University.
* Copyright (C) 2017, Natural Language Processing Lab, Northeastern University.
* All rights reserved.
*
* Licensed under the Apache License, Version 2.0 (the "License");
...
...
@@ -175,7 +175,7 @@ public:
XLink
outgo
;
/********************
XTensor u
n
tilities
XTensor utilities
********************/
/* constructor */
...
...
@@ -440,7 +440,7 @@ public:
void
Read
(
FILE
*
file
,
const
char
*
label
=
NULL
);
/* read data from a binary file */
void
BinaryRead
(
FILE
*
file
,
size_t
offset
);
void
BinaryRead
(
FILE
*
file
,
size_t
offset
=
0
);
/* flush the data to the target device */
void
FlushToMem
(
XMem
*
targetMem
);
...
...
source/tensor/XThread.cpp
查看文件 @
c52f9f7a
/* NiuTrans.Tensor - an open-source tensor library
* Copyright (C) 2017, Natural Language Processing Lab, Northeastern University.
* Copyright (C) 2017, Natural Language Processing Lab, Northeastern University.
* All rights reserved.
*
* Licensed under the Apache License, Version 2.0 (the "License");
...
...
source/tensor/XThread.h
查看文件 @
c52f9f7a
/* NiuTrans.Tensor - an open-source tensor library
* Copyright (C) 2017, Natural Language Processing Lab, Northeastern University.
* Copyright (C) 2017, Natural Language Processing Lab, Northeastern University.
* All rights reserved.
*
* Licensed under the Apache License, Version 2.0 (the "License");
...
...
source/tensor/XUtility.cpp
查看文件 @
c52f9f7a
/* NiuTrans.Tensor - an open-source tensor library
* Copyright (C) 2017, Natural Language Processing Lab, Northeastern University.
* Copyright (C) 2017, Natural Language Processing Lab, Northeastern University.
* All rights reserved.
*
* Licensed under the Apache License, Version 2.0 (the "License");
...
...
source/tensor/XUtility.h
查看文件 @
c52f9f7a
/* NiuTrans.Tensor - an open-source tensor library
* Copyright (C) 2017, Natural Language Processing Lab, Northeastern University.
* Copyright (C) 2017, Natural Language Processing Lab, Northeastern University.
* All rights reserved.
*
* Licensed under the Apache License, Version 2.0 (the "License");
...
...
编写
预览
Markdown
格式
0%
重试
或
添加新文件
添加附件
取消
您添加了
0
人
到此讨论。请谨慎行事。
请先完成此评论的编辑!
取消
请
注册
或者
登录
后发表评论