Skip to content

Commit fff62a8

Browse files
committed
Restore original flag parsing behavior
THe flagset changes misplaced the post-parsing flag processing so that it was only executed if a special flag was found. That was not the case previously and this restores that behavior. I also simplified the code a bit while I was at it. This fixes #1191.
1 parent e8d21a0 commit fff62a8

File tree

1 file changed

+97
-100
lines changed

1 file changed

+97
-100
lines changed

code/weapon/weapons.cpp

Lines changed: 97 additions & 100 deletions
Original file line numberDiff line numberDiff line change
@@ -576,131 +576,128 @@ void parse_wi_flags(weapon_info *weaponp, flagset<Weapon::Info_Flags> wi_flags)
576576

577577
bool set_nopierce = false;
578578

579-
if (!unparsed_or_special.empty()) {
580-
581-
for (auto flag = unparsed_or_special.begin(); flag != unparsed_or_special.end(); ++flag) {
582-
SCP_string flag_text = *flag;
583-
//deal with spawn flag
584-
if (!strnicmp(spawn_str, flag_text.c_str(), 5))
579+
for (auto flag = unparsed_or_special.begin(); flag != unparsed_or_special.end(); ++flag) {
580+
SCP_string flag_text = *flag;
581+
//deal with spawn flag
582+
if (!strnicmp(spawn_str, flag_text.c_str(), 5))
583+
{
584+
if (weaponp->num_spawn_weapons_defined < MAX_SPAWN_TYPES_PER_WEAPON)
585585
{
586-
if (weaponp->num_spawn_weapons_defined < MAX_SPAWN_TYPES_PER_WEAPON)
587-
{
588-
//We need more spawning slots
589-
//allocate in slots of 10
590-
if ((Num_spawn_types % 10) == 0) {
591-
Spawn_names = (char **)vm_realloc(Spawn_names, (Num_spawn_types + 10) * sizeof(*Spawn_names));
592-
}
593-
594-
size_t skip_length, name_length;
595-
std::unique_ptr<char[]> temp_string(new char[flag_text.size() + 1]);
596-
597-
strcpy(temp_string.get(), flag_text.c_str());
586+
//We need more spawning slots
587+
//allocate in slots of 10
588+
if ((Num_spawn_types % 10) == 0) {
589+
Spawn_names = (char **)vm_realloc(Spawn_names, (Num_spawn_types + 10) * sizeof(*Spawn_names));
590+
}
598591

599-
weaponp->wi_flags.set(Weapon::Info_Flags::Spawn);
600-
weaponp->spawn_info[weaponp->num_spawn_weapons_defined].spawn_type = (short)Num_spawn_types;
601-
skip_length = spawn_str_len + strspn(&temp_string[spawn_str_len], NOX(" \t"));
602-
char *num_start = strchr(&temp_string[skip_length], ',');
603-
if (num_start == NULL) {
604-
weaponp->spawn_info[weaponp->num_spawn_weapons_defined].spawn_count = DEFAULT_WEAPON_SPAWN_COUNT;
605-
name_length = 999;
606-
}
607-
else {
608-
weaponp->spawn_info[weaponp->num_spawn_weapons_defined].spawn_count = (short)atoi(num_start + 1);
609-
name_length = num_start - temp_string.get() - skip_length;
610-
}
592+
size_t skip_length, name_length;
593+
std::unique_ptr<char[]> temp_string(new char[flag_text.size() + 1]);
611594

612-
weaponp->total_children_spawned += weaponp->spawn_info[weaponp->num_spawn_weapons_defined].spawn_count;
595+
strcpy(temp_string.get(), flag_text.c_str());
613596

614-
Spawn_names[Num_spawn_types] = vm_strndup(&flag_text[skip_length], name_length);
615-
Num_spawn_types++;
616-
weaponp->num_spawn_weapons_defined++;
597+
weaponp->wi_flags.set(Weapon::Info_Flags::Spawn);
598+
weaponp->spawn_info[weaponp->num_spawn_weapons_defined].spawn_type = (short)Num_spawn_types;
599+
skip_length = spawn_str_len + strspn(&temp_string[spawn_str_len], NOX(" \t"));
600+
char *num_start = strchr(&temp_string[skip_length], ',');
601+
if (num_start == NULL) {
602+
weaponp->spawn_info[weaponp->num_spawn_weapons_defined].spawn_count = DEFAULT_WEAPON_SPAWN_COUNT;
603+
name_length = 999;
617604
}
618605
else {
619-
Warning(LOCATION, "Illegal to have more than %d spawn types for one weapon.\nIgnoring weapon %s", MAX_SPAWN_TYPES_PER_WEAPON, weaponp->name);
620-
}
621-
}
622-
else if (!stricmp(NOX("beam"), flag_text.c_str())) {
623-
weaponp->wi_flags.set(Weapon::Info_Flags::Pierce_shields);
624-
}
625-
else if (!stricmp(NOX("no pierce shields"), flag_text.c_str())) {
626-
set_nopierce = true;
627-
}
628-
else if (!stricmp(NOX("beam no whack"), flag_text.c_str())) {
629-
Warning(LOCATION, "The \"beam no whack\" flag has been deprecated. Set the beam's mass to 0 instead. This has been done for you.\n");
630-
weaponp->mass = 0.0f;
631-
}
632-
else if (!stricmp(NOX("interceptable"), flag_text.c_str())) {
633-
weaponp->wi_flags.set(Weapon::Info_Flags::Turret_Interceptable);
634-
weaponp->wi_flags.set(Weapon::Info_Flags::Fighter_Interceptable);
635-
}
636-
else if (!stricmp(NOX("die on lost lock"), flag_text.c_str())) {
637-
if (!(weaponp->is_locked_homing())) {
638-
Warning(LOCATION, "\"die on lost lock\" may only be used for Homing Type ASPECT/JAVELIN!");
639-
weaponp->wi_flags.remove(Weapon::Info_Flags::Die_on_lost_lock);
606+
weaponp->spawn_info[weaponp->num_spawn_weapons_defined].spawn_count = (short)atoi(num_start + 1);
607+
name_length = num_start - temp_string.get() - skip_length;
640608
}
609+
610+
weaponp->total_children_spawned += weaponp->spawn_info[weaponp->num_spawn_weapons_defined].spawn_count;
611+
612+
Spawn_names[Num_spawn_types] = vm_strndup(&flag_text[skip_length], name_length);
613+
Num_spawn_types++;
614+
weaponp->num_spawn_weapons_defined++;
641615
}
642616
else {
643-
Warning(LOCATION, "Unrecognized flag in flag list for weapon %s: \"%s\"", weaponp->name, (*flag).c_str());
617+
Warning(LOCATION, "Illegal to have more than %d spawn types for one weapon.\nIgnoring weapon %s", MAX_SPAWN_TYPES_PER_WEAPON, weaponp->name);
644618
}
645619
}
620+
else if (!stricmp(NOX("beam"), flag_text.c_str())) {
621+
weaponp->wi_flags.set(Weapon::Info_Flags::Pierce_shields);
622+
}
623+
else if (!stricmp(NOX("no pierce shields"), flag_text.c_str())) {
624+
set_nopierce = true;
625+
}
626+
else if (!stricmp(NOX("beam no whack"), flag_text.c_str())) {
627+
Warning(LOCATION, "The \"beam no whack\" flag has been deprecated. Set the beam's mass to 0 instead. This has been done for you.\n");
628+
weaponp->mass = 0.0f;
629+
}
630+
else if (!stricmp(NOX("interceptable"), flag_text.c_str())) {
631+
weaponp->wi_flags.set(Weapon::Info_Flags::Turret_Interceptable);
632+
weaponp->wi_flags.set(Weapon::Info_Flags::Fighter_Interceptable);
633+
}
634+
else if (!stricmp(NOX("die on lost lock"), flag_text.c_str())) {
635+
if (!(weaponp->is_locked_homing())) {
636+
Warning(LOCATION, "\"die on lost lock\" may only be used for Homing Type ASPECT/JAVELIN!");
637+
weaponp->wi_flags.remove(Weapon::Info_Flags::Die_on_lost_lock);
638+
}
639+
}
640+
else {
641+
Warning(LOCATION, "Unrecognized flag in flag list for weapon %s: \"%s\"", weaponp->name, (*flag).c_str());
642+
}
643+
}
646644

647-
//Do cleanup and sanity checks
645+
//Do cleanup and sanity checks
648646

649-
if (set_nopierce)
650-
weaponp->wi_flags.remove(Weapon::Info_Flags::Pierce_shields);
651-
652-
if (weaponp->wi_flags[Weapon::Info_Flags::Hard_target_bomb] && !weaponp->wi_flags[Weapon::Info_Flags::Bomb]) {
653-
weaponp->wi_flags.remove(Weapon::Info_Flags::Hard_target_bomb);
654-
Warning(LOCATION, "Weapon %s is not a bomb but has \"no radius doubling\" set. Ignoring this flag", weaponp->name);
655-
}
647+
if (set_nopierce)
648+
weaponp->wi_flags.remove(Weapon::Info_Flags::Pierce_shields);
656649

657-
if (weaponp->wi_flags[Weapon::Info_Flags::In_tech_database])
658-
weaponp->wi_flags.set(Weapon::Info_Flags::Default_in_tech_database);
650+
if (weaponp->wi_flags[Weapon::Info_Flags::Hard_target_bomb] && !weaponp->wi_flags[Weapon::Info_Flags::Bomb]) {
651+
weaponp->wi_flags.remove(Weapon::Info_Flags::Hard_target_bomb);
652+
Warning(LOCATION, "Weapon %s is not a bomb but has \"no radius doubling\" set. Ignoring this flag", weaponp->name);
653+
}
659654

660-
if (weaponp->wi_flags[Weapon::Info_Flags::Flak]) {
661-
if (weaponp->wi_flags[Weapon::Info_Flags::Swarm] || weaponp->wi_flags[Weapon::Info_Flags::Corkscrew]) {
662-
weaponp->wi_flags.remove(Weapon::Info_Flags::Swarm);
663-
weaponp->wi_flags.remove(Weapon::Info_Flags::Corkscrew);
664-
Warning(LOCATION, "Swarm, Corkscrew, and Flak are mutually exclusive! Removing Swarm and Corkscrew attributes from weapon %s.\n", weaponp->name);
665-
}
666-
}
655+
if (weaponp->wi_flags[Weapon::Info_Flags::In_tech_database])
656+
weaponp->wi_flags.set(Weapon::Info_Flags::Default_in_tech_database);
667657

668-
if (weaponp->wi_flags[Weapon::Info_Flags::Swarm] && weaponp->wi_flags[Weapon::Info_Flags::Corkscrew]) {
658+
if (weaponp->wi_flags[Weapon::Info_Flags::Flak]) {
659+
if (weaponp->wi_flags[Weapon::Info_Flags::Swarm] || weaponp->wi_flags[Weapon::Info_Flags::Corkscrew]) {
660+
weaponp->wi_flags.remove(Weapon::Info_Flags::Swarm);
669661
weaponp->wi_flags.remove(Weapon::Info_Flags::Corkscrew);
670-
Warning(LOCATION, "Swarm and Corkscrew are mutually exclusive! Defaulting to Swarm on weapon %s.\n", weaponp->name);
662+
Warning(LOCATION, "Swarm, Corkscrew, and Flak are mutually exclusive! Removing Swarm and Corkscrew attributes from weapon %s.\n", weaponp->name);
671663
}
664+
}
672665

673-
if (weaponp->wi_flags[Weapon::Info_Flags::Local_ssm]) {
674-
if (!weaponp->is_homing() || weaponp->subtype != WP_MISSILE) {
675-
Warning(LOCATION, "local ssm must be guided missile: %s", weaponp->name);
676-
}
677-
}
666+
if (weaponp->wi_flags[Weapon::Info_Flags::Swarm] && weaponp->wi_flags[Weapon::Info_Flags::Corkscrew]) {
667+
weaponp->wi_flags.remove(Weapon::Info_Flags::Corkscrew);
668+
Warning(LOCATION, "Swarm and Corkscrew are mutually exclusive! Defaulting to Swarm on weapon %s.\n", weaponp->name);
669+
}
678670

679-
if (weaponp->wi_flags[Weapon::Info_Flags::Small_only] && weaponp->wi_flags[Weapon::Info_Flags::Huge])
680-
{
681-
Warning(LOCATION, "\"small only\" and \"huge\" flags are mutually exclusive.\nThey are used together in %s\nAI will most likely not use this weapon", weaponp->name);
671+
if (weaponp->wi_flags[Weapon::Info_Flags::Local_ssm]) {
672+
if (!weaponp->is_homing() || weaponp->subtype != WP_MISSILE) {
673+
Warning(LOCATION, "local ssm must be guided missile: %s", weaponp->name);
682674
}
675+
}
683676

684-
if (!weaponp->wi_flags[Weapon::Info_Flags::Spawn] && weaponp->wi_flags[Weapon::Info_Flags::Smart_spawn])
685-
{
686-
Warning(LOCATION, "\"smart spawn\" flag used without \"spawn\" flag in %s\n", weaponp->name);
687-
}
677+
if (weaponp->wi_flags[Weapon::Info_Flags::Small_only] && weaponp->wi_flags[Weapon::Info_Flags::Huge])
678+
{
679+
Warning(LOCATION, "\"small only\" and \"huge\" flags are mutually exclusive.\nThey are used together in %s\nAI will most likely not use this weapon", weaponp->name);
680+
}
688681

689-
if (weaponp->wi_flags[Weapon::Info_Flags::Inherit_parent_target] && (!weaponp->wi_flags[Weapon::Info_Flags::Child]))
690-
{
691-
Warning(LOCATION, "Weapon %s has the \"inherit parent target\" flag, but not the \"child\" flag. No changes in behavior will occur.", weaponp->name);
692-
}
682+
if (!weaponp->wi_flags[Weapon::Info_Flags::Spawn] && weaponp->wi_flags[Weapon::Info_Flags::Smart_spawn])
683+
{
684+
Warning(LOCATION, "\"smart spawn\" flag used without \"spawn\" flag in %s\n", weaponp->name);
685+
}
693686

694-
if (!weaponp->wi_flags[Weapon::Info_Flags::Homing_heat] && weaponp->wi_flags[Weapon::Info_Flags::Untargeted_heat_seeker])
695-
{
696-
Warning(LOCATION, "Weapon '%s' has the \"untargeted heat seeker\" flag, but Homing Type is not set to \"HEAT\".", weaponp->name);
697-
}
687+
if (weaponp->wi_flags[Weapon::Info_Flags::Inherit_parent_target] && (!weaponp->wi_flags[Weapon::Info_Flags::Child]))
688+
{
689+
Warning(LOCATION, "Weapon %s has the \"inherit parent target\" flag, but not the \"child\" flag. No changes in behavior will occur.", weaponp->name);
690+
}
698691

699-
if (!weaponp->wi_flags[Weapon::Info_Flags::Cmeasure] && weaponp->wi_flags[Weapon::Info_Flags::Cmeasure_aspect_home_on])
700-
{
701-
weaponp->wi_flags.remove(Weapon::Info_Flags::Cmeasure_aspect_home_on);
702-
Warning(LOCATION, "Weapon %s has the \"pulls aspect seekers\" flag, but is not a countermeasure.\n", weaponp->name);
703-
}
692+
if (!weaponp->wi_flags[Weapon::Info_Flags::Homing_heat] && weaponp->wi_flags[Weapon::Info_Flags::Untargeted_heat_seeker])
693+
{
694+
Warning(LOCATION, "Weapon '%s' has the \"untargeted heat seeker\" flag, but Homing Type is not set to \"HEAT\".", weaponp->name);
695+
}
696+
697+
if (!weaponp->wi_flags[Weapon::Info_Flags::Cmeasure] && weaponp->wi_flags[Weapon::Info_Flags::Cmeasure_aspect_home_on])
698+
{
699+
weaponp->wi_flags.remove(Weapon::Info_Flags::Cmeasure_aspect_home_on);
700+
Warning(LOCATION, "Weapon %s has the \"pulls aspect seekers\" flag, but is not a countermeasure.\n", weaponp->name);
704701
}
705702
}
706703

0 commit comments

Comments
 (0)