Skip to content

Commit 8927235

Browse files
authored
Merge pull request #36 from bdach/missing-set-id-crash
Fix hard crash when BeatmapSetID is completely missing from an `.osu` file
2 parents c55ba95 + 3342fa2 commit 8927235

File tree

3 files changed

+32
-1
lines changed

3 files changed

+32
-1
lines changed

osu.Server.BeatmapSubmission.Tests/BeatmapSubmissionControllerTest.cs

Lines changed: 25 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1086,6 +1086,31 @@ public async Task TestUploadFullPackage_FailsIfCreatorDoesNotMatchHostUsername()
10861086
Assert.Contains("At least one difficulty has a specified creator that isn't the beatmap host's username.", (await response.Content.ReadFromJsonAsync<ErrorResponse>())!.Error);
10871087
}
10881088

1089+
[Fact]
1090+
public async Task TestUploadFullPackage_FailsIfBeatmapSetIDMissing()
1091+
{
1092+
using var db = await DatabaseAccess.GetConnectionAsync();
1093+
await db.ExecuteAsync("INSERT INTO `phpbb_users` (`user_id`, `username`, `username_clean`, `country_acronym`, `user_permissions`, `user_sig`, `user_occ`, `user_interests`) VALUES (1000, 'test', 'test', 'JP', '', '', '', '')");
1094+
1095+
await db.ExecuteAsync(@"INSERT INTO `osu_beatmapsets` (`beatmapset_id`, `user_id`, `creator`, `approved`, `thread_id`, `active`, `submit_date`) VALUES (241526, 1000, 'test user', -1, 0, -1, CURRENT_TIMESTAMP)");
1096+
1097+
foreach (uint beatmapId in new uint[] { 557810 })
1098+
await db.ExecuteAsync(@"INSERT INTO `osu_beatmaps` (`beatmap_id`, `user_id`, `beatmapset_id`, `approved`) VALUES (@beatmapId, 1000, 241526, -1)", new { beatmapId = beatmapId });
1099+
1100+
var request = new HttpRequestMessage(HttpMethod.Put, "/beatmapsets/241526");
1101+
1102+
using var content = new MultipartFormDataContent($"{Guid.NewGuid()}----");
1103+
using var stream = TestResources.GetResource("no-beatmap-set-id.osz")!;
1104+
content.Add(new StreamContent(stream), "beatmapArchive", osz_filename);
1105+
request.Content = content;
1106+
request.Headers.Add(HeaderBasedAuthenticationHandler.USER_ID_HEADER, "1000");
1107+
1108+
var response = await Client.SendAsync(request);
1109+
Assert.False(response.IsSuccessStatusCode);
1110+
Assert.Equal(HttpStatusCode.UnprocessableEntity, response.StatusCode);
1111+
Assert.Contains("Beatmap has no beatmap set ID inside", (await response.Content.ReadFromJsonAsync<ErrorResponse>())!.Error);
1112+
}
1113+
10891114
[Fact]
10901115
public async Task TestUploadFullPackage_FailsIfNonUnicodeMetadataHasMetadataChars()
10911116
{
901 Bytes
Binary file not shown.

osu.Server.BeatmapSubmission/Services/BeatmapPackageParser.cs

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -49,7 +49,13 @@ public BeatmapPackageParseResult Parse(uint beatmapSetId, ArchiveReader archiveR
4949
{
5050
beatmapContent = getBeatmapContent(filename, stream);
5151

52-
if (beatmapContent.Beatmap.BeatmapInfo.BeatmapSet!.OnlineID != beatmapSetId)
52+
// slightly unfortunate but possible if the set ID is completely missing.
53+
// refer to: https://github.com/ppy/osu/blob/a556049c1b29808b5dd9a3d65c7efb5d02315a0c/osu.Game/Beatmaps/Beatmap.cs#L45-L58,
54+
// https://github.com/ppy/osu/blob/a556049c1b29808b5dd9a3d65c7efb5d02315a0c/osu.Game/Beatmaps/Formats/LegacyBeatmapDecoder.cs#L377-L379
55+
if (beatmapContent.Beatmap.BeatmapInfo.BeatmapSet == null)
56+
throw new InvariantException($"Beatmap has no beatmap set ID inside ({filename})");
57+
58+
if (beatmapContent.Beatmap.BeatmapInfo.BeatmapSet.OnlineID != beatmapSetId)
5359
throw new InvariantException($"Beatmap has invalid beatmap set ID inside ({filename})");
5460

5561
if (!MetadataUtils.IsRomanised(beatmapContent.Beatmap.BeatmapInfo.DifficultyName))

0 commit comments

Comments
 (0)