func NewResourceConfigShimmed(val cty.Value, schema *configschema.Block) *ResourceConfig {
	if !val.Type().IsObjectType() {
		panic(fmt.Errorf("NewResourceConfigShimmed given %#v; an object type is required", val.Type()))
	}
	ret := &ResourceConfig{}
	legacyVal := hcl2shim.ConfigValueFromHCL2Block(val, schema)
	if legacyVal != nil {
		ret.Config = legacyVal
		ret.ComputedKeys = newResourceConfigShimmedComputedKeys(val, "")
	} else {
		ret.Config = make(map[string]interface{})
	}
	ret.Raw = ret.Config
	return ret
}
NewResourceConfigShimmed wraps a cty.Value of object type in a legacy
ResourceConfig object, so that it can be passed to older APIs that expect
this wrapping.

The returned ResourceConfig is already interpolated and cannot be
re-interpolated. It is, therefore, useful only to functions that expect
an already-populated ResourceConfig which they then treat as read-only.

If the given value is not of an object type that conforms to the given
schema then this function will panic.
package terraform
import (
	"fmt"
	"reflect"
	"sort"
	"strconv"
	"strings"
	"github.com/mitchellh/copystructure"
	"github.com/mitchellh/reflectwalk"
	"github.com/zclconf/go-cty/cty"
	"github.com/hashicorp/terraform/addrs"
	"github.com/hashicorp/terraform/config"
	"github.com/hashicorp/terraform/configs/configschema"
	"github.com/hashicorp/terraform/configs/hcl2shim"
)
type Resource struct {
	Name       string
	Type       string
	CountIndex int
	Id           string
	Info         *InstanceInfo
	Config       *ResourceConfig
	Dependencies []string
	Diff         *InstanceDiff
	Provider     ResourceProvider
	State        *InstanceState
	Flags        ResourceFlag
}
func NewResource(addr addrs.ResourceInstance) *Resource {
	ret := &Resource{
		Name: addr.Resource.Name,
		Type: addr.Resource.Type,
	}
	if addr.Key != addrs.NoKey {
		switch tk := addr.Key.(type) {
		case addrs.IntKey:
			ret.CountIndex = int(tk)
		default:
			panic(fmt.Errorf("resource instance with key %#v is not supported", addr.Key))
		}
	}
	return ret
}
type ResourceFlag byte
type InstanceInfo struct {
	Id string
	ModulePath []string
	Type string
	uniqueExtra string
}
func NewInstanceInfo(addr addrs.AbsResourceInstance) *InstanceInfo {
	path := make([]string, len(addr.Module))
	for i, step := range addr.Module {
		if step.InstanceKey != addrs.NoKey {
			panic("NewInstanceInfo cannot convert module instance with key")
		}
		path[i] = step.Name
	}
	id := fmt.Sprintf("%s.%s", addr.Resource.Resource.Type, addr.Resource.Resource.Name)
	if addr.Resource.Resource.Mode == addrs.DataResourceMode {
		id = "data." + id
	}
	if addr.Resource.Key != addrs.NoKey {
		switch k := addr.Resource.Key.(type) {
		case addrs.IntKey:
			id = id + fmt.Sprintf(".%d", int(k))
		default:
			panic(fmt.Sprintf("NewInstanceInfo cannot convert resource instance with %T instance key", addr.Resource.Key))
		}
	}
	return &InstanceInfo{
		Id:         id,
		ModulePath: path,
		Type:       addr.Resource.Resource.Type,
	}
}
func (i *InstanceInfo) ResourceAddress() *ResourceAddress {
	id := i.Id
	instanceType := TypeInvalid
	if idx := strings.Index(id, " ("); idx != -1 {
		remain := id[idx:]
		id = id[:idx]
		switch {
		case strings.Contains(remain, "tainted"):
			instanceType = TypeTainted
		case strings.Contains(remain, "deposed"):
			instanceType = TypeDeposed
		}
	}
	addr, err := parseResourceAddressInternal(id)
	if err != nil {
		panic(fmt.Errorf("InstanceInfo has invalid Id %s", id))
	}
	if len(i.ModulePath) > 1 {
		addr.Path = i.ModulePath[1:]  
	}
	if instanceType != TypeInvalid {
		addr.InstanceTypeSet = true
		addr.InstanceType = instanceType
	}
	return addr
}
type ResourceConfig struct {
	ComputedKeys []string
	Raw          map[string]interface{}
	Config       map[string]interface{}
	raw *config.RawConfig
}
func NewResourceConfig(c *config.RawConfig) *ResourceConfig {
	result := &ResourceConfig{raw: c}
	result.interpolateForce()
	return result
}
func NewResourceConfigRaw(raw map[string]interface{}) *ResourceConfig {
	v := hcl2shim.HCL2ValueFromConfigValue(raw)
	cfg := hcl2shim.ConfigValueFromHCL2(v).(map[string]interface{})
	return &ResourceConfig{
		Raw:    raw,
		Config: cfg,
		ComputedKeys: newResourceConfigShimmedComputedKeys(v, ""),
	}
}