refactoring

This commit is contained in:
rusefillc 2023-01-06 11:01:32 -05:00
parent a84335a76b
commit 27ef1c61d0
13 changed files with 188 additions and 163 deletions

View File

@ -3,7 +3,7 @@ package com.rusefi;
import com.devexperts.logging.Logging;
import com.opensr5.ini.field.EnumIniField;
import com.rusefi.core.Pair;
import com.rusefi.output.ConfigStructure;
import com.rusefi.output.ConfigStructureImpl;
import com.rusefi.output.DataLogConsumer;
import com.rusefi.output.JavaFieldsConsumer;
@ -115,7 +115,7 @@ public class ConfigField {
return Integer.parseInt(s);
}
public ConfigStructure getStructureType() {
public ConfigStructureImpl getStructureType() {
return getState().getStructures().get(getType());
}

View File

@ -33,10 +33,10 @@ public class ReaderState implements IReaderState {
private static final String STRUCT = "struct ";
// used to update other files
private final List<String> inputFiles = new ArrayList<>();
private final Stack<ConfigStructure> stack = new Stack<>();
private final Stack<ConfigStructureImpl> stack = new Stack<>();
private final Map<String, Integer> tsCustomSize = new HashMap<>();
private final Map<String, String> tsCustomLine = new HashMap<>();
private final Map<String, ConfigStructure> structures = new HashMap<>();
private final Map<String, ConfigStructureImpl> structures = new HashMap<>();
private String headerMessage;
// well, technically those should be a builder for state, not this state class itself
private String tsFileOutputName = "rusefi.ini";
@ -86,7 +86,7 @@ public class ReaderState implements IReaderState {
ConfigField bitField = new ConfigField(state, bitNameParts[0], comment, null, BOOLEAN_T, new int[0], null, false, false, false, trueName, falseName);
if (state.stack.isEmpty())
throw new IllegalStateException("Parent structure expected");
ConfigStructure structure = state.stack.peek();
ConfigStructureImpl structure = state.stack.peek();
structure.addBitField(bitField);
}
@ -193,7 +193,7 @@ public class ReaderState implements IReaderState {
private void handleEndStruct(List<ConfigurationConsumer> consumers) throws IOException {
if (stack.isEmpty())
throw new IllegalStateException("Unexpected end_struct");
ConfigStructure structure = stack.pop();
ConfigStructureImpl structure = stack.pop();
if (log.debugEnabled())
log.debug("Ending structure " + structure.getName());
structure.addAlignmentFill(this, 4);
@ -259,7 +259,7 @@ public class ReaderState implements IReaderState {
}
private void addBitPadding() {
ConfigStructure structure = stack.peek();
ConfigStructureImpl structure = stack.peek();
structure.addBitPadding(this);
}
@ -279,7 +279,7 @@ public class ReaderState implements IReaderState {
name = line;
comment = null;
}
ConfigStructure structure = new ConfigStructure(name, comment, withPrefix);
ConfigStructureImpl structure = new ConfigStructureImpl(name, comment, withPrefix);
state.stack.push(structure);
if (log.debugEnabled())
log.debug("Starting structure " + structure.getName());
@ -301,7 +301,7 @@ public class ReaderState implements IReaderState {
if (state.stack.isEmpty())
throw new IllegalStateException(cf.getName() + ": Not enclosed in a struct");
ConfigStructure structure = state.stack.peek();
ConfigStructureImpl structure = state.stack.peek();
Integer getPrimitiveSize = TypesHelper.getPrimitiveSize(cf.getType());
Integer customTypeSize = state.tsCustomSize.get(cf.getType());
@ -390,7 +390,7 @@ public class ReaderState implements IReaderState {
return tsCustomSize;
}
public Map<String, ConfigStructure> getStructures() {
public Map<String, ConfigStructureImpl> getStructures() {
return structures;
}

View File

@ -1,148 +1,19 @@
package com.rusefi.output;
import com.rusefi.BitState;
import com.rusefi.ConfigField;
import com.rusefi.ReaderState;
import com.rusefi.TypesHelper;
import java.util.ArrayList;
import java.util.HashSet;
import java.util.List;
import java.util.Set;
import static com.rusefi.ConfigField.BOOLEAN_T;
public interface ConfigStructure {
String getName();
/**
* Mutable representation of a list of related {@link ConfigField}
* <p>
* Andrey Belomutskiy, (c) 2013-2020
* 1/15/15
*/
public class ConfigStructure {
public static final String ALIGNMENT_FILL_AT = "alignmentFill_at_";
public static final String UNUSED_ANYTHING_PREFIX = "unused";
public static final String UNUSED_BIT_PREFIX = "unusedBit_";
int getTotalSize();
private final String name;
private final String comment;
private final boolean withPrefix;
private final List<ConfigField> cFields = new ArrayList<>();
private final List<ConfigField> tsFields = new ArrayList<>();
List<ConfigField> getTsFields();
private int totalSize;
List<ConfigField> getcFields();
private final BitState readingBitState = new BitState();
boolean isWithPrefix();
private ConfigField cPrevField = ConfigField.VOID;
private final Set<String> names = new HashSet<>();
public ConfigStructure(String name, String comment, boolean withPrefix) {
this.name = name;
this.comment = comment;
this.withPrefix = withPrefix;
}
public void addBitField(ConfigField bitField) {
addBoth(bitField);
this.readingBitState.incrementBitIndex(bitField);
}
public String getName() {
return name;
}
public void addAlignmentFill(ReaderState state, int alignment) {
if (alignment == 0)
return;
/**
* we make alignment decision based on C fields since we expect iteration and non-iteration fields
* to match in size
*/
FieldIteratorWithOffset iterator = new FieldIteratorWithOffset(cFields) {
@Override
public void end() {
super.end();
currentOffset += cf.getSize(next);
}
};
iterator.loop();
totalSize = iterator.currentOffset;
int fillSize = totalSize % alignment == 0 ? 0 : alignment - (totalSize % alignment);
if (fillSize > 3)
throw new IllegalStateException("Fill size does not look right: " + fillSize);
if (fillSize != 0) {
int[] fillSizeArray;
if (fillSize != 1) {
fillSizeArray = new int[1];
fillSizeArray[0] = fillSize;
} else {
fillSizeArray = new int[0];
}
ConfigField fill = new ConfigField(state, ALIGNMENT_FILL_AT + totalSize, "need 4 byte alignment",
"" + fillSize,
TypesHelper.UINT8_T, fillSizeArray, "\"units\", 1, 0, -20, 100, 0", false, false, false, null, null);
addBoth(fill);
}
totalSize += fillSize;
}
public void addBoth(ConfigField cf) {
addC(cf);
tsFields.add(cf);
}
public void addC(ConfigField cf) {
// skip duplicate names - that's the weird use-case of conditional project definition like lambdaTable
if (cf.getName().equals(cPrevField.getName()))
return;
boolean isNew = names.add(cf.getName());
if (!isNew)
throw new IllegalStateException(cf.getName() + " name already used");
cFields.add(cf);
cPrevField = cf;
}
public void addTs(ConfigField cf) {
tsFields.add(cf);
}
public void addBitPadding(ReaderState readerState) {
if (readingBitState.get() == 0)
return;
int sizeAtStartOfPadding = cFields.size();
while (readingBitState.get() < 32) {
ConfigField bitField = new ConfigField(readerState, UNUSED_BIT_PREFIX + sizeAtStartOfPadding + "_" + readingBitState.get(), "", null, BOOLEAN_T, new int[0], null, false, false, false, null, null);
addBitField(bitField);
}
readingBitState.reset();
}
public int getTotalSize() {
return totalSize;
}
public List<ConfigField> getTsFields() {
return tsFields;
}
/**
* We have two different collections because if 'array iterate' feature which is handled differently
* in C and TS
*/
public List<ConfigField> getcFields() {
return cFields;
}
public boolean isWithPrefix() {
return withPrefix;
}
public String getComment() {
return comment;
}
String getComment();
}

View File

@ -0,0 +1,154 @@
package com.rusefi.output;
import com.rusefi.BitState;
import com.rusefi.ConfigField;
import com.rusefi.ReaderState;
import com.rusefi.TypesHelper;
import java.util.ArrayList;
import java.util.HashSet;
import java.util.List;
import java.util.Set;
import static com.rusefi.ConfigField.BOOLEAN_T;
/**
* Mutable representation of a list of related {@link ConfigField}
* <p>
* Andrey Belomutskiy, (c) 2013-2020
* 1/15/15
*/
public class ConfigStructureImpl implements ConfigStructure {
public static final String ALIGNMENT_FILL_AT = "alignmentFill_at_";
public static final String UNUSED_ANYTHING_PREFIX = "unused";
public static final String UNUSED_BIT_PREFIX = "unusedBit_";
private final String name;
private final String comment;
private final boolean withPrefix;
private final List<ConfigField> cFields = new ArrayList<>();
private final List<ConfigField> tsFields = new ArrayList<>();
private int totalSize;
private final BitState readingBitState = new BitState();
private ConfigField cPrevField = ConfigField.VOID;
private final Set<String> names = new HashSet<>();
public ConfigStructureImpl(String name, String comment, boolean withPrefix) {
this.name = name;
this.comment = comment;
this.withPrefix = withPrefix;
}
public void addBitField(ConfigField bitField) {
addBoth(bitField);
this.readingBitState.incrementBitIndex(bitField);
}
@Override
public String getName() {
return name;
}
public void addAlignmentFill(ReaderState state, int alignment) {
if (alignment == 0)
return;
/**
* we make alignment decision based on C fields since we expect iteration and non-iteration fields
* to match in size
*/
FieldIteratorWithOffset iterator = new FieldIteratorWithOffset(cFields) {
@Override
public void end() {
super.end();
currentOffset += cf.getSize(next);
}
};
iterator.loop();
totalSize = iterator.currentOffset;
int fillSize = totalSize % alignment == 0 ? 0 : alignment - (totalSize % alignment);
if (fillSize > 3)
throw new IllegalStateException("Fill size does not look right: " + fillSize);
if (fillSize != 0) {
int[] fillSizeArray;
if (fillSize != 1) {
fillSizeArray = new int[1];
fillSizeArray[0] = fillSize;
} else {
fillSizeArray = new int[0];
}
ConfigField fill = new ConfigField(state, ALIGNMENT_FILL_AT + totalSize, "need 4 byte alignment",
"" + fillSize,
TypesHelper.UINT8_T, fillSizeArray, "\"units\", 1, 0, -20, 100, 0", false, false, false, null, null);
addBoth(fill);
}
totalSize += fillSize;
}
public void addBoth(ConfigField cf) {
addC(cf);
tsFields.add(cf);
}
public void addC(ConfigField cf) {
// skip duplicate names - that's the weird use-case of conditional project definition like lambdaTable
if (cf.getName().equals(cPrevField.getName()))
return;
boolean isNew = names.add(cf.getName());
if (!isNew)
throw new IllegalStateException(cf.getName() + " name already used");
cFields.add(cf);
cPrevField = cf;
}
public void addTs(ConfigField cf) {
tsFields.add(cf);
}
public void addBitPadding(ReaderState readerState) {
if (readingBitState.get() == 0)
return;
int sizeAtStartOfPadding = cFields.size();
while (readingBitState.get() < 32) {
ConfigField bitField = new ConfigField(readerState, UNUSED_BIT_PREFIX + sizeAtStartOfPadding + "_" + readingBitState.get(), "", null, BOOLEAN_T, new int[0], null, false, false, false, null, null);
addBitField(bitField);
}
readingBitState.reset();
}
@Override
public int getTotalSize() {
return totalSize;
}
@Override
public List<ConfigField> getTsFields() {
return tsFields;
}
/**
* We have two different collections because if 'array iterate' feature which is handled differently
* in C and TS
*/
@Override
public List<ConfigField> getcFields() {
return cFields;
}
@Override
public boolean isWithPrefix() {
return withPrefix;
}
@Override
public String getComment() {
return comment;
}
}

View File

@ -22,7 +22,7 @@ public class DataLogConsumer implements ConfigurationConsumer {
// https://github.com/rusefi/web_backend/issues/166
private static final int MSQ_LENGTH_LIMIT = 34;
public static final String UNUSED = ConfigStructure.UNUSED_ANYTHING_PREFIX;
public static final String UNUSED = ConfigStructureImpl.UNUSED_ANYTHING_PREFIX;
private final String fileName;
private final StringBuilder tsWriter = new StringBuilder();
private final TreeSet<String> comments = new TreeSet<>(String.CASE_INSENSITIVE_ORDER);

View File

@ -38,16 +38,16 @@ public class FragmentDialogConsumer implements ConfigurationConsumer {
int writeOneField(FieldIterator iterator, String prefix, int tsPosition) {
ConfigField configField = iterator.cf;
if (configField.getName().startsWith(ConfigStructure.ALIGNMENT_FILL_AT))
if (configField.getName().startsWith(ConfigStructureImpl.ALIGNMENT_FILL_AT))
return 0;
ConfigStructure cs = configField.getStructureType();
ConfigStructureImpl cs = configField.getStructureType();
if (cs != null) {
String extraPrefix = cs.isWithPrefix() ? configField.getName() + "_" : "";
return writeFields(cs.getTsFields(), prefix + extraPrefix, tsPosition);
}
if (configField.getName().startsWith(ConfigStructure.UNUSED_BIT_PREFIX))
if (configField.getName().startsWith(ConfigStructureImpl.UNUSED_BIT_PREFIX))
return 0;
if (configField.isBit()) {

View File

@ -14,7 +14,7 @@ import java.util.HashMap;
import java.util.List;
import java.util.concurrent.atomic.AtomicInteger;
import static com.rusefi.output.ConfigStructure.ALIGNMENT_FILL_AT;
import static com.rusefi.output.ConfigStructureImpl.ALIGNMENT_FILL_AT;
import static com.rusefi.output.DataLogConsumer.UNUSED;
import static com.rusefi.output.GetOutputValueConsumer.getHashConflicts;
import static com.rusefi.output.GetOutputValueConsumer.wrapSwitchStatement;

View File

@ -12,7 +12,7 @@ import java.util.HashMap;
import java.util.List;
import java.util.concurrent.atomic.AtomicInteger;
import static com.rusefi.output.ConfigStructure.ALIGNMENT_FILL_AT;
import static com.rusefi.output.ConfigStructureImpl.ALIGNMENT_FILL_AT;
import static com.rusefi.output.DataLogConsumer.UNUSED;
import static com.rusefi.output.GetConfigValueConsumer.FILE_HEADER;
import static com.rusefi.output.GetConfigValueConsumer.getCompareName;

View File

@ -64,7 +64,7 @@ public abstract class JavaFieldsConsumer implements ConfigurationConsumer {
if (configField.getName().equals(prev.getName())) {
return tsPosition;
}
ConfigStructure cs = configField.getStructureType();
ConfigStructureImpl cs = configField.getStructureType();
if (cs != null) {
String extraPrefix = cs.isWithPrefix() ? configField.getName() + "_" : "";
return writeFields(cs.getTsFields(), prefix + extraPrefix, tsPosition);

View File

@ -30,7 +30,7 @@ class PerFieldWithStructuresIterator extends FieldIterator {
@Override
public void end() {
ConfigStructure cs = cf.getState().getStructures().get(cf.getType());
ConfigStructureImpl cs = cf.getState().getStructures().get(cf.getType());
String content;
if (cs != null) {
if (cf.isFromIterate()) {

View File

@ -23,9 +23,9 @@ public class SdCardFieldsContent {
}
private String processOutput(ConfigField configField, String prefix) {
if (configField.getName().startsWith(ConfigStructure.ALIGNMENT_FILL_AT))
if (configField.getName().startsWith(ConfigStructureImpl.ALIGNMENT_FILL_AT))
return "";
if (configField.getName().startsWith(ConfigStructure.UNUSED_ANYTHING_PREFIX))
if (configField.getName().startsWith(ConfigStructureImpl.UNUSED_ANYTHING_PREFIX))
return "";
if (configField.isBit())
return "";

View File

@ -49,12 +49,12 @@ public class TsOutput {
*/
if (!usedNames.add(nameWithPrefix)
&& !isConstantsSection
&& !configField.getName().startsWith(ConfigStructure.ALIGNMENT_FILL_AT)
&& !configField.getName().startsWith(ConfigStructure.UNUSED_ANYTHING_PREFIX)) {
&& !configField.getName().startsWith(ConfigStructureImpl.ALIGNMENT_FILL_AT)
&& !configField.getName().startsWith(ConfigStructureImpl.UNUSED_ANYTHING_PREFIX)) {
throw new IllegalStateException(nameWithPrefix + " already present: " + configField);
}
if (configField.getName().startsWith(ConfigStructure.ALIGNMENT_FILL_AT)) {
if (configField.getName().startsWith(ConfigStructureImpl.ALIGNMENT_FILL_AT)) {
tsPosition += configField.getSize(next);
return tsPosition;
}
@ -65,7 +65,7 @@ public class TsOutput {
return tsPosition;
}
ConfigStructure cs = configField.getStructureType();
ConfigStructureImpl cs = configField.getStructureType();
if (configField.getComment() != null && configField.getComment().trim().length() > 0 && cs == null) {
String commentContent = configField.getCommentTemplated();
commentContent = ConfigField.unquote(commentContent);
@ -78,7 +78,7 @@ public class TsOutput {
}
if (configField.isBit()) {
if (!configField.getName().startsWith(ConfigStructure.UNUSED_BIT_PREFIX)) {
if (!configField.getName().startsWith(ConfigStructureImpl.UNUSED_BIT_PREFIX)) {
tsHeader.append(nameWithPrefix + " = bits, U32,");
tsHeader.append(" " + tsPosition + ", [");
tsHeader.append(bitIndex + ":" + bitIndex);

View File

@ -5,7 +5,7 @@ import com.rusefi.ReaderState;
import com.rusefi.TypesHelper;
import com.rusefi.VariableRegistry;
import com.rusefi.output.BaseCHeaderConsumer;
import com.rusefi.output.ConfigStructure;
import com.rusefi.output.ConfigStructureImpl;
import com.rusefi.output.JavaFieldsConsumer;
import com.rusefi.output.TSProjectConsumer;
import org.junit.Test;
@ -163,7 +163,7 @@ public class ConfigFieldParserTest {
assertEquals(16, TypesHelper.getElementSize(state, "pid_s"));
ConfigStructure structure = state.getStructures().get("pid_s");
ConfigStructureImpl structure = state.getStructures().get("pid_s");
ConfigField firstField = structure.getcFields().get(0);
assertEquals("ms", firstField.getUnits());
}