Skip to content

Commit d403f75

Browse files
yunxuanhaoelysia-bestj2rong4cn
authored
fix: prevent panic in unaligned 64-bit atomic (#2637)
* fix(net): prevent panic in unaligned 64-bit atomic on ARMv7 Convert int64 fields written and readingID to atomic.Int64 guarantees 8-byte alignment on 32-bit ARM architectures. Unaligned 64-bit atomics fault with SIGILL on armv5/armv6 and armv7. Fixes file copy operations. * fix(atomic): migrate more atomic useage * fix(alias): improve link handling and add Clone method for Link struct * fix warn * fix(mem): simplify memory reservation handling in MemoryGrowCheck * fix(link): simplify link handling by using Clone method * fix bug * fix(hash): typo Signed-off-by: Yinan Qin <a.elysia@proton.me> --------- Signed-off-by: Yinan Qin <a.elysia@proton.me> Co-authored-by: Elysia <a.elysia@proton.me> Co-authored-by: j2rong4cn <j2rong@qq.com>
1 parent 3abdf79 commit d403f75

27 files changed

Lines changed: 169 additions & 143 deletions

File tree

drivers/115_open/types.go

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,9 +3,9 @@ package _115_open
33
import (
44
"time"
55

6+
sdk "github.com/OpenListTeam/115-sdk-go"
67
"github.com/OpenListTeam/OpenList/v4/internal/model"
78
"github.com/OpenListTeam/OpenList/v4/pkg/utils"
8-
sdk "github.com/OpenListTeam/115-sdk-go"
99
)
1010

1111
type Obj sdk.GetFilesResp_File

drivers/189pc/torrent.go

Lines changed: 0 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -89,7 +89,6 @@ func (y *Cloud189PC) RapidUploadFromTorrent(ctx context.Context, dstDir model.Ob
8989
sliceMd5Hex = strings.ToUpper(utils.GetMD5EncodeStr(strings.Join(upperSliceMD5s, "\n")))
9090
}
9191

92-
9392
// 使用与 Web 端一致的三步秒传流程
9493
fullUrl := "https://upload.cloud.189.cn"
9594
if isFamily {
@@ -110,7 +109,6 @@ func (y *Cloud189PC) RapidUploadFromTorrent(ctx context.Context, dstDir model.Ob
110109
initParams.Set("familyId", y.FamilyID)
111110
}
112111

113-
114112
var uploadInfo InitMultiUploadResp
115113
_, err = y.request(fullUrl+"/initMultiUpload", "GET", func(req *resty.Request) {
116114
req.SetContext(ctx)
@@ -119,7 +117,6 @@ func (y *Cloud189PC) RapidUploadFromTorrent(ctx context.Context, dstDir model.Ob
119117
return nil, fmt.Errorf("initMultiUpload 失败: %w", err)
120118
}
121119

122-
123120
uploadFileId := uploadInfo.Data.UploadFileID
124121

125122
// Step 2: checkTransSecond(用 fileMd5 + sliceMd5 + uploadFileId 检查秒传)
@@ -129,7 +126,6 @@ func (y *Cloud189PC) RapidUploadFromTorrent(ctx context.Context, dstDir model.Ob
129126
"uploadFileId": uploadFileId,
130127
}
131128

132-
133129
var checkResp struct {
134130
Data struct {
135131
FileDataExists int `json:"fileDataExists"`
@@ -143,7 +139,6 @@ func (y *Cloud189PC) RapidUploadFromTorrent(ctx context.Context, dstDir model.Ob
143139
return nil, fmt.Errorf("秒传检查失败: %w", err)
144140
}
145141

146-
147142
if checkResp.Data.FileDataExists != 1 {
148143
return nil, fmt.Errorf("秒传失败:云端不存在该文件(fileMD5=%s, sliceMD5=%s, size=%d)", fileMD5Upper, sliceMd5Hex, fileSize)
149144
}

drivers/alias/driver.go

Lines changed: 25 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -249,6 +249,7 @@ func (d *Alias) Link(ctx context.Context, file model.Obj, args model.LinkArgs) (
249249
}
250250
linkClosers := make([]io.Closer, 0, len(files))
251251
rrf := make([]model.RangeReaderIF, 0, len(files))
252+
requireReference := false
252253
for _, f := range files {
253254
link, fi, err := d.link(ctx, f.GetPath(), args)
254255
if err != nil {
@@ -258,30 +259,41 @@ func (d *Alias) Link(ctx context.Context, file model.Obj, args model.LinkArgs) (
258259
_ = link.Close()
259260
continue
260261
}
261-
l := *link // 复制一份,避免修改到原始link
262-
if l.ContentLength == 0 {
263-
l.ContentLength = fi.GetSize()
262+
l := &model.Link{
263+
URL: link.URL,
264+
Header: link.Header,
265+
RangeReader: link.RangeReader,
266+
Concurrency: link.Concurrency,
267+
PartSize: link.PartSize,
268+
ContentLength: link.ContentLength,
264269
}
265270
if d.DownloadConcurrency > 0 {
266271
l.Concurrency = d.DownloadConcurrency
267272
}
268273
if d.DownloadPartSize > 0 {
269274
l.PartSize = d.DownloadPartSize * utils.KB
270275
}
271-
rr, err := stream.GetRangeReaderFromLink(l.ContentLength, &l)
276+
if l.ContentLength == 0 {
277+
l.ContentLength = fi.GetSize()
278+
}
279+
rr, err := stream.GetRangeReaderFromLink(l.ContentLength, l)
272280
if err != nil {
273281
_ = link.Close()
274282
continue
275283
}
276284
linkClosers = append(linkClosers, link)
285+
if link.RequireReference {
286+
requireReference = true
287+
}
277288
rrf = append(rrf, rr)
278289
}
279290
rr := func(ctx context.Context, httpRange http_range.Range) (io.ReadCloser, error) {
280291
return rrf[rand.Intn(len(rrf))].RangeRead(ctx, httpRange)
281292
}
282293
return &model.Link{
283-
RangeReader: stream.RangeReaderFunc(rr),
284-
SyncClosers: utils.NewSyncClosers(linkClosers...),
294+
RangeReader: stream.RangeReaderFunc(rr),
295+
SyncClosers: utils.NewSyncClosers(linkClosers...),
296+
RequireReference: requireReference,
285297
}, nil
286298
}
287299

@@ -315,22 +327,21 @@ func (d *Alias) Link(ctx context.Context, file model.Obj, args model.LinkArgs) (
315327
if err != nil {
316328
return nil, err
317329
}
318-
resultLink := *link // 复制一份,避免修改到原始link
330+
resultLink := link.Clone() // 复制一份,避免修改到原始link
319331
resultLink.Expiration = nil
320-
resultLink.SyncClosers = utils.NewSyncClosers(link)
321332
if args.Redirect {
322-
return &resultLink, nil
323-
}
324-
if resultLink.ContentLength == 0 {
325-
resultLink.ContentLength = fi.GetSize()
333+
return resultLink, nil
326334
}
327335
if d.DownloadConcurrency > 0 {
328336
resultLink.Concurrency = d.DownloadConcurrency
329337
}
330338
if d.DownloadPartSize > 0 {
331339
resultLink.PartSize = d.DownloadPartSize * utils.KB
332340
}
333-
return &resultLink, nil
341+
if resultLink.ContentLength == 0 {
342+
resultLink.ContentLength = fi.GetSize()
343+
}
344+
return resultLink, nil
334345
}
335346

336347
func (d *Alias) Other(ctx context.Context, args model.OtherArgs) (interface{}, error) {
@@ -501,9 +512,7 @@ func (d *Alias) Extract(ctx context.Context, obj model.Obj, args model.ArchiveIn
501512
sign.SignArchive(reqPath)),
502513
}, nil
503514
}
504-
resultLink := *link
505-
resultLink.SyncClosers = utils.NewSyncClosers(link)
506-
return &resultLink, nil
515+
return link.Clone(), nil
507516
}
508517

509518
func (d *Alias) ArchiveDecompress(ctx context.Context, srcObj, dstDir model.Obj, args model.ArchiveDecompressArgs) error {

drivers/chunk/driver.go

Lines changed: 1 addition & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -263,9 +263,7 @@ func (d *Chunk) Link(ctx context.Context, file model.Obj, args model.LinkArgs) (
263263
if err != nil {
264264
return nil, err
265265
}
266-
resultLink := *l
267-
resultLink.SyncClosers = utils.NewSyncClosers(l)
268-
return &resultLink, nil
266+
return l.Clone(), nil
269267
}
270268
// 检查0号块不等于-1 以支持空文件
271269
// 如果块数量大于1 最后一块不可能为0

drivers/lanzou/driver.go

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@ package lanzou
33
import (
44
"context"
55
"net/http"
6+
"sync/atomic"
67

78
"github.com/OpenListTeam/OpenList/v4/drivers/base"
89
"github.com/OpenListTeam/OpenList/v4/internal/driver"
@@ -18,7 +19,7 @@ type LanZou struct {
1819
uid string
1920
vei string
2021

21-
flag int32
22+
flag atomic.Int32
2223
}
2324

2425
func (d *LanZou) Config() driver.Config {

drivers/lanzou/util.go

Lines changed: 3 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,6 @@ import (
1010
"strconv"
1111
"strings"
1212
"sync"
13-
"sync/atomic"
1413
"time"
1514

1615
"github.com/OpenListTeam/OpenList/v4/drivers/base"
@@ -43,17 +42,17 @@ func (d *LanZou) get(url string, callback base.ReqCallback) ([]byte, error) {
4342
func (d *LanZou) post(url string, callback base.ReqCallback, resp interface{}) ([]byte, error) {
4443
data, err := d._post(url, callback, resp, false)
4544
if err == ErrCookieExpiration && d.IsAccount() {
46-
if atomic.CompareAndSwapInt32(&d.flag, 0, 1) {
45+
if d.flag.CompareAndSwap(0, 1) {
4746
_, err2 := d.Login()
48-
atomic.SwapInt32(&d.flag, 0)
47+
d.flag.Swap(0)
4948
if err2 != nil {
5049
err = errors.Join(err, err2)
5150
d.Status = err.Error()
5251
op.MustSaveDriverStorage(d)
5352
return data, err
5453
}
5554
}
56-
for atomic.LoadInt32(&d.flag) != 0 {
55+
for d.flag.Load() != 0 {
5756
runtime.Gosched()
5857
}
5958
return d._post(url, callback, resp, false)

drivers/mediafire/meta.go

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -58,4 +58,3 @@ func init() {
5858
}
5959
})
6060
}
61-

drivers/mediafire/types.go

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -244,4 +244,3 @@ type MediafireUserInfoResponse struct {
244244
CurrentAPIVersion string `json:"current_api_version"`
245245
} `json:"response"`
246246
}
247-

drivers/mediafire/util.go

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -732,4 +732,3 @@ func (d *Mediafire) getFileByHash(ctx context.Context, hash string) (*model.ObjT
732732
file := resp.Response.FileInfo[0]
733733
return d.fileToObj(file), nil
734734
}
735-

drivers/smb/driver.go

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@ import (
66
"path"
77
"path/filepath"
88
"strings"
9+
"sync/atomic"
910

1011
"github.com/OpenListTeam/OpenList/v4/internal/driver"
1112
"github.com/OpenListTeam/OpenList/v4/internal/model"
@@ -16,7 +17,7 @@ import (
1617
)
1718

1819
type SMB struct {
19-
lastConnTime int64
20+
lastConnTime atomic.Int64
2021
model.Storage
2122
Addition
2223
fs *smb2.Share

0 commit comments

Comments
 (0)